RadioHead
RadioHead.h
1 // RadioHead.h
2 // Author: Mike McCauley (mikem@airspayce.com) DO NOT CONTACT THE AUTHOR DIRECTLY
3 // Copyright (C) 2014 Mike McCauley
4 // $Id: RadioHead.h,v 1.68 2017/11/06 00:04:08 mikem Exp mikem $
5 
6 /// \mainpage RadioHead Packet Radio library for embedded microprocessors
7 ///
8 /// This is the RadioHead Packet Radio library for embedded microprocessors.
9 /// It provides a complete object-oriented library for sending and receiving packetized messages
10 /// via a variety of common data radios and other transports on a range of embedded microprocessors.
11 ///
12 /// The version of the package that this documentation refers to can be downloaded
13 /// from http://www.airspayce.com/mikem/arduino/RadioHead/RadioHead-1.81.zip
14 /// You can find the latest version of the documentation at http://www.airspayce.com/mikem/arduino/RadioHead
15 ///
16 /// You can also find online help and discussion at
17 /// http://groups.google.com/group/radiohead-arduino
18 /// Please use that group for all questions and discussions on this topic.
19 /// Do not contact the author directly, unless it is to discuss commercial licensing.
20 /// Before asking a question or reporting a bug, please read
21 /// - http://en.wikipedia.org/wiki/Wikipedia:Reference_desk/How_to_ask_a_software_question
22 /// - http://www.catb.org/esr/faqs/smart-questions.html
23 /// - http://www.chiark.greenend.org.uk/~shgtatham/bugs.html
24 ///
25 /// \par Overview
26 ///
27 /// RadioHead consists of 2 main sets of classes: Drivers and Managers.
28 ///
29 /// - Drivers provide low level access to a range of different packet radios and other packetized message transports.
30 /// - Managers provide high level message sending and receiving facilities for a range of different requirements.
31 ///
32 /// Every RadioHead program will have an instance of a Driver to provide access to the data radio or transport,
33 /// and a Manager that uses that driver to send and receive messages for the application. The programmer is required
34 /// to instantiate a Driver and a Manager, and to initialise the Manager. Thereafter the facilities of the Manager
35 /// can be used to send and receive messages.
36 ///
37 /// It is also possible to use a Driver on its own, without a Manager, although this only allows unaddressed,
38 /// unreliable transport via the Driver's facilities.
39 ///
40 /// In some specialised use cases, it is possible to instantiate more than one Driver and more than one Manager.
41 ///
42 /// A range of different common embedded microprocessor platforms are supported, allowing your project to run
43 /// on your choice of processor.
44 ///
45 /// Example programs are included to show the main modes of use.
46 ///
47 /// \par Drivers
48 ///
49 /// The following Drivers are provided:
50 ///
51 /// - RH_RF22
52 /// Works with Hope-RF
53 /// RF22B and RF23B based transceivers, and compatible chips and modules,
54 /// including the RFM22B transceiver module such as
55 /// this bare module: http://www.sparkfun.com/products/10153
56 /// and this shield: http://www.sparkfun.com/products/11018
57 /// and this board: http://www.anarduino.com/miniwireless
58 /// and RF23BP modules such as: http://www.anarduino.com/details.jsp?pid=130
59 /// Supports GFSK, FSK and OOK. Access to other chip
60 /// features such as on-chip temperature measurement, analog-digital
61 /// converter, transmitter power control etc is also provided.
62 ///
63 /// - RH_RF24
64 /// Works with Silicon Labs Si4460/4461/4463/4464 family of transceivers chip, and the equivalent
65 /// HopeRF RF24/26/27 family of chips and the HopeRF RFM24W/26W/27W modules.
66 /// Supports GFSK, FSK and OOK. Access to other chip
67 /// features such as on-chip temperature measurement, analog-digital
68 /// converter, transmitter power control etc is also provided.
69 ///
70 /// - RH_RF69
71 /// Works with Hope-RF
72 /// RF69B based radio modules, such as the RFM69 module, (as used on the excellent Moteino and Moteino-USB
73 /// boards from LowPowerLab http://lowpowerlab.com/moteino/ )
74 /// and compatible chips and modules such as RFM69W, RFM69HW, RFM69CW, RFM69HCW (Semtech SX1231, SX1231H).
75 /// Also works with Anarduino MiniWireless -CW and -HW boards http://www.anarduino.com/miniwireless/ including
76 /// the marvellous high powered MinWireless-HW (with 20dBm output for excellent range).
77 /// Supports GFSK, FSK.
78 ///
79 /// - RH_NRF24
80 /// Works with Nordic nRF24 based 2.4GHz radio modules, such as nRF24L01 and others.
81 /// Also works with Hope-RF RFM73
82 /// and compatible devices (such as BK2423). nRF24L01 and RFM73 can interoperate
83 /// with each other.
84 ///
85 /// - RH_NRF905
86 /// Works with Nordic nRF905 based 433/868/915 MHz radio modules.
87 ///
88 /// - RH_NRF51
89 /// Works with Nordic nRF51 compatible 2.4 GHz SoC/devices such as the nRF51822.
90 /// Also works with Sparkfun nRF52832 breakout board, with Arduino 1.6.13 and
91 /// Sparkfun nRF52 boards manager 0.2.3
92 ///
93 /// - RH_RF95
94 /// Works with Semtech SX1276/77/78/79, Modtronix inAir4 and inAir9,
95 /// and HopeRF RFM95/96/97/98 and other similar LoRa capable radios.
96 /// Supports Long Range (LoRa) with spread spectrum frequency hopping, large payloads etc.
97 /// FSK/GFSK/OOK modes are not (yet) supported.
98 ///
99 /// - RH_MRF89
100 /// Works with Microchip MRF89XA and compatible transceivers.
101 /// and modules such as MRF89XAM9A.
102 ///
103 /// - RH_CC110
104 /// Works with Texas Instruments CC110L transceivers and compatible modules such as Anaren AIR BoosterPack 430BOOST-CC110L
105 ///
106 /// - RH_E32
107 /// Works with EBYTE E32-TTL-1W serial radio transceivers (and possibly other transceivers in the same family)
108 ///
109 /// - RH_ASK
110 /// Works with a range of inexpensive ASK (amplitude shift keying) RF transceivers such as RX-B1
111 /// (also known as ST-RX04-ASK) receiver; TX-C1 transmitter and DR3100 transceiver; FS1000A/XY-MK-5V transceiver;
112 /// HopeRF RFM83C / RFM85. Supports ASK (OOK).
113 ///
114 /// - RH_Serial
115 /// Works with RS232, RS422, RS485, RS488 and other point-to-point and multidropped serial connections,
116 /// or with TTL serial UARTs such as those on Arduino and many other processors,
117 /// or with data radios with a
118 /// serial port interface. RH_Serial provides packetization and error detection over any hardware or
119 /// virtual serial connection. Also builds and runs on Linux and OSX.
120 ///
121 /// - RH_TCP
122 /// For use with simulated sketches compiled and running on Linux.
123 /// Works with tools/etherSimulator.pl to pass messages between simulated sketches, allowing
124 /// testing of Manager classes on Linux and without need for real radios or other transport hardware.
125 ///
126 /// - RHEncryptedDriver
127 /// Adds encryption and decryption to any RadioHead transport driver, using any encrpytion cipher
128 /// supported by ArduinoLibs Cryptogrphic Library http://rweather.github.io/arduinolibs/crypto.html
129 ///
130 /// Drivers can be used on their own to provide unaddressed, unreliable datagrams.
131 /// All drivers have the same identical API.
132 /// Or you can use any Driver with any of the Managers described below.
133 ///
134 /// We welcome contributions of well tested and well documented code to support other transports.
135 ///
136 /// \par Managers
137 ///
138 /// The following Mangers are provided:
139 ///
140 /// - RHDatagram
141 /// Addressed, unreliable variable length messages, with optional broadcast facilities.
142 ///
143 /// - RHReliableDatagram
144 /// Addressed, reliable, retransmitted, acknowledged variable length messages.
145 ///
146 /// - RHRouter
147 /// Multi-hop delivery from source node to destination node via 0 or more intermediate nodes, with manual routing.
148 ///
149 /// - RHMesh
150 /// Multi-hop delivery with automatic route discovery and rediscovery.
151 ///
152 /// Any Manager may be used with any Driver.
153 ///
154 /// \par Platforms
155 ///
156 /// A range of platforms is supported:
157 ///
158 /// - Arduino and the Arduino IDE (version 1.0 to 1.8.1 and later)
159 /// Including Diecimila, Uno, Mega, Leonardo, Yun, Due, Zero etc. http://arduino.cc/, Also similar boards such as
160 /// - Moteino http://lowpowerlab.com/moteino/
161 /// - Anarduino Mini http://www.anarduino.com/mini/
162 /// - RedBearLab Blend V1.0 http://redbearlab.com/blend/ (with Arduino 1.0.5 and RedBearLab Blend Add-On version 20140701)
163 /// - MoteinoMEGA https://lowpowerlab.com/shop/moteinomega
164 /// (with Arduino 1.0.5 and the MoteinoMEGA Arduino Core
165 /// https://github.com/LowPowerLab/Moteino/tree/master/MEGA/Core)
166 /// - ESP8266 on Arduino IDE and Boards Manager per https://github.com/esp8266/Arduino
167 /// Tested using Arduino 1.6.8 with esp8266 by ESP8266 Community version 2.1.0
168 /// Examples serial_reliable_datagram_* and ask_* are shown to work.
169 /// CAUTION: The GHz radio included in the ESP8266 is
170 /// not yet supported.
171 /// - Various Talk2 Whisper boards eg https://wisen.com.au/store/products/whisper-node-lora.
172 /// Use Arduino Board Manager to install the Talk2 code support.
173 /// - etc.
174 ///
175 /// - ChipKIT Core with Arduino IDE on any ChipKIT Core supported Digilent processor (tested on Uno32)
176 /// http://chipkit.net/wiki/index.php?title=ChipKIT_core
177 ///
178 /// - Maple and Flymaple boards with libmaple and the Maple-IDE development environment
179 /// http://leaflabs.com/devices/maple/ and http://www.open-drone.org/flymaple
180 ///
181 /// - Teensy including Teensy 3.1 and earlier built using Arduino IDE 1.0.5 to 1.6.4 and later with
182 /// teensyduino addon 1.18 to 1.23 and later.
183 /// http://www.pjrc.com/teensy
184 ///
185 /// - Particle Photon https://store.particle.io/collections/photon and ARM3 based CPU with built-in
186 /// Wi-Fi transceiver and extensive IoT software suport. RadioHead does not support the built-in transceiver
187 /// but can be used to control other SPI based radios, Serial ports etc.
188 /// See below for details on how to build RadioHead for Photon
189 ///
190 /// - ATtiny built using Arduino IDE 1.0.5 with the arduino-tiny support from https://code.google.com/p/arduino-tiny/
191 /// and Digispark built with Arduino 1.6.5.
192 /// (Caution: these are very small processors and not all RadioHead features may be available, depending on memory requirements)
193 ///
194 /// - nRF51 compatible Arm chips such as nRF51822 with Arduino 1.6.4 and later using the procedures
195 /// in http://redbearlab.com/getting-started-nrf51822/
196 ///
197 /// - nRF52 compatible Arm chips such as as Adafruit BLE Feather board
198 /// https://www.adafruit.com/product/3406
199 ///
200 /// - Adafruit Feather. These are excellent boards that are available with a variety of radios. We tested with the
201 /// Feather 32u4 with RFM69HCW radio, with Arduino IDE 1.6.8 and the Adafruit AVR Boards board manager version 1.6.10.
202 /// https://www.adafruit.com/products/3076
203 ///
204 /// - ESP32 built using Arduino IDE 1.8.1 or later using the ESP32 toolchain installed per
205 /// https://diyprojects.io/programming-esp32-board-arduino-ide-macos-windows-linux-arm-raspberrypi-orangepi/
206 /// The internal 2.4GHz radio is not yet supported. Tested with RFM22 using SPI interfcace
207 ///
208 /// - Raspberry Pi
209 /// Uses BCM2835 library for GPIO http://www.airspayce.com/mikem/bcm2835/
210 /// Currently works only with RH_NRF24 driver or other drivers that do not require interrupt support.
211 /// Contributed by Mike Poublon.
212 ///
213 /// - Linux and OSX
214 /// Using the RHutil/HardwareSerial class, the RH_Serial driver and any manager will
215 /// build and run on Linux and OSX. These can be used to build programs that talk securely and reliably to
216 /// Arduino and other processors or to other Linux or OSX hosts on a reliable, error detected datagram
217 /// protocol over a serial line.
218 ///
219 /// Other platforms are partially supported, such as Generic AVR 8 bit processors, MSP430.
220 /// We welcome contributions that will expand the range of supported platforms.
221 ///
222 /// RadioHead is available (through the efforts of others)
223 /// for PlatformIO. PlatformIO is a cross-platform code builder and the missing library manager.
224 /// http://platformio.org/#!/lib/show/124/RadioHead
225 ///
226 /// \par History
227 ///
228 /// RadioHead was created in April 2014, substantially based on code from some of our other earlier Radio libraries:
229 ///
230 /// - RHMesh, RHRouter, RHReliableDatagram and RHDatagram are derived from the RF22 library version 1.39.
231 /// - RH_RF22 is derived from the RF22 library version 1.39.
232 /// - RH_RF69 is derived from the RF69 library version 1.2.
233 /// - RH_ASK is based on the VirtualWire library version 1.26, after significant conversion to C++.
234 /// - RH_Serial was new.
235 /// - RH_NRF24 is based on the NRF24 library version 1.12, with some significant changes.
236 ///
237 /// During this combination and redevelopment, we have tried to retain all the processor dependencies and support from
238 /// the libraries that were contributed by other people. However not all platforms can be tested by us, so if you
239 /// find that support from some platform has not been successfully migrated, please feel free to fix it and send us a
240 /// patch.
241 ///
242 /// Users of RHMesh, RHRouter, RHReliableDatagram and RHDatagram in the previous RF22 library will find that their
243 /// existing code will run mostly without modification. See the RH_RF22 documentation for more details.
244 ///
245 /// \par Installation
246 ///
247 /// Install in the usual way: unzip the distribution zip file to the libraries
248 /// sub-folder of your sketchbook.
249 /// The example sketches will be visible in in your Arduino, mpide, maple-ide or whatever.
250 /// http://arduino.cc/en/Guide/Libraries
251 ///
252 /// \par Building for Particle Photon
253 ///
254 /// The Photon is not supported by the Arduino IDE, so it takes a little effort to set up a build environment.
255 /// Heres what we did to enable building of RadioHead example sketches on Linux,
256 /// but there are other ways to skin this cat.
257 /// Basic reference for getting stated is: http://particle-firmware.readthedocs.org/en/develop/build/
258 /// - Download the ARM gcc cross compiler binaries and unpack it in a suitable place:
259 /// \code
260 /// cd /tmp
261 /// wget https://launchpad.net/gcc-arm-embedded/5.0/5-2015-q4-major/+download/gcc-arm-none-eabi-5_2-2015q4-20151219-linux.tar.bz2
262 /// tar xvf gcc-arm-none-eabi-5_2-2015q4-20151219-linux.tar.bz2
263 /// \endcode
264 /// - If dfu-util and friends not installed on your platform, download dfu-util and friends to somewhere in your path
265 /// \code
266 /// cd ~/bin
267 /// wget http://dfu-util.sourceforge.net/releases/dfu-util-0.8-binaries/linux-i386/dfu-util
268 /// wget http://dfu-util.sourceforge.net/releases/dfu-util-0.8-binaries/linux-i386/dfu-suffix
269 /// wget http://dfu-util.sourceforge.net/releases/dfu-util-0.8-binaries/linux-i386/dfu-prefix
270 /// \endcode
271 /// - Download the Particle firmware (contains headers and libraries require to compile Photon sketches)
272 /// to a suitable place:
273 /// \code
274 /// cd /tmp
275 /// wget https://github.com/spark/firmware/archive/develop.zip
276 /// unzip develop.zip
277 /// \endcode
278 /// - Make a working area containing the RadioHead library source code and your RadioHead sketch. You must
279 /// rename the sketch from .pde or .ino to application.cpp
280 /// \code
281 /// cd /tmp
282 /// mkdir RadioHead
283 /// cd RadioHead
284 /// cp /usr/local/projects/arduino/libraries/RadioHead/*.h .
285 /// cp /usr/local/projects/arduino/libraries/RadioHead/*.cpp .
286 /// cp /usr/local/projects/arduino/libraries/RadioHead/examples/cc110/cc110_client/cc110_client.pde application.cpp
287 /// \endcode
288 /// - Edit application.cpp and comment out any \#include <SPI.h> so it looks like:
289 /// \code
290 /// // #include <SPI.h>
291 /// \endcode
292 /// - Connect your Photon by USB. Put it in DFU mode as descibed in Photon documentation. Light should be flashing yellow
293 /// - Compile the RadioHead sketch and install it as the user program (this does not update the rest of the
294 /// Photon firmware, just the user part:
295 /// \code
296 /// cd /tmp/firmware-develop/main
297 /// PATH=$PATH:/tmp/gcc-arm-none-eabi-5_2-2015q4/bin make APPDIR=/tmp/RadioHead all PLATFORM=photon program-dfu
298 /// \endcode
299 /// - You should see RadioHead compile without errors and download the finished sketch into the Photon.
300 ///
301 /// \par Compatible Hardware Suppliers
302 ///
303 /// We have had good experiences with the following suppliers of RadioHead compatible hardware:
304 ///
305 /// - LittleBird http://littlebirdelectronics.com.au in Australia for all manner of Arduinos and radios.
306 /// - LowPowerLab http://lowpowerlab.com/moteino in USA for the excellent Moteino and Moteino-USB
307 /// boards which include Hope-RF RF69B radios on-board.
308 /// - Anarduino and HopeRF USA (http://www.hoperfusa.com and http://www.anarduino.com) who have a wide range
309 /// of HopeRF radios and Arduino integrated modules.
310 /// - SparkFun https://www.sparkfun.com/ in USA who design and sell a wide range of Arduinos and radio modules.
311 /// - Wisen http://wisen.com.au who design and sell a wide range of integrated radio/processor modules including the
312 /// excellent Talk2 range.
313 ///
314 /// \par Coding Style
315 ///
316 /// RadioHead is designed so it can run on small processors with very
317 /// limited resources and strict timing contraints. As a result, we
318 /// tend only to use the simplest and least demanding (in terms of memory and CPU) C++
319 /// facilities. In particular we avoid as much as possible dynamic
320 /// memory allocation, and the use of complex objects like C++
321 /// strings, IO and buffers. We are happy with this, but we are aware
322 /// that some people may think we are leaving useful tools on the
323 /// table. You should not use this code as an example of how to do
324 /// generalised C++ programming on well resourced processors.
325 ///
326 /// \par Donations
327 ///
328 /// This library is offered under a free GPL license for those who want to use it that way.
329 /// We try hard to keep it up to date, fix bugs
330 /// and to provide free support. If this library has helped you save time or money, please consider donating at
331 /// http://www.airspayce.com or here:
332 ///
333 /// \htmlonly <form action="https://www.paypal.com/cgi-bin/webscr" method="post"><input type="hidden" name="cmd" value="_donations" /> <input type="hidden" name="business" value="mikem@airspayce.com" /> <input type="hidden" name="lc" value="AU" /> <input type="hidden" name="item_name" value="Airspayce" /> <input type="hidden" name="item_number" value="RadioHead" /> <input type="hidden" name="currency_code" value="USD" /> <input type="hidden" name="bn" value="PP-DonationsBF:btn_donateCC_LG.gif:NonHosted" /> <input type="image" alt="PayPal — The safer, easier way to pay online." name="submit" src="https://www.paypalobjects.com/en_AU/i/btn/btn_donateCC_LG.gif" /> <img alt="" src="https://www.paypalobjects.com/en_AU/i/scr/pixel.gif" width="1" height="1" border="0" /></form> \endhtmlonly
334 ///
335 /// \subpage packingdata "Passing Sensor Data Between RadioHead nodes"
336 ///
337 /// \par Trademarks
338 ///
339 /// RadioHead is a trademark of AirSpayce Pty Ltd. The RadioHead mark was first used on April 12 2014 for
340 /// international trade, and is used only in relation to data communications hardware and software and related services.
341 /// It is not to be confused with any other similar marks covering other goods and services.
342 ///
343 /// \par Copyright
344 ///
345 /// This software is Copyright (C) 2011-2016 Mike McCauley. Use is subject to license
346 /// conditions. The main licensing options available are GPL V2 or Commercial:
347 ///
348 /// \par Open Source Licensing GPL V2
349 ///
350 /// This is the appropriate option if you want to share the source code of your
351 /// application with everyone you distribute it to, and you also want to give them
352 /// the right to share who uses it. If you wish to use this software under Open
353 /// Source Licensing, you must contribute all your source code to the open source
354 /// community in accordance with the GPL Version 2 when your application is
355 /// distributed. See https://www.gnu.org/licenses/gpl-2.0.html
356 ///
357 /// \par Commercial Licensing
358 ///
359 /// This is the appropriate option if you are creating proprietary applications
360 /// and you are not prepared to distribute and share the source code of your
361 /// application. Purchase commercial licenses at http://airspayce.binpress.com
362 ///
363 /// \par Revision History
364 /// \version 1.1 2014-04-14<br>
365 /// Initial public release
366 /// \version 1.2 2014-04-23<br>
367 /// Fixed various typos. <br>
368 /// Added links to compatible Anarduino products.<br>
369 /// Added RHNRFSPIDriver, RH_NRF24 classes to support Nordic NRF24 based radios.
370 /// \version 1.3 2014-04-28<br>
371 /// Various documentation fixups.<br>
372 /// RHDatagram::setThisAddress() did not set the local copy of thisAddress. Reported by Steve Childress.<br>
373 /// Fixed a problem on Teensy with RF22 and RF69, where the interrupt pin needs to be set for input, <br>
374 /// else pin interrupt doesn't work properly. Reported by Steve Childress and patched by
375 /// Adrien van den Bossche. Thanks.<br>
376 /// Fixed a problem that prevented RF22 honouring setPromiscuous(true). Reported by Steve Childress.<br>
377 /// Updated documentation to clarify some issues to do with maximum message lengths
378 /// reported by Steve Childress.<br>
379 /// Added support for yield() on systems that support it (currently Arduino 1.5.5 and later)
380 /// so that spin-loops can suport multitasking. Suggested by Steve Childress.<br>
381 /// Added RH_RF22::setGpioReversed() so the reversal it can be configured at run-time after
382 /// radio initialisation. It must now be called _after_ init(). Suggested by Steve Childress.<br>
383 /// \version 1.4 2014-04-29<br>
384 /// Fixed further problems with Teensy compatibility for RH_RF22. Tested on Teensy 3.1.
385 /// The example/rf22_* examples now run out of the box with the wiring connections as documented for Teensy
386 /// in RH_RF22.<br>
387 /// Added YIELDs to spin-loops in RHRouter, RHMesh and RHReliableDatagram, RH_NRF24.<br>
388 /// Tested RH_Serial examples with Teensy 3.1: they now run out of the box.<br>
389 /// Tested RH_ASK examples with Teensy 3.1: they now run out of the box.<br>
390 /// Reduced default SPI speed for NRF24 from 8MHz to 1MHz on Teensy, to improve reliability when
391 /// poor wiring is in use.<br>
392 /// on some devices such as Teensy.<br>
393 /// Tested RH_NRF24 examples with Teensy 3.1: they now run out of the box.<br>
394 /// \version 1.5 2014-04-29<br>
395 /// Added support for Nordic Semiconductor nRF905 transceiver with RH_NRF905 driver. Also
396 /// added examples for nRF905 and tested on Teensy 3.1
397 /// \version 1.6 2014-04-30<br>
398 /// NRF905 examples were missing
399 /// \version 1.7 2014-05-03<br>
400 /// Added support for Arduino Due. Tested with RH_NRF905, RH_Serial, RH_ASK.
401 /// IMPORTANT CHANGE to interrupt pins on Arduino with RH_RF22 and RH_RF69 constructors:
402 /// previously, you had to specify the interrupt _number_ not the interrupt _pin_. Arduinos and Uno32
403 /// are now consistent with all other platforms: you must specify the interrupt pin number. Default
404 /// changed to pin 2 (a common choice with RF22 shields).
405 /// Removed examples/maple/maple_rf22_reliable_datagram_client and
406 /// examples/maple/maple_rf22_reliable_datagram_client since the rf22 examples now work out
407 /// of the box with Flymaple.
408 /// Removed examples/uno32/uno32_rf22_reliable_datagram_client and
409 /// examples/uno32/uno32_rf22_reliable_datagram_client since the rf22 examples now work out
410 /// of the box with ChipKit Uno32.
411 /// \version 1.8 2014-05-08 <br>
412 /// Added support for YIELD in Teensy 2 and 3, suggested by Steve Childress.<br>
413 /// Documentation updates. Clarify use of headers and Flags<br>
414 /// Fixed misalignment in RH_RF69 between ModemConfigChoice definitions and the implemented choices
415 /// which meant you didnt get the choice you thought and GFSK_Rb55555Fd50 hung the transmitter.<br>
416 /// Preliminary work on Linux simulator.
417 /// \version 1.9 2014-05-14 <br>
418 /// Added support for using Timer 2 instead of Timer 1 on Arduino in RH_ASK when
419 /// RH_ASK_ARDUINO_USE_TIMER2 is defined. With the kind assistance of
420 /// Luc Small. Thanks!<br>
421 /// Updated comments in RHReliableDatagram concerning servers, retries, timeouts and delays.
422 /// Fixed an error in RHReliableDatagram where recvfrom return value was not checked.
423 /// Reported by Steve Childress.<br>
424 /// Added Linux simulator support so simple RadioHead sketches can be compiled and run on Linux.<br>
425 /// Added RH_TCP driver to permit message passing between simulated sketches on Linux.<br>
426 /// Added example simulator sketches.<br>
427 /// Added tools/etherSimulator.pl, a simulator of the 'Luminiferous Ether' that passes
428 /// messages between simulated sketches and can simulate random message loss etc.<br>
429 /// Fixed a number of typos and improved some documentation.<br>
430 /// \version 1.10 2014-05-15 <br>
431 /// Added support for RFM73 modules to RH_NRF24. These 2 radios are very similar, and can interoperate
432 /// with each other. Added new RH_NRF24::TransmitPower enums for the RFM73, which has a different
433 /// range of available powers<br>
434 /// reduced the default SPI bus speed for RH_NRF24 to 1MHz, since so many modules and CPU have problems
435 /// with 8MHz.<br>
436 /// \version 1.11 2014-05-18<br>
437 /// Testing RH_RF22 with RFM23BP and 3.3V Teensy 3.1 and 5V Arduinos.
438 /// Updated documentation with respect to GPIO and antenna
439 /// control pins for RFM23. Updated documentation with respect to transmitter power control for RFM23<br>
440 /// Fixed a problem with RH_RF22 driver, where GPIO TX and RX pins were not configured during
441 /// initialisation, causing poor transmit power and sensitivity on those RF22/RF23 devices where GPIO controls
442 /// the antenna selection pins.
443 /// \version 1.12 2014-05-20<br>
444 /// Testing with RF69HW and the RH_RF69 driver. Works well with the Anarduino MiniWireless -CW and -HW
445 /// boards http://www.anarduino.com/miniwireless/ including
446 /// the marvellous high powered MinWireless-HW (with 20dBm output for excellent range).<br>
447 /// Clarified documentation of RH_RF69::setTxPower values for different models of RF69.<br>
448 /// Added RHReliableDatagram::resetRetransmissions().<br>
449 /// Retransmission count precision increased to uin32_t.<br>
450 /// Added data about actual power measurements from RFM22 module.<br>
451 /// \version 1.13 2014-05-23<br>
452 /// setHeaderFlags(flags) changed to setHeaderFlags(set, clear), enabling any flags to be
453 /// individually set and cleared by either RadioHead or application code. Requested by Steve Childress.<br>
454 /// Fixed power output setting for boost power on RF69HW for 18, 19 and 20dBm.<br>
455 /// Added data about actual power measurements from RFM69W and RFM69HW modules.<br>
456 /// \version 1.14 2014-05-26<br>
457 /// RH_RF69::init() now always sets the PA boost back to the default settings, else can get invalid
458 /// PA power modes after uploading new sketches without a power cycle. Reported by Bryan.<br>
459 /// Added new macros RH_VERSION_MAJOR RH_VERSION_MINOR, with automatic maintenance in Makefile.<br>
460 /// Improvements to RH_TCP: constructor now honours the server argument in the form "servername:port".<br>
461 /// Added YIELD to RHReliableDatagram::recvfromAckTimeout. Requested by Steve Childress.<br>
462 /// Fixed a problem with RH_RF22 reliable datagram acknowledgements that was introduced in version 1.13.
463 /// Reported by Steve Childress.<br>
464 /// \version 1.15 2014-05-27<br>
465 /// Fixed a problem with the RadioHead .zip link.
466 /// \version 1.16 2014-05-30 <br>
467 /// Fixed RH_RF22 so that lastRssi() returns the signal strength in dBm. Suggested by Steve Childress.<br>
468 /// Added support for getLastPreambleTime() to RH_RF69. Requested by Steve Childress.<br>
469 /// RH_NRF24::init() now checks if there is a device connected and responding, else init() will fail.
470 /// Suggested by Steve Brown.<br>
471 /// RHSoftwareSPI now initialises default values for SPI pins MOSI = 12, MISO = 11 and SCK = 13.<br>
472 /// Fixed some problems that prevented RH_NRF24 working with mixed software and hardware SPI
473 /// on different devices: a race condition
474 /// due to slow SPI transfers and fast acknowledgement.<br>
475 /// \version 1.17 2014-06-02 <br>
476 /// Fixed a debug typo in RHReliableDatagram that was introduced in 1.16.<br>
477 /// RH_NRF24 now sets default power, data rate and channel in init(), in case another
478 /// app has previously set different values without powerdown.<br>
479 /// Caution: there are still problems with RH_NRF24 and Software SPI. Do not use.<br>
480 /// \version 1.18 2014-06-02<br>
481 /// Improvements to performance of RH_NRF24 statusRead, allowing RH_NRF24 and Software SPI
482 /// to operate on slow devices like Arduino Uno.<br>
483 /// \version 1.19 2014-06-19<br>
484 /// Added examples ask_transmitter.pde and ask_receiver.pde.<br>
485 /// Fixed an error in the RH_RF22 doc for connection of Teensy to RF22.<br>
486 /// Improved documentation of start symbol bit patterns in RH_ASK.cpp
487 /// \version 1.20 2014-06-24<br>
488 /// Fixed a problem with compiling on platforms such as ATTiny where SS is not defined.<br>
489 /// Added YIELD to RHMesh::recvfromAckTimeout().<br>
490 /// \version 1.21 2014-06-24<br>
491 /// Fixed an issue in RH_Serial where characters might be lost with back-to-back frames.
492 /// Suggested by Steve Childress.<br>
493 /// Brought previous RHutil/crc16.h code into mainline RHCRC.cpp to prevent name collisions
494 /// with other similarly named code in other libraries. Suggested by Steve Childress.<br>
495 /// Fix SPI bus speed errors on 8MHz Arduinos.
496 /// \version 1.22 2014-07-01<br>
497 /// Update RH_ASK documentation for common wiring connections.<br>
498 /// Testing RH_ASK with HopeRF RFM83C/RFM85 courtesy Anarduino http://www.anarduino.com/<br>
499 /// Testing RH_NRF24 with Itead Studio IBoard Pro http://imall.iteadstudio.com/iboard-pro.html
500 /// using both hardware SPI on the ITDB02 Parallel LCD Module Interface pins and software SPI
501 /// on the nRF24L01+ Module Interface pins. Documented wiring required.<br>
502 /// Added support for AVR 1284 and 1284p, contributed by Peter Scargill.
503 /// Added support for Semtech SX1276/77/78 and HopeRF RFM95/96/97/98 and other similar LoRa capable radios
504 /// in LoRa mode only. Tested with the excellent MiniWirelessLoRa from
505 /// Anarduino http://www.anarduino.com/miniwireless<br>
506 /// \version 1.23 2014-07-03<br>
507 /// Changed the default modulation for RH_RF69 to GFSK_Rb250Fd250, since the previous default
508 /// was not very reliable.<br>
509 /// Documented RH_RF95 range tests.<br>
510 /// Improvements to RH_RF22 RSSI readings so that lastRssi correctly returns the last message in dBm.<br>
511 /// \version 1.24 2014-07-18
512 /// Added support for building RadioHead for STM32F4 Discovery boards, using the native STM Firmware libraries,
513 /// in order to support Codec2WalkieTalkie (http://www.airspayce.com/mikem/Codec2WalkieTalkie)
514 /// and other projects. See STM32ArduinoCompat.<br>
515 /// Default modulation for RH_RF95 was incorrectly set to a very slow Bw125Cr48Sf4096
516 /// \version 1.25 2014-07-25
517 /// The available() function will longer terminate any current transmission, and force receive mode.
518 /// Now, if there is no unprocessed incoming message and an outgoing message is currently being transmitted,
519 /// available() will return false.<br>
520 /// RHRouter::sendtoWait(uint8_t*, uint8_t, uint8_t, uint8_t) renamed to sendtoFromSourceWait due to conflicts
521 /// with new sendtoWait() with optional flags.<br>
522 /// RHMEsh and RHRouter already supported end-to-end application layer flags, but RHMesh::sendtoWait()
523 /// and RHRouter::sendToWait have now been extended to expose a way to send optional application layer flags.
524 /// \version 1.26 2014-08-12
525 /// Fixed a Teensy 2.0 compile problem due yield() not available on Teensy < 3.0. <br>
526 /// Adjusted the algorithm of RH_RF69::temperatureRead() to more closely reflect reality.<br>
527 /// Added functions to RHGenericDriver to get driver packet statistics: rxBad(), rxGood(), txGood().<br>
528 /// Added RH_RF69::printRegisters().<br>
529 /// RH_RF95::printRegisters() was incorrectly printing the register index instead of the address.
530 /// Reported by Phang Moh Lim.<br>
531 /// RH_RF95, added definitions for some more registers that are usable in LoRa mode.<br>
532 /// RH_RF95::setTxPower now uses RH_RF95_PA_DAC_ENABLE to achieve 21, 22 and 23dBm.<br>
533 /// RH_RF95, updated power output measurements.<br>
534 /// Testing RH_RF69 on Teensy 3.1 with RF69 on PJRC breakout board. OK.<br>
535 /// Improvements so RadioHead will build under Arduino where SPI is not supported, such as
536 /// ATTiny.<br>
537 /// Improvements so RadioHead will build for ATTiny using Arduino IDE and tinycore arduino-tiny-0100-0018.zip.<br>
538 /// Testing RH_ASK on ATTiny85. Reduced RAM footprint.
539 /// Added helpful documentation. Caution: RAM memory is *very* tight on this platform.<br>
540 /// RH_RF22 and RH_RF69, added setIdleMode() function to allow the idle mode radio operating state
541 /// to be controlled for lower idle power consumption at the expense of slower transitions to TX and RX.<br>
542 /// \version 1.27 2014-08-13
543 /// All RH_RF69 modulation schemes now have data whitening enabled by default.<br>
544 /// Tested and added a number of OOK modulation schemes to RH_RF69 Modem config table.<br>
545 /// Minor improvements to a number of the faster RH_RF69 modulation schemes, but some slower ones
546 /// are still not working correctly.<br>
547 /// \version 1.28 2014-08-20
548 /// Added new RH_RF24 driver to support Si446x, RF24/26/26, RFM24/26/27 family of transceivers.
549 /// Tested with the excellent
550 /// Anarduino Mini and RFM24W and RFM26W with the generous assistance of the good people at
551 /// Anarduino http://www.anarduino.com.
552 /// \version 1.29 2014-08-21
553 /// Fixed a compile error in RH_RF24 introduced at the last minute in hte previous release.<br>
554 /// Improvements to RH_RF69 modulation schemes: now include the AFCBW in teh ModemConfig.<br>
555 /// ModemConfig RH_RF69::FSK_Rb2Fd5 and RH_RF69::GFSK_Rb2Fd5 are now working.<br>
556 /// \version 1.30 2014-08-25
557 /// Fixed some compile problems with ATtiny84 on Arduino 1.5.5 reported by Glen Cook.<br>
558 /// \version 1.31 2014-08-27
559 /// Changed RH_RF69 FSK and GFSK modulations from Rb2_4Fd2_4 to Rb2_4Fd4_8 and FSK_Rb4_8Fd4_8 to FSK_Rb4_8Fd9_6
560 /// since the previous ones were unreliable (they had modulation indexes of 1).<br>
561 /// \version 1.32 2014-08-28
562 /// Testing with RedBearLab Blend board http://redbearlab.com/blend/. OK.<br>
563 /// Changed more RH_RF69 FSK and GFSK slowish modulations to have modulation index of 2 instead of 1.
564 /// This required chnaging the symbolic names.<br>
565 /// \version 1.33 2014-09-01
566 /// Added support for sleep mode in RHGeneric driver, with new mode
567 /// RHModeSleep and new virtual function sleep().<br>
568 /// Added support for sleep to RH_RF69, RH_RF22, RH_NRF24, RH_RF24, RH_RF95 drivers.<br>
569 /// \version 1.34 2014-09-19
570 /// Fixed compile errors in example rf22_router_test.<br>
571 /// Fixed a problem with RH_NRF24::setNetworkAddress, also improvements to RH_NRF24 register printing.
572 /// Patched by Yveaux.<br>
573 /// Improvements to RH_NRF24 initialisation for version 2.0 silicon.<br>
574 /// Fixed problem with ambigiguous print call in RH_RFM69 when compiling for Codec2.<br>
575 /// Fixed a problem with RH_NRF24 on RFM73 where the LNA gain was not set properly, reducing the sensitivity
576 /// of the receiver.
577 /// \version 1.35 2014-09-19
578 /// Fixed a problem with interrupt setup on RH_RF95 with Teensy3.1. Reported by AD.<br>
579 /// \version 1.36 2014-09-22
580 /// Improvements to interrupt pin assignments for __AVR_ATmega1284__ and__AVR_ATmega1284P__, provided by
581 /// Peter Scargill.<br>
582 /// Work around a bug in Arduino 1.0.6 where digitalPinToInterrupt is defined but NOT_AN_INTERRUPT is not.<br>
583 /// \version 1.37 2014-10-19
584 /// Updated doc for connecting RH_NRF24 to Arduino Mega.<br>
585 /// Changes to RHGenericDriver::setHeaderFlags(), so that the default for the clear argument
586 /// is now RH_FLAGS_APPLICATION_SPECIFIC, which is less surprising to users.
587 /// Testing with the excellent MoteinoMEGA from LowPowerLab
588 /// https://lowpowerlab.com/shop/moteinomega with on-board RFM69W.
589 /// \version 1.38 2014-12-29
590 /// Fixed compile warning on some platforms where RH_RF24::send and RH_RF24::writeTxFifo
591 /// did not return a value.<br>
592 /// Fixed some more compiler warnings in RH_RF24 on some platforms.<br>
593 /// Refactored printRegisters for some radios. Printing to Serial
594 /// is now controlled by the definition of RH_HAVE_SERIAL.<br>
595 /// Added partial support for ARM M4 w/CMSIS with STM's Hardware Abstraction lib for
596 /// Steve Childress.<br>
597 /// \version 1.39 2014-12-30
598 /// Fix some compiler warnings under IAR.<br>
599 /// RH_HAVE_SERIAL and Serial.print calls removed for ATTiny platforms.<br>
600 /// \version 1.40 2015-03-09
601 /// Added notice about availability on PlatformIO, thanks to Ivan Kravets.<br>
602 /// Fixed a problem with RH_NRF24 where short packet lengths would occasionally not be trasmitted
603 /// due to a race condition with RH_NRF24_TX_DS. Reported by Mark Fox.<br>
604 /// \version 1.41 2015-03-29
605 /// RH_RF22, RH_RF24, RH_RF69 and RH_RF95 improved to allow driver.init() to be called multiple
606 /// times without reallocating a new interrupt, allowing the driver to be reinitialised
607 /// after sleeping or powering down.
608 /// \version 1.42 2015-05-17
609 /// Added support for RH_NRF24 driver on Raspberry Pi, using BCM2835
610 /// library for GPIO pin IO. Contributed by Mike Poublon.<br>
611 /// Tested RH_NRF24 module with NRF24L01+PA+LNA SMA Antenna Wireless Transceiver modules
612 /// similar to: http://www.elecfreaks.com/wiki/index.php?title=2.4G_Wireless_nRF24L01p_with_PA_and_LNA
613 /// works with no software changes. Measured max power output 18dBm.<br>
614 /// \version 1.43 2015-08-02
615 /// Added RH_NRF51 driver to support Nordic nRF51 family processor with 2.4GHz radio such
616 /// as nRF51822, to be built on Arduino 1.6.4 and later. Tested with RedBearLabs nRF51822 board
617 /// and BLE Nano kit<br>
618 /// \version 1.44 2015-08-08
619 /// Fixed errors with compiling on some platforms without serial, such as ATTiny.
620 /// Reported by Friedrich Müller.<br>
621 /// \version 1.45 2015-08-13
622 /// Added support for using RH_Serial on Linux and OSX (new class RHutil/HardwareSerial
623 /// encapsulates serial ports on those platforms). Example examples/serial upgraded
624 /// to build and run on Linux and OSX using the tools/simBuild builder.
625 /// RHMesh, RHRouter and RHReliableDatagram updated so they can use RH_Serial without
626 /// polling loops on Linux and OSX for CPU efficiency.<br>
627 /// \version 1.46 2015-08-14
628 /// Amplified some doc concerning Linux and OSX RH_Serial. Added support for 230400
629 /// baud rate in HardwareSerial.<br>
630 /// Added sample sketches nrf51_audio_tx and nrf51_audio_rx which show how to
631 /// build an audio TX/RX pair with RedBear nRF51822 boards and a SparkFun MCP4725 DAC board.
632 /// Uses the built-in ADC of the nRF51822 to sample audio at 5kHz and transmit packets
633 /// to the receiver which plays them via the DAC.<br>
634 /// \version 1.47 2015-09-18
635 /// Removed top level Makefile from distribution: its only used by the developer and
636 /// its presence confuses some people.<br>
637 /// Fixed a problem with RHReliableDatagram with some versions of Raspberry Pi random() that causes
638 /// problems: random(min, max) sometimes exceeds its max limit.
639 /// \version 1.48 2015-09-30
640 /// Added support for Arduino Zero. Tested on Arduino Zero Pro.
641 /// \version 1.49 2015-10-01
642 /// Fixed problems that prevented interrupts working correctly on Arduino Zero and Due.
643 /// Builds and runs with 1.6.5 (with 'Arduino SAMD Boards' for Zero version 1.6.1) from arduino.cc.
644 /// Arduino version 1.7.7 from arduino.org is not currently supported.
645 /// \version 1.50 2015-10-25
646 /// Verified correct building and operation with Arduino 1.7.7 from arduino.org.
647 /// Caution: You must burn the bootloader from 1.7.7 to the Arduino Zero before it will
648 /// work with Arduino 1.7.7 from arduino.org. Conversely, you must burn the bootloader from 1.6.5
649 /// to the Arduino Zero before it will
650 /// work with Arduino 1.6.5 from arduino.cc. Sigh.
651 /// Fixed a problem with RH_NRF905 that prevented the power and frequency ranges being set
652 /// properly. Reported by Alan Webber.
653 /// \version 1.51 2015-12-11
654 /// Changes to RH_RF6::setTxPower() to be compatible with SX1276/77/78/79 modules that
655 /// use RFO transmitter pins instead of PA_BOOST, such as the excellent
656 /// Modtronix inAir4 http://modtronix.com/inair4.html
657 /// and inAir9 modules http://modtronix.com/inair9.html. With the kind assistance of
658 /// David from Modtronix.
659 /// \version 1.52 2015-12-17
660 /// Added RH_MRF89 module to suport Microchip MRF89XA and compatible transceivers.
661 /// and modules.<br>
662 /// \version 1.53 2016-01-02
663 /// Added RH_CC110 module to support Texas Instruments CC110L and compatible transceivers and modules.<br>
664 /// \version 1.54 2016-01-29
665 /// Added support for ESP8266 processor on Arduino IDE. Examples serial_reliable_datagram_* are shown to work.
666 /// CAUTION: SPI not supported yet. Timers used by RH_ASK are not tested.
667 /// The GHz radio included in the ESP8266 is not yet supported.
668 /// \version 1.55 2016-02-12
669 /// Added macros for htons() and friends to RadioHead.h.
670 /// Added example sketch serial_gateway.pde. Acts as a transparent gateway between RH_RF22 and RH_Serial,
671 /// and with minor mods acts as a universal gateway between any 2 RadioHead driver networks.
672 /// Initial work on supporting STM32 F2 on Particle Photon: new platform type defined.
673 /// Fixed many warnings exposed by test building for Photon.
674 /// Particle Photon tested support for RH_Serial, RH_ASK, SPI, RH_CC110 etc.
675 /// Added notes on how to build RadioHead sketches for Photon.
676 /// \version 1.56 2016-02-18
677 /// Implemented timers for RH_ASK on ESP8266, added some doc on IO pin selection.
678 /// \version 1.57 2016-02-23
679 /// Fixed an issue reported by S3B, where RH_RF22 would sometimes not clear the rxbufvalid flag.
680 /// \version 1.58 2-16-04-04
681 /// Tested RH_RF69 with Arduino Due. OK. Updated doc.<br>
682 /// Added support for all ChipKIT Core supported boards
683 /// http://chipkit.net/wiki/index.php?title=ChipKIT_core
684 /// Tested on ChipKIT Uno32.<br>
685 /// Digilent Uno32 under the old MPIDE is no longer formally
686 /// supported but may continue to work for some time.<br>
687 /// \version 1.59 2016-04-12
688 /// Testing with the excellent Rocket Scream Mini Ultra Pro with the RFM95W and RFM69HCW modules from
689 /// http://www.rocketscream.com/blog/product/mini-ultra-pro-with-radio/ (915MHz versions). Updated
690 /// documentation with hints to suit. Caution: requires Arduino 1.6.8 and Arduino SAMD Boards 1.6.5.
691 /// See also http://www.rocketscream.com/blog/2016/03/10/radio-range-test-with-rfm69hcw/
692 /// for the vendors tests and range with the RFM69HCW version. They also have an RF95 version equipped with
693 /// TCXO temperature controllled oscillator for extra frequency stability and support of very slow and
694 /// long range protocols.
695 /// These boards are highly recommended. They also include battery charging support.
696 /// \version 1.60 2016-06-25
697 /// Tested with the excellent talk2 Whisper Node boards
698 /// (https://talk2.wisen.com.au/ and https://bitbucket.org/talk2/),
699 /// an Arduino Nano compatible board, which include an on-board RF69 radio, external antenna,
700 /// run on 2xAA batteries and support low power operations. RF69 examples work without modification.
701 /// Added support for ESP8266 SPI, provided by David Skinner.
702 /// \version 1.61 2016-07-07
703 /// Patch to RH_ASK.cpp for ESP8266, to prevent crashes in interrupt handlers. Patch from Alexander Mamchits.
704 /// \version 1.62 2016-08-17
705 /// Fixed a problem in RH_ASK where _rxInverted was not properly initialised. Reported by "gno.sun.sop".
706 /// Added support for waitCAD() and isChannelActive() and setCADTimeout() to RHGeneric.
707 /// Implementation of RH_RF95::isChannelActive() allows the RF95 module to support
708 /// Channel Activity Detection (CAD). Based on code contributed by Bent Guldbjerg Christensen.
709 /// Implmentations of isChannelActive() plus documentation for other radio modules wil be welcomed.
710 /// \version 1.63 2016-10-20
711 /// Testing with Adafruit Feather 32u4 with RFM69HCW. Updated documentation to reflect.<br>
712 /// \version 1.64 2016-12-10
713 /// RHReliableDatagram now initialises _seenids. Fix from Ben Lim.<br>
714 /// In RH_NRF51, added get_temperature().<br>
715 /// In RH_NRF51, added support for AES packet encryption, which required a slight change
716 /// to the on-air message format.<br>
717 /// \version 1.65 2017-01-11
718 /// Fixed a race condition with RH_NRF51 that prevented ACKs being reliably received.<br>
719 /// Removed code in RH_NRF51 that enabled the DC-DC converter. This seems not to be a necessary condition
720 /// for the radio to work and is now left to the application if that is required.<br>
721 /// Proven interoperation between nRF51822 and nRF52832.<br>
722 /// Modification and testing of RH_NRF51 so it works with nRF52 family processors,
723 /// such Sparkfun nRF52832 breakout board, with Arduino 1.6.13 and
724 /// Sparkfun nRF52 boards manager 0.2.3 using the procedures outlined in
725 /// https://learn.sparkfun.com/tutorials/nrf52832-breakout-board-hookup-guide<br>
726 /// Caution, the Sparkfun development system for Arduino is still immature. We had to
727 /// rebuild the nrfutil program since the supplied one was not suitable for
728 /// the Linux host we were developing on. See https://forum.sparkfun.com/viewtopic.php?f=32&t=45071
729 /// Also, after downloading a sketch in the nRF52832, the program does not start executing cleanly:
730 /// you have to reset the processor again by pressing the reset button.
731 /// This appears to be a problem with nrfutil, rather than a bug in RadioHead.
732 /// \version 1.66 2017-01-15
733 /// Fixed some errors in (unused) register definitions in RH_RF95.h.<br>
734 /// Fixed a problem that caused compilation errors in RH_NRF51 if the appropriate board
735 /// support was not installed.
736 /// \version 1.67 2017-01-24
737 /// Added RH_RF95::frequencyError() to return the estimated centre frequency offset in Hz
738 /// of the last received message
739 /// \version 1.68 2017-01-25
740 /// Fixed arithmetic error in RH_RF95::frequencyError() for some platforms.
741 /// \version 1.69 2017-02-02
742 /// Added RH_RF95::lastSNR() and improved lastRssi() calculations per the manual.
743 /// \version 1.70 2017-02-03
744 /// Added link to Binpress commercial license purchasing.
745 /// \version 1.71 2017-02-07
746 /// Improved support for STM32. Patch from Bent Guldbjerg Christensen.
747 /// \version 1.72 2017-03-02
748 /// In RH_RF24, fixed a problem where some important properties were not set by the ModemConfig.
749 /// Added properties 2007, 2008, 2009. Also properties 200a was not being set in the chip.
750 /// Reported by Shannon Bailey and Alan Adamson.
751 /// Fixed corresponding convert.pl and added it to the distribution.
752 /// \version 1.73 2017-03-04
753 /// Significant changes to RH_RF24 and its API. It is no longer possible to change the modulation scheme
754 /// programatically: it proved impossible to cater for all the possible crystal frequencies,
755 /// base frequency and modulation schemes. Instead you can use one of a small set of supplied radio
756 /// configuration header files, or generate your own with Silicon Labs WDS application. Changing
757 /// modulation scheme required editing RH_RF24.cpp to specify the appropriate header and recompiling.
758 /// convert.pl is now redundant and removed from the distribution.
759 /// \version 1.74 2017-03-08
760 /// Changed RHReliableDatagram so it would not ACK messages heard addressed to other nodes
761 /// in promiscuous mode.<br>
762 /// Added RH_RF24::deviceType() to return the integer value of the connected device.<br>
763 /// Added documentation about how to connect RFM69 to an ESP8266. Tested OK.<br>
764 /// RH_RF24 was not correctly changing state in sleep() and setModeIdle().<br>
765 /// Added example rf24_lowpower_client.pde showing how to put an arduino and radio into a low power
766 /// mode between transmissions to save battery power.<br>
767 /// Improvements to RH_RF69::setTxPower so it now takes an optional ishighpowermodule
768 /// flag to indicate if the connected module is a high power RFM69HW, and so set the power level
769 /// correctly. Based on code contributed by bob.
770 /// \version 1.75 2017-06-22
771 /// Fixed broken compiler issues with RH_RF95::frequencyError() reported by Steve Rogerson.<br>
772 /// Testing with the very excellent Rocket Scream boards equipped with RF95 TCXO modules. The
773 /// temperature controlled oscillator stabilises the chip enough to be able to use even the slowest
774 /// protocol Bw125Cr48Sf4096. Caution, the TCXO model radios are not low power when in sleep (consuming
775 /// about ~600 uA, reported by Phang Moh Lim).<br>
776 /// Added support for EBYTE E32-TTL-1W and family serial radio transceivers. These RF95 LoRa based radios
777 /// can deliver reliable messages at up to 7km measured.
778 /// \version 1.76 2017-06-23
779 /// Fixed a problem with RH_RF95 hanging on transmit under some mysterious circumstances.
780 /// Reported by several people at https://forum.pjrc.com/threads/41878-Probable-race-condition-in-Radiohead-library?p=146601#post146601 <br>
781 /// Increased the size of rssi variables to 16 bits to permit RSSI less than -128 as reported by RF95.
782 /// \version 1.77 2017-06-25
783 /// Fixed a compilation error with lastRssi().<br>
784 /// \version 1.78 2017-07-19
785 /// Fixed a number of unused variable warnings from g++.<br>
786 /// Added new module RHEncryptedDriver and examples, contributed by Philippe Rochat, which
787 /// adds encryption and decryption to any RadioHead transport driver, using any encryption cipher
788 /// supported by ArduinoLibs Cryptographic Library http://rweather.github.io/arduinolibs/crypto.html
789 /// Includes several examples.<br>
790 /// \version 1.79 2017-07-25
791 /// Added documentation about 'Passing Sensor Data Between RadioHead nodes'.<br>
792 /// Changes to RH_CC110 driver to calculate RSSI in dBm, based on a patch from Jurie Pieterse.<br>
793 /// Added missing passthroughmethoids to RHEncryptedDriver, allowing it to be used with RHDatagram,
794 /// RHReliableDatagram etc. Tested with RH_Serial. Added examples
795 /// \version 1.80 2017-10-04
796 /// Testing with the very fine Talk2 Whisper Node LoRa boards https://wisen.com.au/store/products/whisper-node-lora
797 /// an Arduino compatible board, which include an on-board RFM95/96 LoRa Radio (Semtech SX1276), external antenna,
798 /// run on 2xAAA batteries and support low power operations. RF95 examples work without modification.
799 /// Use Arduino Board Manager to install the Talk2 code support. Upload the code with an FTDI adapter set to 5V.<br>
800 /// Added support for SPI transactions in development environments that support it with SPI_HAS_TRANSACTION.
801 /// Tested on ESP32 with RFM-22 and Teensy 3.1 with RF69
802 /// Added support for ESP32, tested with RFM-22 connected by SPI.<br>
803 ///
804 ///\version 1.81 2017-11-15
805 /// RH_CC110, moved setPaTable() from protected to public.<br>
806 /// RH_RF95 modem config Bw125Cr48Sf4096 altered to enable slow daat rate in register 26
807 /// as suggested by Dieter Kneffel.
808 /// Added support for nRF52 compatible Arm chips such as as Adafruit BLE Feather board
809 /// https://www.adafruit.com/product/3406, with a patch from Mike Bell.<br>
810 /// Fixed a problem where rev 1.80 broke Adafruit M0 LoRa support by declaring
811 /// bitOrder variable always as a unsigned char. Reported by Guilherme Jardim.<br>
812 /// In RH_RF95, all modes now have AGC enabled, as suggested by Dieter Kneffel.<br>
813 ///
814 /// \author Mike McCauley. DO NOT CONTACT THE AUTHOR DIRECTLY. USE THE GOOGLE LIST GIVEN ABOVE
815 
816 /*! \page packingdata
817 \par Passing Sensor Data Between RadioHead nodes
818 
819 People often ask about how to send data (such as numbers, sensor
820 readings etc) from one RadioHead node to another. Although this issue
821 is not specific to RadioHead, and more properly lies in the area of
822 programming for networks, we will try to give some guidance here.
823 
824 One reason for the uncertainty and confusion in this area, especially
825 amongst beginners, is that there is no *best* way to do it. The best
826 solution for your project may depend on the range of processors and
827 data that you have to deal with. Also, it gets more difficult if you
828 need to send several numbers in one packet, and/or deal with floating
829 point numbers.
830 
831 The principal cause of difficulty is that different microprocessors of
832 the kind that run RadioHead may have different ways of representing
833 binary data such as integers. Some processors are little-endian and
834 some are big-endian in the way they represent multi-byte integers
835 (https://en.wikipedia.org/wiki/Endianness). And different processors
836 and maths libraries may represent floating point numbers in radically
837 different ways:
838 (https://en.wikipedia.org/wiki/Floating-point_arithmetic)
839 
840 All the RadioHead examples show how to send and receive simple ASCII
841 strings, and if thats all you want, refer to the examples folder in
842 your RadioHead distribution. But your needs may be more complicated
843 than that.
844 
845 The essence of all engineering is compromise so it will be up to you to
846 decide whats best for your paricular needs. The main choices are:
847 - Raw Binary
848 - Network Order Binary
849 - ASCII
850 
851 \par Raw Binary
852 
853 With this technique you just pack the raw binary numbers into the packet:
854 
855 \code
856 // Sending a single integer
857 // in the transmitter:
858 ...
859 uint16_t data = getsomevalue();
860 if (!driver.send((uint8_t*)&data, sizeof(data)))
861 {
862  ...
863 \endcode
864 
865 \code
866 // and in the receiver:
867 ...
868 uint16_t data;
869 uint8_t datalen = sizeof(data);
870 if ( driver.recv((uint8_t*)&data, &datalen)
871  && datalen == sizeof(data))
872 {
873  // Have the data, so do something with it
874  uint16_t xyz = data;
875  ...
876 \endcode
877 
878 If you need to send more than one number at a time, its best to pack
879 them into a structure
880 
881 \code
882 // Sending several integers in a structure
883 // in a common header for your project:
884 typedef struct
885 {
886  uint16_t dataitem1;
887  uint16_t dataitem2;
888 } MyDataStruct;
889 ...
890 \endcode
891 
892 \code
893 // In the transmitter
894 ...
895 MyDataStruct data;
896 data.dataitem1 = getsomevalue();
897 data.dataitem2 = getsomeothervalue();
898 if (!driver.send((uint8_t*)&data, sizeof(data)))
899 {
900  ...
901 \endcode
902 
903 \code
904 // in the receiver
905 MyDataStruct data;
906 uint8_t datalen = sizeof(data);
907 if ( driver.recv((uint8_t*)&data, &datalen)
908  && datalen == sizeof(data))
909 {
910  // Have the data, so do something with it
911  uint16_t pqr = data.dataitem1;
912  uint16_t xyz = data.dataitem2;
913  ....
914 \endcode
915 
916 
917 The disadvantage with this simple technique becomes apparent if your
918 transmitter and receiver have different endianness: the integers you
919 receive will not be the same as the ones you sent (actually they are,
920 but with the internal bytes swapped around, so they probably wont make
921 sense to you). Endianness is not a problem if *every* data item you
922 send is a just single byte (uint8_t or int8_t or char).
923 
924 So you should only adopt this technique if:
925 - You only send data items of a single byte each, or
926 - You are absolutely sure (now and forever into the future) that you
927 will only ever use the same processor in the transmitter and receiver.
928 
929 \par Network Order Binary
930 
931 One solution to the issue of endianness in your processors to to
932 always convert your data from the processor's native byte order to
933 'network byte order' before transmission and then convert it back to
934 the receiver's native byte order. You do this with the htons (host to
935 network short) macro and friends. These functions may be a no-op on
936 big-endian processors.
937 
938 With this technique you convert every multi-byte number to and from
939 network byte order (note that in most Arduino processors an integer is
940 in fact a short, and is the same as int16_t. We prefer to use types
941 that explicitly specify their size so we can be sure of applying the
942 right conversions):
943 
944 \code
945 // Sending a single integer
946 // in the transmitter:
947 ...
948 uint16_t data = htons(getsomevalue());
949 if (!driver.send((uint8_t*)&data, sizeof(data)))
950 {
951  ...
952 \endcode
953 \code
954 // and in the receiver:
955 ...
956 uint16_t data;
957 uint8_t datalen = sizeof(data);
958 if ( driver.recv((uint8_t*)&data, &datalen)
959  && datalen == sizeof(data))
960 {
961  // Have the data, so do something with it
962  uint16_t xyz = ntohs(data);
963  ...
964 \endcode
965 
966 If you need to send more than one number at a time, its best to pack
967 them into a structure
968 
969 \code
970 // Sending several integers in a structure
971 // in a common header for your project:
972 typedef struct
973 {
974  uint16_t dataitem1;
975  uint16_t dataitem2;
976 } MyDataStruct;
977 ...
978 \endcode
979 \code
980 // In the transmitter
981 ...
982 MyDataStruct data;
983 data.dataitem1 = htons(getsomevalue());
984 data.dataitem2 = htons(getsomeothervalue());
985 if (!driver.send((uint8_t*)&data, sizeof(data)))
986 {
987  ...
988 \endcode
989 \code
990 // in the receiver
991 MyDataStruct data;
992 uint8_t datalen = sizeof(data);
993 if ( driver.recv((uint8_t*)&data, &datalen)
994  && datalen == sizeof(data))
995 {
996  // Have the data, so do something with it
997  uint16_t pqr = ntohs(data.dataitem1);
998  uint16_t xyz = ntohs(data.dataitem2);
999  ....
1000 \endcode
1001 
1002 This technique is quite general for integers but may not work if you
1003 want to send floating point number between transmitters and receivers
1004 that have different floating point number representations.
1005 
1006 
1007 \par ASCII
1008 
1009 In this technique, you transmit the printable ASCII equivalent of
1010 each floating point and then convert it back to a float in the receiver:
1011 
1012 \code
1013 // In the transmitter
1014 ...
1015 float data = getsomevalue();
1016 uint8_t buf[15]; // Bigger than the biggest possible ASCII
1017 snprintf(buf, sizeof(buf), "%f", data);
1018 if (!driver.send(buf, strlen(buf) + 1)) // Include the trailing NUL
1019 {
1020  ...
1021 \endcode
1022 \code
1023 
1024 // In the receiver
1025 ...
1026 float data;
1027 uint8_t buf[15]; // Bigger than the biggest possible ASCII
1028 uint8_t buflen = sizeof(buf);
1029 if (driver.recv(buf, &buflen))
1030 {
1031  // Have the data, so do something with it
1032  float data = atof(buf); // String to float
1033  ...
1034 \endcode
1035 
1036 \par Conclusion:
1037 
1038 - This is just a basic introduction to the issues. You may need to
1039 extend your study into related C/C++ programming techniques.
1040 
1041 - You can extend these ideas to signed 16 bit (int16_t) and 32 bit
1042 (uint32_t, int32_t) numbers.
1043 
1044 - Things can be simple or complicated depending on the needs of your
1045 project.
1046 
1047 - We are not going to write your code for you: its up to you to take
1048 these examples and explanations and extend them to suit your needs.
1049 
1050 */
1051 
1052 
1053 
1054 #ifndef RadioHead_h
1055 #define RadioHead_h
1056 
1057 // Official version numbers are maintained automatically by Makefile:
1058 #define RH_VERSION_MAJOR 1
1059 #define RH_VERSION_MINOR 81
1060 
1061 // Symbolic names for currently supported platform types
1062 #define RH_PLATFORM_ARDUINO 1
1063 #define RH_PLATFORM_MSP430 2
1064 #define RH_PLATFORM_STM32 3
1065 #define RH_PLATFORM_GENERIC_AVR8 4
1066 #define RH_PLATFORM_UNO32 5
1067 #define RH_PLATFORM_UNIX 6
1068 #define RH_PLATFORM_STM32STD 7
1069 #define RH_PLATFORM_STM32F4_HAL 8
1070 #define RH_PLATFORM_RASPI 9
1071 #define RH_PLATFORM_NRF51 10
1072 #define RH_PLATFORM_ESP8266 11
1073 #define RH_PLATFORM_STM32F2 12
1074 #define RH_PLATFORM_CHIPKIT_CORE 13
1075 #define RH_PLATFORM_ESP32 14
1076 #define RH_PLATFORM_NRF52 15
1077 
1078 ////////////////////////////////////////////////////
1079 // Select platform automatically, if possible
1080 #ifndef RH_PLATFORM
1081  #if (MPIDE>=150 && defined(ARDUINO))
1082  // Using ChipKIT Core on Arduino IDE
1083  #define RH_PLATFORM RH_PLATFORM_CHIPKIT_CORE
1084  #elif defined(MPIDE)
1085  // Uno32 under old MPIDE, which has been discontinued:
1086  #define RH_PLATFORM RH_PLATFORM_UNO32
1087 #elif defined(NRF51)
1088  #define RH_PLATFORM RH_PLATFORM_NRF51
1089 #elif defined(NRF52)
1090  #define RH_PLATFORM RH_PLATFORM_NRF52
1091  #elif defined(ESP8266)
1092  #define RH_PLATFORM RH_PLATFORM_ESP8266
1093  #elif defined(ESP32)
1094  #define RH_PLATFORM RH_PLATFORM_ESP32
1095  #elif defined(ARDUINO)
1096  #define RH_PLATFORM RH_PLATFORM_ARDUINO
1097  #elif defined(__MSP430G2452__) || defined(__MSP430G2553__)
1098  #define RH_PLATFORM RH_PLATFORM_MSP430
1099  #elif defined(MCU_STM32F103RE)
1100  #define RH_PLATFORM RH_PLATFORM_STM32
1101  #elif defined(STM32F2XX)
1102  #define RH_PLATFORM RH_PLATFORM_STM32F2
1103  #elif defined(USE_STDPERIPH_DRIVER)
1104  #define RH_PLATFORM RH_PLATFORM_STM32STD
1105  #elif defined(RASPBERRY_PI)
1106  #define RH_PLATFORM RH_PLATFORM_RASPI
1107 #elif defined(__unix__) // Linux
1108  #define RH_PLATFORM RH_PLATFORM_UNIX
1109 #elif defined(__APPLE__) // OSX
1110  #define RH_PLATFORM RH_PLATFORM_UNIX
1111  #else
1112  #error Platform not defined!
1113  #endif
1114 #endif
1115 
1116 #if defined(__AVR_ATtiny84__) || defined(__AVR_ATtiny85__) || defined(__AVR_ATtiny24__) || defined(__AVR_ATtiny44__) || defined(__AVR_ATtiny45__) || defined(__AVR_ATtinyX4__) || defined(__AVR_ATtinyX5__) || defined(__AVR_ATtiny2313__) || defined(__AVR_ATtiny4313__) || defined(__AVR_ATtinyX313__)
1117  #define RH_PLATFORM_ATTINY
1118 #endif
1119 
1120 ////////////////////////////////////////////////////
1121 // Platform specific headers:
1122 #if (RH_PLATFORM == RH_PLATFORM_ARDUINO)
1123  #if (ARDUINO >= 100)
1124  #include <Arduino.h>
1125  #else
1126  #include <wiring.h>
1127  #endif
1128  #ifdef RH_PLATFORM_ATTINY
1129  #warning Arduino TinyCore does not support hardware SPI. Use software SPI instead.
1130  #else
1131  #include <SPI.h>
1132  #define RH_HAVE_HARDWARE_SPI
1133  #define RH_HAVE_SERIAL
1134  #endif
1135 
1136 #elif (RH_PLATFORM == RH_PLATFORM_ESP8266) // ESP8266 processor on Arduino IDE
1137  #include <Arduino.h>
1138  #include <SPI.h>
1139  #define RH_HAVE_HARDWARE_SPI
1140  #define RH_HAVE_SERIAL
1141 
1142 #elif (RH_PLATFORM == RH_PLATFORM_ESP32) // ESP32 processor on Arduino IDE
1143  #include <Arduino.h>
1144  #include <SPI.h>
1145  #define RH_HAVE_HARDWARE_SPI
1146  #define RH_HAVE_SERIAL
1147 
1148 #elif (RH_PLATFORM == RH_PLATFORM_MSP430) // LaunchPad specific
1149  #include "legacymsp430.h"
1150  #include "Energia.h"
1151  #include <SPI.h>
1152  #define RH_HAVE_HARDWARE_SPI
1153  #define RH_HAVE_SERIAL
1154 
1155 #elif (RH_PLATFORM == RH_PLATFORM_UNO32 || RH_PLATFORM == RH_PLATFORM_CHIPKIT_CORE)
1156  #include <WProgram.h>
1157  #include <string.h>
1158  #include <SPI.h>
1159  #define RH_HAVE_HARDWARE_SPI
1160  #define memcpy_P memcpy
1161  #define RH_HAVE_SERIAL
1162 
1163 #elif (RH_PLATFORM == RH_PLATFORM_STM32) // Maple, Flymaple etc
1164  #include <STM32ArduinoCompat/wirish.h>
1165  #include <stdint.h>
1166  #include <string.h>
1167  #include <STM32ArduinoCompat/HardwareSPI.h>
1168  #define RH_HAVE_HARDWARE_SPI
1169  // Defines which timer to use on Maple
1170  #define MAPLE_TIMER 1
1171  #define PROGMEM
1172  #define memcpy_P memcpy
1173  #define Serial SerialUSB
1174  #define RH_HAVE_SERIAL
1175 
1176 #elif (RH_PLATFORM == RH_PLATFORM_STM32F2) // Particle Photon with firmware-develop
1177  #include <stm32f2xx.h>
1178  #include <application.h>
1179  #include <math.h> // floor
1180  #define RH_HAVE_SERIAL
1181  #define RH_HAVE_HARDWARE_SPI
1182 
1183 #elif (RH_PLATFORM == RH_PLATFORM_STM32STD) // STM32 with STM32F4xx_StdPeriph_Driver
1184  #include <stm32f4xx.h>
1185  #include <wirish.h>
1186  #include <stdint.h>
1187  #include <string.h>
1188  #include <math.h>
1189  #include <HardwareSPI.h>
1190  #define RH_HAVE_HARDWARE_SPI
1191  #define Serial SerialUSB
1192  #define RH_HAVE_SERIAL
1193 
1194 #elif (RH_PLATFORM == RH_PLATFORM_GENERIC_AVR8)
1195  #include <avr/io.h>
1196  #include <avr/interrupt.h>
1197  #include <util/delay.h>
1198  #include <string.h>
1199  #include <stdbool.h>
1200  #define RH_HAVE_HARDWARE_SPI
1201  #include <SPI.h>
1202 
1203 // For Steve Childress port to ARM M4 w/CMSIS with STM's Hardware Abstraction lib.
1204 // See ArduinoWorkarounds.h (not supplied)
1205 #elif (RH_PLATFORM == RH_PLATFORM_STM32F4_HAL)
1206  #include <ArduinoWorkarounds.h>
1207  #include <stm32f4xx.h> // Also using ST's CubeMX to generate I/O and CPU setup source code for IAR/EWARM, not GCC ARM.
1208  #include <stdint.h>
1209  #include <string.h>
1210  #include <math.h>
1211  #define RH_HAVE_HARDWARE_SPI // using HAL (Hardware Abstraction Libraries from ST along with CMSIS, not arduino libs or pins concept.
1212 
1213 #elif (RH_PLATFORM == RH_PLATFORM_RASPI)
1214  #define RH_HAVE_HARDWARE_SPI
1215  #define RH_HAVE_SERIAL
1216  #define PROGMEM
1217  #include <RHutil/RasPi.h>
1218  #include <string.h>
1219  //Define SS for CS0 or pin 24
1220  #define SS 8
1221 
1222 #elif (RH_PLATFORM == RH_PLATFORM_NRF51)
1223  #define RH_HAVE_SERIAL
1224  #define PROGMEM
1225  #include <Arduino.h>
1226 
1227 #elif (RH_PLATFORM == RH_PLATFORM_NRF52)
1228  #include <SPI.h>
1229  #define RH_HAVE_HARDWARE_SPI
1230  #define RH_HAVE_SERIAL
1231  #define PROGMEM
1232  #include <Arduino.h>
1233 
1234 #elif (RH_PLATFORM == RH_PLATFORM_UNIX)
1235  // Simulate the sketch on Linux and OSX
1236  #include <RHutil/simulator.h>
1237  #define RH_HAVE_SERIAL
1238 #include <netinet/in.h> // For htons and friends
1239 
1240 #else
1241  #error Platform unknown!
1242 #endif
1243 
1244 ////////////////////////////////////////////////////
1245 // This is an attempt to make a portable atomic block
1246 #if (RH_PLATFORM == RH_PLATFORM_ARDUINO)
1247 #if defined(__arm__)
1248  #include <RHutil/atomic.h>
1249  #else
1250  #include <util/atomic.h>
1251  #endif
1252  #define ATOMIC_BLOCK_START ATOMIC_BLOCK(ATOMIC_RESTORESTATE) {
1253  #define ATOMIC_BLOCK_END }
1254 #elif (RH_PLATFORM == RH_PLATFORM_CHIPKIT_CORE)
1255  // UsingChipKIT Core on Arduino IDE
1256  #define ATOMIC_BLOCK_START unsigned int __status = disableInterrupts(); {
1257  #define ATOMIC_BLOCK_END } restoreInterrupts(__status);
1258 #elif (RH_PLATFORM == RH_PLATFORM_UNO32)
1259  // Under old MPIDE, which has been discontinued:
1260  #include <peripheral/int.h>
1261  #define ATOMIC_BLOCK_START unsigned int __status = INTDisableInterrupts(); {
1262  #define ATOMIC_BLOCK_END } INTRestoreInterrupts(__status);
1263 #elif (RH_PLATFORM == RH_PLATFORM_STM32F2) // Particle Photon with firmware-develop
1264  #define ATOMIC_BLOCK_START { int __prev = HAL_disable_irq();
1265  #define ATOMIC_BLOCK_END HAL_enable_irq(__prev); }
1266 #elif (RH_PLATFORM == RH_PLATFORM_ESP8266)
1267 // See hardware/esp8266/2.0.0/cores/esp8266/Arduino.h
1268  #define ATOMIC_BLOCK_START { uint32_t __savedPS = xt_rsil(15);
1269  #define ATOMIC_BLOCK_END xt_wsr_ps(__savedPS);}
1270 #else
1271  // TO BE DONE:
1272  #define ATOMIC_BLOCK_START
1273  #define ATOMIC_BLOCK_END
1274 #endif
1275 
1276 ////////////////////////////////////////////////////
1277 // Try to be compatible with systems that support yield() and multitasking
1278 // instead of spin-loops
1279 // Recent Arduino IDE or Teensy 3 has yield()
1280 #if (RH_PLATFORM == RH_PLATFORM_ARDUINO && ARDUINO >= 155 && !defined(RH_PLATFORM_ATTINY)) || (TEENSYDUINO && defined(__MK20DX128__))
1281  #define YIELD yield();
1282 #elif (RH_PLATFORM == RH_PLATFORM_ESP8266)
1283 // ESP8266 also hash it
1284  #define YIELD yield();
1285 #else
1286  #define YIELD
1287 #endif
1288 
1289 ////////////////////////////////////////////////////
1290 // digitalPinToInterrupt is not available prior to Arduino 1.5.6 and 1.0.6
1291 // See http://arduino.cc/en/Reference/attachInterrupt
1292 #ifndef NOT_AN_INTERRUPT
1293  #define NOT_AN_INTERRUPT -1
1294 #endif
1295 #ifndef digitalPinToInterrupt
1296  #if (RH_PLATFORM == RH_PLATFORM_ARDUINO) && !defined(__arm__)
1297 
1298  #if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__)
1299  // Arduino Mega, Mega ADK, Mega Pro
1300  // 2->0, 3->1, 21->2, 20->3, 19->4, 18->5
1301  #define digitalPinToInterrupt(p) ((p) == 2 ? 0 : ((p) == 3 ? 1 : ((p) >= 18 && (p) <= 21 ? 23 - (p) : NOT_AN_INTERRUPT)))
1302 
1303  #elif defined(__AVR_ATmega1284__) || defined(__AVR_ATmega1284P__)
1304  // Arduino 1284 and 1284P - See Manicbug and Optiboot
1305  // 10->0, 11->1, 2->2
1306  #define digitalPinToInterrupt(p) ((p) == 10 ? 0 : ((p) == 11 ? 1 : ((p) == 2 ? 2 : NOT_AN_INTERRUPT)))
1307 
1308  #elif defined(__AVR_ATmega32U4__)
1309  // Leonardo, Yun, Micro, Pro Micro, Flora, Esplora
1310  // 3->0, 2->1, 0->2, 1->3, 7->4
1311  #define digitalPinToInterrupt(p) ((p) == 0 ? 2 : ((p) == 1 ? 3 : ((p) == 2 ? 1 : ((p) == 3 ? 0 : ((p) == 7 ? 4 : NOT_AN_INTERRUPT)))))
1312 
1313  #else
1314  // All other arduino except Due:
1315  // Serial Arduino, Extreme, NG, BT, Uno, Diecimila, Duemilanove, Nano, Menta, Pro, Mini 04, Fio, LilyPad, Ethernet etc
1316  // 2->0, 3->1
1317  #define digitalPinToInterrupt(p) ((p) == 2 ? 0 : ((p) == 3 ? 1 : NOT_AN_INTERRUPT))
1318 
1319  #endif
1320 
1321  #elif (RH_PLATFORM == RH_PLATFORM_UNO32) || (RH_PLATFORM == RH_PLATFORM_CHIPKIT_CORE)
1322  // Hmmm, this is correct for Uno32, but what about other boards on ChipKIT Core?
1323  #define digitalPinToInterrupt(p) ((p) == 38 ? 0 : ((p) == 2 ? 1 : ((p) == 7 ? 2 : ((p) == 8 ? 3 : ((p) == 735 ? 4 : NOT_AN_INTERRUPT)))))
1324 
1325  #else
1326  // Everything else (including Due and Teensy) interrupt number the same as the interrupt pin number
1327  #define digitalPinToInterrupt(p) (p)
1328  #endif
1329 #endif
1330 
1331 // On some platforms, attachInterrupt() takes a pin number, not an interrupt number
1332 #if (RH_PLATFORM == RH_PLATFORM_ARDUINO) && defined (__arm__) && (defined(ARDUINO_ARCH_SAMD) || defined(ARDUINO_SAM_DUE))
1333  #define RH_ATTACHINTERRUPT_TAKES_PIN_NUMBER
1334 #endif
1335 
1336 // Slave select pin, some platforms such as ATTiny do not define it.
1337 #ifndef SS
1338  #define SS 10
1339 #endif
1340 
1341 // These defs cause trouble on some versions of Arduino
1342 #undef abs
1343 #undef round
1344 #undef double
1345 
1346 // Sigh: there is no widespread adoption of htons and friends in the base code, only in some WiFi headers etc
1347 // that have a lot of excess baggage
1348 #if RH_PLATFORM != RH_PLATFORM_UNIX && !defined(htons)
1349 // #ifndef htons
1350 // These predefined macros available on modern GCC compilers
1351  #if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__
1352  // Atmel processors
1353  #define htons(x) ( ((x)<<8) | (((x)>>8)&0xFF) )
1354  #define ntohs(x) htons(x)
1355  #define htonl(x) ( ((x)<<24 & 0xFF000000UL) | \
1356  ((x)<< 8 & 0x00FF0000UL) | \
1357  ((x)>> 8 & 0x0000FF00UL) | \
1358  ((x)>>24 & 0x000000FFUL) )
1359  #define ntohl(x) htonl(x)
1360 
1361  #elif __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
1362  // Others
1363  #define htons(x) (x)
1364  #define ntohs(x) (x)
1365  #define htonl(x) (x)
1366  #define ntohl(x) (x)
1367 
1368  #else
1369  #error "Dont know how to define htons and friends for this processor"
1370  #endif
1371 #endif
1372 
1373 // This is the address that indicates a broadcast
1374 #define RH_BROADCAST_ADDRESS 0xff
1375 
1376 // Uncomment this is to enable Encryption (see RHEncryptedDriver):
1377 // But ensure you have installed the Crypto directory from arduinolibs first:
1378 // http://rweather.github.io/arduinolibs/index.html
1379 //#define RH_ENABLE_ENCRYPTION_MODULE
1380 
1381 #endif