Optimized high speed nRF24L01+ driver class documentation v1.4.10
TMRh20 2020 - Optimized fork of the nRF24L01+ driver
Loading...
Searching...
No Matches
examples/old_backups/GettingStarted_HandlingFailures/GettingStarted_HandlingFailures.ino

Written by TMRh20 in 2019

This example demonstrates the basic getting started functionality, but with failure handling for the radio chip. Addresses random radio failures etc, potentially due to loose wiring on breadboards etc.

1
2/*
3 Getting Started example sketch for nRF24L01+ radios
4 This is a very basic example of how to send data from one node to another
5 but modified to include failure handling.
6
7 The nrf24l01+ radios are fairly reliable devices, but on breadboards etc, with inconsistent wiring, failures may
8 occur randomly after many hours to days or weeks. This sketch demonstrates how to handle the various failures and
9 keep the radio operational.
10
11 The three main failure modes of the radio include:
12 Writing to radio: Radio unresponsive - Fixed internally by adding a timeout to the internal write functions in RF24 (failure handling)
13 Reading from radio: Available returns true always - Fixed by adding a timeout to available functions by the user. This is implemented internally in RF24Network.
14 Radio configuration settings are lost - Fixed by monitoring a value that is different from the default, and re-configuring the radio if this setting reverts to the default.
15
16 The printDetails output should appear as follows for radio #0:
17
18 STATUS = 0x0e RX_DR=0 TX_DS=0 MAX_RT=0 RX_P_NO=7 TX_FULL=0
19 RX_ADDR_P0-1 = 0x65646f4e31 0x65646f4e32
20 RX_ADDR_P2-5 = 0xc3 0xc4 0xc5 0xc6
21 TX_ADDR = 0x65646f4e31
22 RX_PW_P0-6 = 0x20 0x20 0x00 0x00 0x00 0x00
23 EN_AA = 0x3f
24 EN_RXADDR = 0x02
25 RF_CH = 0x4c
26 RF_SETUP = 0x03
27 CONFIG = 0x0f
28 DYNPD/FEATURE = 0x00 0x00
29 Data Rate = 1MBPS
30 Model = nRF24L01+
31 CRC Length = 16 bits
32 PA Power = PA_LOW
33
34 Users can use this sketch to troubleshoot radio module wiring etc. as it makes the radios hot-swappable
35
36 Updated: 2019 by TMRh20
37*/
38
39#include <SPI.h>
40#include "RF24.h"
41#include "printf.h"
42
43/****************** User Config ***************************/
44/*** Set this radio as radio number 0 or 1 ***/
45bool radioNumber = 0;
46
47/* Hardware configuration: Set up nRF24L01 radio on SPI bus plus pins 7 & 8 */
48RF24 radio(7, 8);
49/**********************************************************/
50
51byte addresses[][6] = { "1Node", "2Node" };
52
53// Used to control whether this node is sending or receiving
54bool role = 0;
55
56
57/**********************************************************/
58//Function to configure the radio
59void configureRadio() {
60
61 radio.begin();
62
63 // Set the PA Level low to prevent power supply related issues since this is a
64 // getting_started sketch, and the likelihood of close proximity of the devices. RF24_PA_MAX is default.
65 radio.setPALevel(RF24_PA_LOW);
66
67 // Open a writing and reading pipe on each radio, with opposite addresses
68 if (radioNumber) {
69 radio.openWritingPipe(addresses[1]);
70 radio.openReadingPipe(1, addresses[0]);
71 } else {
72 radio.openWritingPipe(addresses[0]);
73 radio.openReadingPipe(1, addresses[1]);
74 }
75
76 // Start the radio listening for data
77 radio.startListening();
78 radio.printDetails();
79}
80
81
82/**********************************************************/
83
84void setup() {
85 Serial.begin(115200);
86 Serial.println(F("RF24/examples/GettingStarted"));
87 Serial.println(F("*** PRESS 'T' to begin transmitting to the other node"));
88
90
91 configureRadio();
92}
93
94uint32_t configTimer = millis();
95
96void loop() {
97
98 if (radio.failureDetected) {
99 radio.failureDetected = false;
100 delay(250);
101 Serial.println("Radio failure detected, restarting radio");
102 configureRadio();
103 }
104 // Every 5 seconds, verify the configuration of the radio. This can be
105 // done using any setting that is different from the radio defaults.
106 if (millis() - configTimer > 5000) {
107 configTimer = millis();
108 if (radio.getDataRate() != RF24_1MBPS) {
109 radio.failureDetected = true;
110 Serial.print("Radio configuration error detected");
111 }
112 }
113
114
115 /****************** Ping Out Role ***************************/
116
117 if (role == 1) {
118
119 radio.stopListening(); // First, stop listening so we can talk.
120
121 Serial.println(F("Now sending"));
122
123 unsigned long start_time = micros(); // Take the time, and send it. This will block until complete
124 if (!radio.write(&start_time, sizeof(unsigned long))) {
125 Serial.println(F("failed"));
126 }
127
128 radio.startListening(); // Now, continue listening
129
130 unsigned long started_waiting_at = micros(); // Set up a timeout period, get the current microseconds
131 bool timeout = false; // Set up a variable to indicate if a response was received or not
132
133 while (!radio.available()) // While nothing is received
134 {
135 if (micros() - started_waiting_at > 200000) // If waited longer than 200ms, indicate timeout and exit while loop
136 {
137 timeout = true;
138 break;
139 }
140 }
141
142 if (timeout) {
143 // Describe the results
144 Serial.println(F("Failed, response timed out."));
145 } else {
146 // Grab the response, compare, and send to debugging spew
147
148 unsigned long got_time; // Variable for the received timestamp
149
150 // Failure Handling
151 uint32_t failTimer = millis();
152 while (radio.available()) // If available() always returns true, there is a problem
153 {
154 if (millis() - failTimer > 250) {
155 radio.failureDetected = true;
156 Serial.println("Radio available failure detected");
157 break;
158 }
159 radio.read(&got_time, sizeof(unsigned long));
160 }
161 unsigned long end_time = micros();
162
163 // Spew it
164 Serial.print(F("Sent "));
165 Serial.print(start_time);
166 Serial.print(F(", Got response "));
167 Serial.print(got_time);
168 Serial.print(F(", Round-trip delay "));
169 Serial.print(end_time - start_time);
170 Serial.println(F(" microseconds"));
171 }
172
173 delay(1000); // Try again 1s later
174 }
175
176
177 /****************** Pong Back Role ***************************/
178
179 if (role == 0) {
180 unsigned long got_time; // Variable for the received timestamp
181
182 if (radio.available()) {
183 uint32_t failTimer = millis();
184
185 while (radio.available()) // While there is data ready
186 {
187 if (millis() - failTimer > 500) {
188 Serial.println("Radio available failure detected");
189 radio.failureDetected = true;
190 break;
191 }
192 radio.read(&got_time, sizeof(unsigned long)); // Get the payload
193 }
194
195 radio.stopListening(); // First, stop listening so we can talk
196 radio.write(&got_time, sizeof(unsigned long)); // Send the final one back.
197 radio.startListening(); // Now, resume listening so we catch the next packets.
198 Serial.print(F("Sent response "));
199 Serial.println(got_time);
200 }
201 }
202
203
204 /****************** Change Roles via Serial Commands ***************************/
205
206 if (Serial.available()) {
207 char c = toupper(Serial.read());
208 if (c == 'T' && role == 0) {
209 Serial.println(F("*** CHANGING TO TRANSMIT ROLE -- PRESS 'R' TO SWITCH BACK"));
210 role = 1; // Become the primary transmitter (ping out)
211 } else if (c == 'R' && role == 1) {
212 Serial.println(F("*** CHANGING TO RECEIVE ROLE -- PRESS 'T' TO SWITCH BACK"));
213 role = 0; // Become the primary receiver (pong back)
214 radio.startListening();
215 }
216 }
217} // Loop
Driver class for nRF24L01(+) 2.4GHz Wireless Transceiver.
Definition RF24.h:116
@ RF24_1MBPS
Definition RF24.h:83
@ RF24_PA_LOW
Definition RF24.h:50
#define delay(millisec)
#define millis()
void printf_begin(void)
Definition printf.h:33