nRF24L01+ : побеждаем модуль.

Тема в разделе "Проводная и беспроводная связь", создана пользователем ИгорьК, 19 июн 2014.

  1. parovoZZ

    parovoZZ Гуру

    бред. Напиши номер страницы из даташита, где такое написано.
     
  2. Ghosty

    Ghosty Нерд

  3. Faig

    Faig Нерд

    Этого не может быть, наверное совпало. Я думаю , вы стали отправлять по одному байту за раз поэтому перестало. Выж не весь буфер считываете как это может работать?
     
  4. Faig

    Faig Нерд

    Код (C++):
      * The maximum size of data written is the fixed payload size, see
       * getPayloadSize(). However, you can write less, and the remainder
       * will just be filled with zeroes.
    файл: RF24.h
    Строка: 215
    Коментарии к bool write( const void* buf, uint8_t len );
    Вы скажите если я что-то понял не правильно то, я удалю свой тот пост чтобы не загрязнять форум неверной информацией.
    А что вы насчет прерываний мне скажете? Дергаются ли они и при akcnowledge?
     
  5. parovoZZ

    parovoZZ Гуру

    я же просил даташит, а не комментарии к кривой библиотеке.

    Максимальный размер данных, который модуль может передать в одном пакете - 32 байта. Здесь же написано, что передавать можно и меньше, но надо добивать нулями, если приемная сторона ждет 32 байта в пакете. Если передавать меньше - приемная сторона не примет, т.к. структура пакета будет иной (все поля разъедутся и CRC проверку такой пакет не пройдет). Я вот прямо сейчас передаю всего 1 байт. И его же принимаю. Никаких нулей в пакете у меня нет.
     
    Последнее редактирование: 7 фев 2019
  6. Faig

    Faig Нерд

    Я ведь об этой библиотеке говорил.
     
  7. parovoZZ

    parovoZZ Гуру

    Если речь про данные в ACK пакете - сейчас не скажу. Надо либо даташит раскуривать, либо же подождать - у меня сейчас на стапеле как раз разработка с nRF.
     
  8. Faig

    Faig Нерд

    Но подождиде, а как приемник узнает размер передачи до ее передачи? Тут только в фиксед варианте удастся такое проделать, а с динамик пэйлоад получается нет?
     
  9. parovoZZ

    parovoZZ Гуру

    давай различать функции приемника и передатчика. Передатчик передает, приемник принимает. Передатчику длину данных задавать не нужно - он её сам считает на лету и помещает в соответствующее поле. Приемнику надо обязательно указывать какой размер данных ему принимать, либо же указать ему, что пакет может быть любой длины (хоть нулевой). Другое дело ACK пакет. Но про них я писал чуть выше. Повторяться не буду.
     
  10. Faig

    Faig Нерд

    Они же нули , как вы их увидите? Я думаю что единственный способ - это понапосылать 1000 пакетов сперва с одним полезным байтом а потом с 32 и посмотреть выросла ли задержда существенно или нет. И надо учесть еще навесок времени считывания из буфера, или обойти его. Чтобы обойти его, можно при считывании одного полезного байта выполнить эту операцию 32 раза вместо одного чтобы, разница была только во времени радиотрансмитта
     
    Последнее редактирование: 7 фев 2019
  11. Faig

    Faig Нерд

    Вот этот момент мне и интересен. Какой смысл, на приемнике, указывать фиксед сайз если приемнику можно указать "жди любой размер"?
     
  12. Faig

    Faig Нерд

    Спс, ничего, я уже понял что, придется копаться. Надеялся, мож кто уже пару собак съел на нем...
     
  13. parovoZZ

    parovoZZ Гуру

    наверное я уже с помощью ЛА посмотрел.
    Ещё раз - читать надо даташит, а не комментарий к кривой библиотеке.
     
  14. Ghosty

    Ghosty Нерд

    Друг, не знаю всех тонкостей, но с другой библиотекой работает.
    Пробовал тот же скетч но с библиотекой от продована - не принимает)
     
    Последнее редактирование: 7 фев 2019
  15. Faig

    Faig Нерд

    Код (C++):
    uint8_t RF24::write_payload(const void* buf, uint8_t data_len, const uint8_t writeType)
    {
      uint8_t status;
      const uint8_t* current = reinterpret_cast<const uint8_t*>(buf);

       data_len = rf24_min(data_len, payload_size);
       uint8_t blank_len = dynamic_payloads_enabled ? 0 : payload_size - data_len;

      //printf("[Writing %u bytes %u blanks]",data_len,blank_len);
      IF_SERIAL_DEBUG( printf("[Writing %u bytes %u blanks]\n",data_len,blank_len); );

    #if defined (RF24_LINUX)
        beginTransaction();
        uint8_t * prx = spi_rxbuff;
        uint8_t * ptx = spi_txbuff;
        uint8_t size;
        size = data_len + blank_len + 1 ; // Add register value to transmit buffer

        *ptx++ =  writeType;
        while ( data_len-- )
          *ptx++ =  *current++;
        while ( blank_len-- )
          *ptx++ =  0;

        _SPI.transfernb( (char *) spi_txbuff, (char *) spi_rxbuff, size);
        status = *prx; // status is 1st byte of receive buffer
        endTransaction();

      #else

      beginTransaction();
      status = _SPI.transfer( writeType );
      while ( data_len-- ) {
        _SPI.transfer(*current++);
      }
      while ( blank_len-- ) {
        _SPI.transfer(0);
      }
      endTransaction();

      #endif

      return status;
    }
    Вот и раскрыта тайна авто подгрузки нулей в RF24.h:
    Код (C++):
     uint8_t blank_len = dynamic_payloads_enabled ? 0 : payload_size - data_len;
    Если не включить "dynamic payload" или не изменить (
    "setPayloadSize()") "payload_size" то библиотека берет за размер 32 байта, как я понял. Вот и верь теперь после этого людям(я о библиотеке) на слово...

    А какую именно другую библиотеку?
     
    Последнее редактирование: 7 фев 2019
  16. Ghosty

    Ghosty Нерд

     
  17. Faig

    Faig Нерд

    Дорогие товарищи,
    Подскажите полжалуйста что я упустил? Работает только первая часть кода до того как я меняю назначения передатчика и приемник. То есть, до delay(1000);
    Update: Если не использовать delay() то вроде бы работает. Дай Бог все протестирую и отпишусь с отчетом.

    Код (C++):
    //Receiver

    #include <RF24.h>
    #include <RF24_config.h>
    #include <SPI.h>
    #include "printf.h"
    // Set pipes
    const uint64_t pipe01_ = 0xE8E8F0F0A1LL;
    const uint64_t pipe02_ = 0xE8E8F0F0A2LL;
    const uint64_t pipe03_ = 0xA3LL;
    const uint64_t pipe04_ = 0xA4LL;
    const uint64_t pipe05_ = 0xA5LL;
    const uint64_t pipe06_ = 0xA6LL;
    RF24 radio(9, 53);

    void setup()
    {
        Serial.begin(115200);
        delay(250);
        radio.begin();
        radio.setChannel(0x57);
        radio.setPALevel(RF24_PA_LOW);
        radio.enableAckPayload();
        radio.openReadingPipe(1, pipe01_);
        radio.openWritingPipe(pipe02_);
        radio.enableDynamicPayloads();
        radio.startListening();
    }

    void loop()
    {
        if (radio.available())
        {
            char newMessage[33];
            memset(newMessage, 0, sizeof(byte) * 33);
            while (radio.available())    
            {radio.read(newMessage, 32);}
       
            Serial.println("newMessage: " + String((const char*)newMessage));
            delay(1000);
            radio.stopListening();

            char response[32] = "1234567890qwertyuiopasdfghjklzxc";
            radio.write(response, 32);
            unsigned long ack = 0;
            if (radio.isAckPayloadAvailable())
            {
                radio.read(&ack, sizeof(ack));
                Serial.println("ack: " + String(ack));
            }
            radio.startListening();
        }
    }
    Код (C++):
    //Sender
    #include <RF24.h>
    #include <RF24_config.h>
    #include <SPI.h>
    #include "printf.h"
    const uint64_t pipe01_ = 0xE8E8F0F0A1LL;
    const uint64_t pipe02_ = 0xA2LL;
    const uint64_t pipe03_ = 0xA3LL;
    const uint64_t pipe04_ = 0xA4LL;
    const uint64_t pipe05_ = 0xA5LL;
    const uint64_t pipe06_ = 0xA6LL;
    RF24 radio(9, 53);

    void setup()
    {
        Serial.begin(115200);
        delay(250);
        radio.begin();
        radio.setChannel(0x57);
        radio.setPALevel(RF24_PA_LOW);
        radio.enableAckPayload();
        radio.openReadingPipe(2, pipe02_);
        radio.openWritingPipe(pipe01_);
        radio.enableDynamicPayloads();
        radio.stopListening();

        char message[32] = "qwertyuiopasdfghjklzxc1234567890";
        radio.write(message, 32);

        radio.startListening();
    }

    void loop()
    {
        if (radio.available())
        {
            char respMessage[33];
            memset(respMessage, 0, sizeof(byte) * 33);
            while (radio.available())
            {radio.read(respMessage, 32);}

            Serial.println("respMessage: " + String((const char*)respMessage));
        }
    }
    Ну очень мало времени на ковыряния и разбирательства :( может у кого есть быстрый ответ?
     
    Последнее редактирование: 10 фев 2019
  18. ImrDuke

    ImrDuke Гик

    А что должны делать первый и второй скетчи?
     
  19. Faig

    Faig Нерд

    Первый скетч ждет сообщение. Как только получит его печетает его, потом ждет 1 секунду переводит модуль в режим отправки и отправляет ответное сообщение.
    Второй скетч отправляет сообщение как тоьлко включился, потом сразу переводит радио-модуль в режим приема и ждет ответа.
     
  20. parovoZZ

    parovoZZ Гуру

    Не проще ли это делать через ACK ответ?