While having done some projects with Arduinos and nRF24l01 modules I was wondering if I could save some effort by using an ESP8266 module instead. The advantage of the ESP8266 module is that it contains a micro controller on board, so no additional Arduino board is needed. Additionally the memory size of the ESP8266 is much bigger and in regard to speed the ESP8266 runs at max 160MHz instead of the Arduino's 16MHz. Of course there are some negative sides.
The ESP8266 runs on 3.3V only, has fewer pins and is missing the nice analog inputs the Arduino has (it has one, but only for 1.0V and not 3.3V). Additionally there are many more code examples for the Arduino + nRF24l01 then there are for the ESP8266 especially when it comes to direct data transfer.
So with a project in mind, I looked into the topic of fast and lightweight data transfer between two ESP8266 without all the WWW and HTTP stuff.
While searching the internet for examples (most of the below code was picked from the net at various places) I came across many questions how to implement a direct data transfer without the nice "do it like that" examples. There was some example code, but mostly with question why it did not work.
So after some reading and trying to understand, I created the below examples which allow fast and simple transfer of data between two ESP8266.
Step 1: Boundaries and Backgrounds (TCP Vs. UDP)
To get there, some boundaries have to be clarified compared to the nRF24l01.
To use the ESP8266 within the Arduino environment, the basic library to use is the ESP8266WiFi.h. The might be different ones, but most examples use the mentioned on. When using this, you need to get your communication to WiFi level.
So, to communicate there needs to be at least an access point(AP) / server and a client. The AP provides the name of the network and the IP addresses and the client will connect to this server.
So compared the nRF24l01, where the code at both ends is more or less the same (except for the transmission channels) the code of the ESP8266 is fundamentally different, as one is configured as AP and the other as client.
The next topic is, that instead of just sending some bytes to the nRF24l01, for the ESP8266 transfer protocols need to be observed.
There are two common used protocols: TCP and UDP.
The TCP (Transmission Control Protocol) is a protocol which allows a loss-free transmission between a server and a client. The protocol incorporates “handshakes” (lots of flags and acknoledges sent between both parties) and packet numbering and detection to identify and re-transmission of lost packets. Additionally, by using all these handshakes the protocol prevents data lost due to many packets send at the same time in the network. Data packets wait until they can be received.
The UDP (User Datagram Protocol) is lacking all the handshakes, packet numbering and re-transmission. Its overhead is therefore smaller and there is no need for all the handshakes to maintain a connection. UDP incorporates some basic error detection, but no correction (the corrupted package is just dropped). Data are send, without the knowledge if the receiving party is free to receive the data. At the same time, multiple packets can collide, as each party sends the data whenever it is needed. By omiting all the handshakes, there is one additional nice feature of UDP called “multicast” and “broadcast”. In the “multicast” case data packets are sent to a predefined group of members, in a “broadcast” data packets are sent to all connected members. This reduces data transfer considerably in case of streams to be received by multiple members (e.g. by sending a video feed to multiple receivers or by sending the current time to multiple connected devices).
There are some good videos on Youtube explaining it even better.
So when sending data, it is important to know your needs:
- un-corrupted data, management of multiple peers by handshakes → TCP
- real time data, fast connection → UDP
I first started with the implementation of a TCP based communication (between one Server and one Client). While testing it, I had stalling problems in transmission. At the beginning the data was exchanged fast, then after a while the speed dropped dramatically. I concluded that this was a typical problem of the TCP approach (which was wrong!), so then changed to a solution based on UDP. Finally I got both approached working. So both solution will be provided.
Sketches below have for TCP and UDP in common that they:
- are independent to any existing WiFi network. So it will work anywhere far away from the internet and connected routers.
- are sending ASCII data to be printed via the serial monitor.
- are sending data obtained by the millis()-function, to analyze the speed of the transmission.
- are not tested for multiple clients (due to having the hardware to set up the network right now)
Step 2: Hardware
To test the whole set up I used two ESP8266 modules. One module is an ESP-01 + USB-to-UART adapter. The other module is a ESP-12 based module incorporating the USB connection, Voltage regulator and some fun-stuff like switches, LDR and multi-color LED.
The USB-to-UART Module for the ESP-01 needed to be modified a bit to be able to use it as a programmer (again Youtube by Csongor Varga).
In order to run the sketches, you need to install the ESP8266 libraries (as described at many places in the internet). In both cases (TCP and UDP) there is a server and client sketch each. Which sketch is loaded to which module does not matter.
As mentioned, the sketches are based on many bits and pieces I found at the web. I do not remember anymore where I found what, and what is original code or what I changed. So I just wanted to thank the big community in general out there for publishing all the great examples.
Step 3: The Sketches
The Code consist of two sketches each (as explained), a server sketch and client sketch, for TCP and UDP each.