nRF24L01 +pa +lna link не связывается

Я пытаюсь создать связь между двумя блоками nRF24L01. Каждый модуль на базе nRF24L01+ подключается к Arduino Nano на специально разработанной печатной плате.

Печатная проводка соответствует аппаратному приложению и функционально проверяется положительным результатом метода isChipConnected ().

Питание NRF24L01 осуществляется от выхода Nano 3,3 В. Согласно спецификации компонента, это должно быть нормально:

• Согласно техническому паспорту, максимальное потребление составляет 9 мА при передаче с высокой мощностью. Нано-выход может излучать до 150 мА. Так что она не приближается к пределу.

• Я измерил линию питания 3,3 В, и значение 3,23 В на обоих модулях (указанный минимум 3,0 В).

• Питающая линия фильтруется колпачком 10 мкФ.

Две станции используют один и тот же код; роли определяются уровнем ввода-вывода. Он содержит два модуля - приложение и высокоуровневый класс драйверов.

Теперь перейдем к проблеме: судя по скриншотам Arduino, передатчик не отправляет данные. Поскольку низкоуровневая процедура передачи (radio.write()) ожидает автоматического подтверждения приемника, я также рассматривал возможность того, что сторона приемника не отправляет автоматическое ПОДТВЕРЖДЕНИЕ. Однако я отключил автоматическое подтверждение на обеих станциях, и результат не изменился.

Любая подсказка будет полезна. - Спасибо.

#define Radio0_IRQ   2
#define TerminalPin  6
#define CsnPin       10
#define terminalRole 1

String msgHeader;
bool role;
/************************************************/
void(*resetFunc) (void) = 0;//declare reset function at address 0
/***********************************************************/
#include "radioPortClass.h"
RadioPort communicationPort;

/************************************************/
void setup(void)
{
  pinMode(TerminalPin, INPUT_PULLUP);
  role = !digitalRead(TerminalPin);
  if(role == terminalRole)
    msgHeader = "Terminal: ";
  else
    msgHeader = "Field unit: ";

  Serial.begin(9600);
  while (!Serial)
    delay(10);
  if (communicationPort.portInit(role))
    Serial.println(msgHeader + "Port initiated successfully\n\n");
  else if (!radio.isChipConnected ())
  {
    Serial.println(msgHeader + "Port initiation failed\n\n");
    delay(2000);
    resetFunc();
  }
}
/***********************************************************/
void loop(void)
{
  if (role == terminalRole)
  {
// Terminal role. Transmit a message and receive the reply
    if (!communicationPort.tx("Terminal to field unit"))
      Serial.println(msgHeader + "Failed, transmit timed out.\n\n");
    else
    {
      Serial.print(msgHeader + "Got response: ");
      delay(1000);
      Serial.println(communicationPort.rx());
      started_waiting_at = millis();
    }
    delay(3000);
  }
  else  // Field unit role. Receive each packet, print it and reply
  {
    String receive_payload = communicationPort.rx();
    if (receive_payload == "\0")
    {
      if((millis() - started_waiting_at) > rxDelay)
      {
        Serial.println(msgHeader + "Failed, receive timed out.\n\n");
        delay(100);
        resetFunc(); //call reset    
      }
    }
    else
    {
      Serial.print  (msgHeader + "Got payload: ");
      Serial.println(receive_payload);
      if (!communicationPort.tx("Field unit to terminal"))
        Serial.println(msgHeader + "Failed, transmit timed out.\n\n");
      else
        Serial.println(msgHeader + "Sent response.\n\n");
    }
  }
}
 
Radio Driver
class RadioPort
{
  public:
    bool tx(String txData);
    String rx(void);
    bool portInit(bool role);
};
#include "RF24.h"
RF24 radio(9, CsnPin);

const uint64_t pipes[2] = {0xF0F0F0F0E1LL, 0xF0F0F0F0D2LL};
#define rxDelay   1000
#define txDelay   100
unsigned long started_waiting_at;

/************************************************/
bool RadioPort::tx(String txData)
{
// First, stop listening so we can talk.
  radio.stopListening();
  bool success = radio.write(&txData, txData.length());
  radio.startListening();
  return success;
}
/************************************************/
String RadioPort::rx(void)
{
 // if there is data ready
  if (radio.available())
  {
// Fetch the payload, and see if this was the last one.
    uint8_t len = radio.getDynamicPayloadSize();
    char receive_payload[len + 1];
    radio.read(receive_payload, len);
// Put a zero at the end for easy printing
    receive_payload[len] = 0;
    return receive_payload;
  }
  else return "\0";      // Dummy statement, for the compiler warning
}
/************************************************/
bool RadioPort::portInit(bool role)
{
  pinMode(Radio0_IRQ, INPUT_PULLUP);
  radio.begin();//(5,CsnPin)
  if(!radio.isChipConnected ())
    return false;

  radio.enableDynamicPayloads();
  radio.setRetries(15,15);
  radio.setPALevel(0, true);
  radio.setChannel(105);
  radio.setAutoAck(false);//true);
  
  if (role == terminalRole)
  {
    radio.openWritingPipe(pipes[0]);
    radio.openReadingPipe(1,pipes[1]);
  }
  else
  {
    radio.openWritingPipe(pipes[1]);
    radio.openReadingPipe(1,pipes[0]);
    started_waiting_at = millis();
  }
  radio.startListening();
  return true;
}

, 👍2

Обсуждение

"Согласно скриншотам Arduino" какие скриншоты? Вы подтверждаете, что каждый Arduino находится в своей правильной роли?, @timemage

Да: я открываю последовательный монитор для каждой станции. Как видно из кода, основной активностью метода LOOP скетча является печать сообщений на последовательный монитор, которые видны на последовательном мониторе. Все сообщения вызываются обратной связью сбоя методов tx и rx. Сообщения имеют префикс с ролью станции, поэтому я знаю, какой из них отправил его., @user1511360