Closed Ganesh-Shanbhag closed 3 years ago
You may have to set setAutoAck(0,false) before sending because the writing pipe (pipe0) needs AA disabled when broadcasting. Call setAutoAck(0,true) before sending normal payloads. You could also try using dynamic acks as well.
On Jan 25, 2021, at 7:40 AM, Ganesh-Shanbhag notifications@github.com wrote:
My requirements are using an address for broadcasting message to all the devices present which should not send an ACK after reception all the device will listen to this address on pipe 2. And every device will listen to its own address on pipe 0 which must send an ACK after successful reception.
So I disabled ACK on pipe 2 by using setAutoAck(2, false) but when I broadcasted data then none of the devices received the message although they are listening on the broadcast address. But when sent from one device to other with recipient's address it was sent successfully.
So how to perform a NONACK write on broadcast address such that all can receive the message?
— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub, or unsubscribe.
Hi I followed you but still I am not able to broadcast. If I did any mistakes in the code let me know I am sharing my code here. I took 3 nodes but for simplicity I initially took only two nodes to try. I am using Arduino Nano in all the devices.
/********** Node 2 code **********/
#include <RF24.h>
RF24 node(7, 8); // CE, CSN
byte netAddr[] = {0x31, 0x30, 0x30}; // Broadcast address
byte nodeAddr[] = {0x32, 0x30, 0x30}; // Node 2 address
void setup() {
Serial.begin(9600);
node.begin();
node.setPALevel(RF24_PA_MIN);
node.setDataRate(RF24_250KBPS);
node.setAddressWidth(3);
node.setChannel(3);
// Address to read broadcast messages (NOACK messages)
node.openReadingPipe(2, netAddr);
node.setAutoAck(2, false);
// Address to read ACK messages
node.openReadingPipe(0, nodeAddr);
////////////////////////////////////////////////////////////////////////////////////////////////
Serial.print("Network Address: "); Serial.write(netAddr, sizeof(netAddr)); Serial.println();
Serial.print("Channel : "); Serial.println(node.getChannel());
Serial.print("Node Address : "); Serial.write(nodeAddr, sizeof(nodeAddr)); Serial.println();
////////////////////////////////////////////////////////////////////////////////////////////////
}
void loop() {
if (Serial.available()) {
char buf[32] = "";
String str = Serial.readString();
// Write ACK message to node 3
if (str == "n3") {
strcpy(buf, "Hi I am node 2");
// Write to other node address
byte addr[3] = {0x33, 0x30, 0x30};
node.setAutoAck(0, true);
node.openWritingPipe(addr);
Serial.println("Writing to node 3");
}
// Write NOACK message
else if (str == "br") {
strcpy(buf, "Node 2 broadcasted a message");
// Write to other node address
node.setAutoAck(0, false);
node.openWritingPipe(netAddr);
Serial.println("Broadcasting");
}
node.stopListening();
if (node.write(&buf, sizeof(buf)))
Serial.println("Success");
else
Serial.println("Failed");
}
node.startListening();
if (node.available()) {
char buf[32] = "";
node.read(&buf, sizeof(buf));
Serial.println(buf);
}
}
/********** Node 3 code **********/
#include <RF24.h>
RF24 node(7, 8); // CE, CSN
byte netAddr[] = {0x31, 0x30, 0x30}; // Broadcast Address
byte nodeAddr[] = {0x33, 0x30, 0x30}; // Node 3 Address
void setup() {
Serial.begin(9600);
node.begin();
node.setPALevel(RF24_PA_MIN);
node.setDataRate(RF24_250KBPS);
node.setAddressWidth(3);
node.setChannel(3);
// Address to read broadcast messages (NOACK messages)
node.openReadingPipe(2, netAddr);
node.setAutoAck(2, false);
// Address to read ACK messages
node.openReadingPipe(0, nodeAddr);
////////////////////////////////////////////////////////////////////////////////////////////////
Serial.print("Network Address: "); Serial.write(netAddr, sizeof(netAddr)); Serial.println();
Serial.print("Channel : "); Serial.println(node.getChannel());
Serial.print("Node Address : "); Serial.write(nodeAddr, sizeof(nodeAddr)); Serial.println();
////////////////////////////////////////////////////////////////////////////////////////////////
}
void loop() {
if (Serial.available()) {
char buf[32] = "";
String str = Serial.readString();
// Write ACK message to node 2
if (str == "n2") {
strcpy(buf, "Hi I am node 3");
byte addr[3] = {0x32, 0x30, 0x30};
// Write to other node address
node.setAutoAck(0, true);
node.openWritingPipe(addr);
Serial.println("Writing to node 2");
}
// Write NOACK message
else if (str == "br") {
strcpy(buf, "Node 3 broadcasted a message");
// Write to other node address
node.setAutoAck(0, false);
node.openWritingPipe(netAddr);
Serial.println("Broadcasting");
}
node.stopListening();
if (node.write(&buf, sizeof(buf)))
Serial.println("Success");
else
Serial.println("Failed");
}
node.startListening();
if (node.available()) {
char buf[32] = "";
node.read(&buf, sizeof(buf));
Serial.println(buf);
}
}
If you can send data using auto-ack, then you're probably not using a clone/counterfeit radio. I would have tried the enableDynamicAck()
in setup()
and simply use the multicast
set to true
in calls to write()
when no ACK is desired.
If transmissions with auto-ack are not getting received, then you may have a different problem.
Also, docs recommend using pipe 1 to receive and leaving pipe 0 to only transmit. Remember that pipes 2-5 use the first 4 LSBytes from pipe 1's address and only allows setting the MSByte of an address to any pipe greater than 1.
Also, docs recommend using pipe 1 to receive and leaving pipe 0 to only transmit. Remember that pipes 2-5 use the first 4 LSBytes from pipe 1's address and only allows setting the MSByte of an address to any pipe greater than 1.
@2bndy5 As per my knowledge pipe 1-5 uses the first 4 MSBytes (Byte 4 to 1) from pipe 1 with LSByte (Byte 0) always unique and must be greater than 1. Correct me if I am wrong.
I get my endianess backwards all the time. I would consult the datasheet for correctness. I think the docs have this mentioned with example code snippet.
The fact is that your code never sets an address to pipe 1. If your program is running after a power-on-reset (unplug and replug the USB cable), then the address used on pipe 2 is probably 0xc2c231
. Use printDetails()
to verify the addresses on the pipes.
@TMRh20 and @2bndy5 Thanks for your suggestions and input now it is working as per my expectation.
I am sharing my code here. For any further doubts/questions I will reach you guys
/************* Node 2 code ****************/
#include <RF24.h>
RF24 node(7, 8); // CE, CSN
byte netAddr[] = {0x31, 0x30, 0x30}; // Broadcast Address
byte nodeAddr[] = {0x32, 0x30, 0x30}; // Node 2 Address
void setup() {
Serial.begin(9600);
node.begin();
node.setPALevel(RF24_PA_MIN);
node.setDataRate(RF24_250KBPS);
node.setAddressWidth(3);
node.setChannel(3);
// Listen to broadcast Address
node.openReadingPipe(2, netAddr);
// Disable ACK on broadcast address
node.setAutoAck(2, false);
// Listen to its own address
node.openReadingPipe(1, nodeAddr);
////////////////////////////////////////////////////////////////////////////////////////////////
Serial.print("Network Address: "); Serial.write(netAddr, sizeof(netAddr)); Serial.println();
Serial.print("Channel : "); Serial.println(node.getChannel());
Serial.print("Node Address : "); Serial.write(nodeAddr, sizeof(nodeAddr)); Serial.println();
////////////////////////////////////////////////////////////////////////////////////////////////
}
void loop() {
if (Serial.available()) {
char buf[32] = "";
String str = Serial.readString();
if (str == "n3") {
byte addr[3] = {0x33, 0x30, 0x30};
// Enable ACK on pipe 0
node.setAutoAck(0, true);
// Write to other node address
node.openWritingPipe(addr);
Serial.println("Writing to node 3");
}
else if (str == "br") {
// Disable ACK on pipe 0 for broadcast
node.setAutoAck(0, false);
// Write to broadcast address
node.openWritingPipe(netAddr);
Serial.println("Broadcasting");
}
if (str == "n3")
strcpy(buf, "Hi I am node 2");
else if (str == "br")
strcpy(buf, "Node 2 broadcasted a message");
node.stopListening();
if (node.write(&buf, sizeof(buf)))
Serial.println("Success");
else
Serial.println("Failed");
}
node.startListening();
if (node.available()) {
char buf[32] = "";
node.read(&buf, sizeof(buf));
Serial.println(buf);
}
}
/************* Node 3 code ****************/
#include <RF24.h>
RF24 node(7, 8); // CE, CSN
byte netAddr[] = {0x31, 0x30, 0x30}; // Broadcast address
byte nodeAddr[] = {0x33, 0x30, 0x30}; // Node 3 address
void setup() {
delay(500);
Serial.begin(9600);
node.begin();
node.setPALevel(RF24_PA_MIN);
node.setDataRate(RF24_250KBPS);
node.setAddressWidth(3);
node.setChannel(3);
// Listen to broadcast Address
node.openReadingPipe(2, netAddr);
// Disable ACK on broadcast address
node.setAutoAck(2, false);
// Listen to its own address
node.openReadingPipe(1, nodeAddr);
////////////////////////////////////////////////////////////////////////////////////////////////
Serial.print("Network Address: "); Serial.write(netAddr, sizeof(netAddr)); Serial.println();
Serial.print("Channel : "); Serial.println(node.getChannel());
Serial.print("Node Address : "); Serial.write(nodeAddr, sizeof(nodeAddr)); Serial.println();
////////////////////////////////////////////////////////////////////////////////////////////////
}
void loop() {
if (Serial.available()) {
char buf[32] = "";
String str = Serial.readString();
if (str == "n2") {
byte addr[3] = {0x32, 0x30, 0x30};
// Enable ACK on pipe 0
node.setAutoAck(0, true);
// Write to other node address
node.openWritingPipe(addr);
Serial.println("Writing to node 2");
}
else if (str == "br") {
// Disable ACK on pipe 0 for broadcast
node.setAutoAck(0, false);
// Write to broadcast address
node.openWritingPipe(netAddr);
Serial.println("Broadcasting");
}
if (str == "n2")
strcpy(buf, "Hi I am node 3");
else if (str == "br")
strcpy(buf, "Node 3 broadcasted a message");
node.stopListening();
if (node.write(&buf, sizeof(buf)))
Serial.println("Success");
else
Serial.println("Failed");
}
node.startListening();
if (node.available()) {
char buf[32] = "";
node.read(&buf, sizeof(buf));
Serial.println(buf);
}
}
My requirements are using an address for broadcasting message to all the devices present which should not send an ACK after reception all the device will listen to this address on pipe 2. And every device will listen to its own address on pipe 0 which must send an ACK after successful reception.
So I disabled ACK on pipe 2 by using setAutoAck(2, false) but when I broadcasted data then none of the devices received the message although they are listening on the broadcast address. But when sent from one device to other with recipient's address it was sent successfully.
So how to perform a NONACK write on broadcast address such that all can receive the message?