Помните, как мы удаленно мигали светодиодом при помощи NRF24L01 , а затем использовали этот же беспроводной модуль для управления гусеничным роботом ? В этих заметках модуль мы использовали по принципу «подключаем к таким-то пинам, берем готовую библиотеку, пишем пару строк кода и все работает, магия». Так вот, мне не нравится магия. Я программист, а не колдун, и потому хочу знать точно, что там и в каком виде передается в эфире. К счастью, Software Defined Radio позволяет с легкостью это увидеть.

Итак, первым делом я залил в Arduino следующий скетч:

#include <Arduino.h>
#include «nRF24L01.h»
#include «RF24.h»

RF24 radio ( 9 , 10 ) ;

void setup ( void )
{
radio. begin ( ) ;
radio. setChannel ( 108 ) ;
radio. setPALevel ( RF24_PA_LOW ) ;
radio. setDataRate ( RF24_250KBPS ) ;
radio. openWritingPipe ( 0xA1B2C3D4E5 ) ;
}

void loop ( void )
{
uint8_t state [ ] = { 0x00 , 0x11 , 0x22 , 0x33 , 0x44 , 0x55 , 0x66 , 0x77 } ;
delay ( 100 ) ;
radio. write ( & state, sizeof ( state ) ) ;
}

Как видите, он просто передает раз в 100 мс довольно бессмысленный пакет размером 8 байт на 108-м канале. С помощью LimeSDR и Gqrx несложно увидеть, что сигнал, в соответствии с нашими ожиданиями, передается на частоте 2508 МГц (2400 + номер канала). Также Gqrx позволяет записать сигнал в файл, чтобы сигнал этот можно было, например, лучше рассмотреть в Inspectrum:

Каждый вызов radio.write сопровождается посылкой 16-и пакетов (см верхнюю часть картинки). Забегая немного вперед отмечу, что пакеты абсолютно идентичны и посылаются повторно исключительно для избыточности. Если приблизить один из этих пакетов (см нижнюю часть картинки), можно фактически увидеть единички и нолики, передаваемые при помощи изменения частоты сигнала. Как нам уже известно, NRF24L01 использует модуляцию GFSK , поэтому такой результат был вполне ожидаем. В сигнале можно заметить длинную последовательность нулей. Это тоже вполне объяснимо, если вспомнить, что максимальный размер пакета у NRF24L01 составляет 32 байта, из которых мы использовали только 8.

Декодировать GFSK можно при помощи такого проекта в GNU Radio:

Изучать получившийся в итоге сигнал можно, конечно, и в Scope Sink, но на практике это не очень-то удобно. Scope Sink подходит разве что для визуального определения, что что-то действительно декодировалось. Для просмотра получившегося сигнала лучше подходит утилита под названием baudline . Открываем файл, указав sample rate, использованный при записи (в моем случае это 5000000), а также формат 32 bit float, little endian. Открываем окно waveform и ищем что-то вроде:

Фактически, это уже единички и нолики в чистом виде. Как не видите единичек и ноликов? Да вот же они:

Здесь красная полоска означает границу бита, а синяя полоска — границу байта. Аккуратно выписав единички и нолики, получаем:

10101010  AA <- преамбула
10100001  A1 <- 5 байт адреса
10110010  B2
11000011  C3
11010100  D4
11100101  E5
11001101  CD <- видимо, флаги
00000000  00 <- данные
00010001  11
00100010  22
00110011  33
01000100  44
…

То есть, при сильном желании теперь мы можем написать софтверный декодер пакетов. Только польза от такого проекта, на мой взгляд, будет несколько сомнительной. Во-первых, потому что такой проект уже есть , и, возможно, не один. А во-вторых, потому что пакеты намного проще декодировать при помощи самого NRF24L01 и Arduino. Может понадобиться разве что знать адрес передающего устройства, но мы только что выяснили, как его определить. Впрочем, если рассматривать задачу исключительно как code kata на выходные, то почему бы и нет.

Все исходники к посту, как обычно, вы найдете на GitHub .

admin

Share
Published by
admin

Recent Posts

Настройка Mercurial по HTTPS

Иногда mercurial, при скачивании и комитах ругается на https. Особенно на самоподписанные сертификаты. Чтобы заработал…

6 месяцев ago

Компиляция libvirt в Ubuntu

Компиляция libvirt Подробнее

6 месяцев ago

Ошибка libvirt permission denied: решение

Если возникает ошибка libvirt destroy lxc permission denied , при попытке остановить контейнер: _x000D_# virsh…

6 месяцев ago

Настройка редиректа в NGINX

Файлы с примерами редиректа для nginx Подробнее

6 месяцев ago

Включение gzip в NGINX

Как включить gzip сжатие в Nginx ? Подробнее

6 месяцев ago

Удаление postinst-скрипта в Linux

Иногда возникает ситуация, когда криво настроенные пакеты не устанавливаются в системе. У меня это произошло…

6 месяцев ago