Embedded Networking and Communications

Assignment to be done:

1.Group Assignment:
Send a message between two projects

To be found here

What I have learned from group assignment

In our group assignment, We want to use two esp32 MCU communicate and exhange data via wifi network protocol over esp-now data protocol.
Esp32 is built in bluetooth and wifi which makes it to be suitable to use for this assignment.

What ESP-NOW Protocol?

ESP-NOW is a proprietary communication protocol developed by Espressif, the company that manufactures the ESP8266 and ESP32 microcontrollers. It allows for communication between two or more ESP devices without the need for a Wi-Fi network.
ESP-NOW uses a simple and lightweight message format that consists of a header and a payload. The header includes the sender and receiver MAC addresses and a message type field, while the payload can be up to 250 bytes. The protocol uses a one-to-many communication model, where a sender can broadcast a message to multiple receivers in a single transmission. ESP-NOW also provides strong security features, including message encryption and authentication, to protect against unauthorized access and tampering. Overall, ESP-NOW is a reliable and easy-to-use protocol for building low-power, wireless networks with ESP devices.

RANGE TEST FOR ESP-NOW

The ESP-NOW Documentations such as (Espressif say that the range is about 200 meters in open space but the range can vary according to the area , walls and other obstacles can reduce the range

2. Individual Assignment:

Design, build, and connect wired or wireless node(s) with network or bus addresses


What I have learned from implementing networking and communication

What is emmbedded networking? Refering to here,The field of embedded networking deals with the network design and topology, hardware devices, and communication/data exchange protocols needed to connect and exchange information between embedded systems.
Embedded systems engineers today have access to a range of wired and wireless communication options for implementing networking capabilities into their embedded systems.

In networking, two or more devices are wired or wireless connect sothat they will be able to exchange the data or information.
Here in my assignment, I used the previuosly designed ESP32 board as the first node and another commercial ESP32 board as the second node and then I elaborated the communication between them as detailed in the following procedures.

Above is the board I have designed in the previous works.
This board, I want to eleborate a wireless communication between it and an other commecial one which both are of ESP32 board. I want each to send and receive the data to or from an other which I can say is Full Duplex Transmission Mode.

According to (here is the link), Full Duplex Transmission Mode is a mode of transmission in which the flow of data is bi-directional. But here, the devices can send as well as receive data simultaneously at the same time. It means that the receiver can receive as well as send data at the very same time with no hitch.

Above image is of a commercial board to be used.
This means that each board will be a transmitted(sender) as well as a receiver at the same time.

Before I implement the communication between my boards, I had to think about different requirements for their communication be possible. First I thought on the network protocols to be used.
By refering from here(link)Network protocols are a set of rules outlining how connected devices communicate across a network to exchange information easily and safely.

To elaborate the communication between my boards, I used ESP-NOW communication protocol developed by Expressif.
Reference from here is the link

What is ESP-NOW?
According to (Link here), ESP-NOW is a wireless communication protocol defined by Espressif, which enables the direct, quick and low-power control of smart devices, without the need of a router. ESP-NOW can work with Wi-Fi and Bluetooth LE, and supports the ESP8266, ESP32, ESP32-S and ESP32-C series of SoCs. It’s widely used in smart-home appliances, remote controlling, sensors, etc.

Second I thought about what address to used by those two boards and we found the MAC address of each board through an Arduino sketch to differentiate between the two modules.

Programming process

The programming process started by scanning the MAC address of each board and programming them with a specific message to be send in each board.

    
       
     
codes to scan the mac addres of the boards:
 
  
    #include< WiFi.h>

        void setup() {
          Serial.begin(115200);
          
          // initialize WiFi
          WiFi.mode(WIFI_STA);
          WiFi.disconnect();
            
          // print the MAC address of the ESP32
          Serial.print("MAC address: ");
          Serial.println(WiFi.macAddress());
        }
        
        void loop() {
          // print the MAC address of the ESP32
          Serial.print("MAC address: ");
          Serial.println(WiFi.macAddress());
          delay(2000);
        }

  
 
Then the MAC address is displayed in the serial monitor as shown in the images below:

Image above shows the MAC address of the first board.

Then with the same code and second board connected on the other port,
 
    
      #include< mWiFi.h>
  
          void setup() {
            Serial.begin(115200);
            
            // initialize WiFi
            WiFi.mode(WIFI_STA);
            WiFi.disconnect();
              
            // print the MAC address of the ESP32
            Serial.print("MAC address: ");
            Serial.println(WiFi.macAddress());
          }
          
          void loop() {
            // print the MAC address of the ESP32
            Serial.print("MAC address: ");
            Serial.println(WiFi.macAddress());
            delay(2000);
          }
  
    
   
I got the MAC address of the second board as shown with the immage below

From there I got the MAC addresses of my two boards.

The next is programming of the boards with a message to be send. Note that each board will be transmitting to an other and receiving from another at the same time provided that in the code of each board I mentioned the address of an other as its receiver.

Sender Codes
 
    
        #include < esp_now.h >
            #include < WiFi.h >
            
            #include < Wire.h >
            
            
            // REPLACE WITH THE MAC Address of your receiver 
            uint8_t broadcastAddress[] = {0x7C, 0x9E, 0xBD, 0x49, 0x4E, 0x28};
            
            // Define variables to store BME280 readings to be sent
            float temperature;
            float humidity;
            float pressure;
            
            // Define variables to store incoming readings
            float incomingTemp;
            float incomingHum;
            float incomingPres;
            
            // Variable to store if sending data was successful
            String success;
            
            //Structure example to send data
            //Must match the receiver structure
            typedef struct struct_message {
                float temp;
                float hum;
                float pres;
            } struct_message;
            
            // Create a struct_message called BME280Readings to hold sensor readings
            struct_message BME280Readings;
            
            // Create a struct_message to hold incoming sensor readings
            struct_message incomingReadings;
            
            esp_now_peer_info_t peerInfo;
            
            // Callback when data is sent
            void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status) {
              Serial.print("\r\nLast Packet Send Status:\t");
              Serial.println(status == ESP_NOW_SEND_SUCCESS ? "Delivery Success" : "Delivery Fail");
              if (status ==0){
                success = "Delivery Success :)";
              }
              else{
                success = "Delivery Fail :(";
              }
            }
            
            // Callback when data is received
            void OnDataRecv(const uint8_t * mac, const uint8_t *incomingData, int len) {
              memcpy(&incomingReadings, incomingData, sizeof(incomingReadings));
              Serial.print("Bytes received: ");
              Serial.println(len);
              incomingTemp = incomingReadings.temp;
              incomingHum = incomingReadings.hum;
              incomingPres = incomingReadings.pres;
            }
             
            void setup() {
              // Init Serial Monitor
              Serial.begin(115200);
            
            
              // Set device as a Wi-Fi Station
              WiFi.mode(WIFI_STA);
            
              // Init ESP-NOW
              if (esp_now_init() != ESP_OK) {
                Serial.println("Error initializing ESP-NOW");
                return;
              }
            
              // Once ESPNow is successfully Init, we will register for Send CB to
              // get the status of Trasnmitted packet
              esp_now_register_send_cb(OnDataSent);
              
              // Register peer
              memcpy(peerInfo.peer_addr, broadcastAddress, 6);
              peerInfo.channel = 0;  
              peerInfo.encrypt = false;
              
              // Add peer        
              if (esp_now_add_peer(&peerInfo) != ESP_OK){
                Serial.println("Failed to add peer");
                return;
              }
              // Register for a callback function that will be called when data is received
              esp_now_register_recv_cb(OnDataRecv);
            }
             
            void loop() {
              getReadings();
              delay(1000);  
              // Set values to send
              BME280Readings.temp = temperature;
              BME280Readings.hum = humidity;
              BME280Readings.pres = pressure;
            
              // Send message via ESP-NOW
              esp_err_t result = esp_now_send(broadcastAddress, (uint8_t *) &BME280Readings, sizeof(BME280Readings));
               
              if (result == ESP_OK) {
                Serial.println("Sent with success");
              }
              else {
                Serial.println("Error sending the data");
              }
            
              // Display Readings in Serial Monitor
              Serial.println("INCOMING READINGS");
              Serial.print("Temperature: ");
              Serial.print(incomingReadings.temp);
              Serial.println(" ºC");
              Serial.print("Humidity: ");
              Serial.print(incomingReadings.hum);
              Serial.println(" %");
              Serial.print("Pressure: ");
              Serial.print(incomingReadings.pres);
              Serial.println(" hPa");
              Serial.println();
            }
            void getReadings(){
              temperature = 50.1;
              humidity = 40;
              pressure = 80;
            }
  
    
   
The up codes include the message about temperature = 50.1, humidity = 40, and pressure =80 and these data have been embedded directly into the source code(Hard codings) that are being sent to other board.
Below video uploaded on youtube lets say of transmitter.


As it is sending, It also receing the message from other board and the receiving status is shown in the following image:

From above image, you can see that the last packet sent status is Delivery succes or sent with success and also shows the incoming readings

Receiver Codes

 
    
        #include < esp_now.h >
            #include < WiFi.h >
            
            #include < Wire.h >
            
            
            // REPLACE WITH THE MAC Address of your receiver 
            uint8_t broadcastAddress[] = {0x94, 0xE6, 0x86, 0x04, 0x89, 0x3C};
            
            // Define variables to store BME280 readings to be sent
            float temperature;    
            float humidity;
            float pressure;
            
            // Define variables to store incoming readings
            float incomingTemp;
            float incomingHum;
            float incomingPres;
            
            // Variable to store if sending data was successful
            String success;
            
            //Structure example to send data
            //Must match the receiver structure
            typedef struct struct_message {
                float temp;
                float hum;
                float pres;
            } struct_message;
            
            // Create a struct_message called BME280Readings to hold sensor readings
            struct_message BME280Readings;
            
            // Create a struct_message to hold incoming sensor readings
            struct_message incomingReadings;
            
            esp_now_peer_info_t peerInfo;
            
            // Callback when data is sent
            void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status) {
              Serial.print("\r\nLast Packet Send Status:\t");
              Serial.println(status == ESP_NOW_SEND_SUCCESS ? "Delivery Success" : "Delivery Fail");
              if (status ==0){
                success = "Delivery Success :)";
              }
              else{
                success = "Delivery Fail :(";
              }
            }
            
            // Callback when data is received
            void OnDataRecv(const uint8_t * mac, const uint8_t *incomingData, int len) {
              memcpy(&incomingReadings, incomingData, sizeof(incomingReadings));
              Serial.print("Bytes received: ");
              Serial.println(len);
              incomingTemp = incomingReadings.temp;
              incomingHum = incomingReadings.hum;
              incomingPres = incomingReadings.pres;
            }
             
            void setup() {
              // Init Serial Monitor
              Serial.begin(115200);
            
            
              // Set device as a Wi-Fi Station
              WiFi.mode(WIFI_STA);
            
              // Init ESP-NOW
              if (esp_now_init() != ESP_OK) {
                Serial.println("Error initializing ESP-NOW");
                return;
              }
            
              // Once ESPNow is successfully Init, we will register for Send CB to
              // get the status of Trasnmitted packet
              esp_now_register_send_cb(OnDataSent);
              
              // Register peer
              memcpy(peerInfo.peer_addr, broadcastAddress, 6);
              peerInfo.channel = 0;  
              peerInfo.encrypt = false;
              
              // Add peer        
              if (esp_now_add_peer(&peerInfo) != ESP_OK){
                Serial.println("Failed to add peer");
                return;
              }
              // Register for a callback function that will be called when data is received
              esp_now_register_recv_cb(OnDataRecv);
            }
             
            void loop() {
              getReadings();
              delay(1000);  
              // Set values to send
              BME280Readings.temp = temperature;
              BME280Readings.hum = humidity;
              BME280Readings.pres = pressure;
            
              // Send message via ESP-NOW
              esp_err_t result = esp_now_send(broadcastAddress, (uint8_t *) &BME280Readings, sizeof(BME280Readings));
               
              if (result == ESP_OK) {
                Serial.println("Sent with success");
              }
              else {
                Serial.println("Error sending the data");
              }
            
              // Display Readings in Serial Monitor
              Serial.println("INCOMING READINGS");
              Serial.print("Temperature: ");
              Serial.print(incomingReadings.temp);
              Serial.println(" ºC");
              Serial.print("Humidity: ");
              Serial.print(incomingReadings.hum);
              Serial.println(" %");
              Serial.print("Pressure: ");
              Serial.print(incomingReadings.pres);
              Serial.println(" hPa");
              Serial.println();
            }
            void getReadings(){
              temperature = 20.1;
              humidity = 99;
              pressure = 120;
            }
  
    
   
The up codes includes the message about temperature, humidity and pressure that are being sent to other board.

As it is sending, It also receing the message from other board and the receiving status is shown in the following image:

From above image, you can see that the last packet sent status is Delivery succes or sent with success and also shows the incoming readings

Below video uploaded on youtube is lets say of receiver .


These boards also can communicate when they are connected on the same computer provided that you change the port number when you want to see the serial monitor of an other or to see how an other is sending and receiving the data.

The used board has been designed in the previous assignments and its design files can downloaded from here