Thread: How to verify my incoming UDP packet correctly?

  1. #1
    Registered User
    Join Date
    Sep 2020
    Posts
    20

    How to verify my incoming UDP packet correctly?

    I believe I'm trying to fix something quite easy. Still I'm having issues unfortunately.


    With my windows forms I'm sending a UDP packet which contains a 3 digits number (for example: `101` ) and a string with a task `"_available"`.


    Now my device, who captures the packet should read this as a ID and a task. If it is his ID, then he has to execute the task.


    I'm sure the message arrives correctly, for debug I did a simple string comparison`!strcmp(packetBuffer, "101_available"));`, which works. Also, I can see in console that the devices receives the messages correctly, so here is the dumb part;
    Somehow I can't get the code correctly to make a correct comparison.


    I've tried three things so far.


    First of all I've tried to compare the incoming PacketBuffer (tableID is defined as byte, this works best):


    Code:
          if (packetBuffer,UDP_TX_PACKET_MAX_SIZE){   
            if(packetBuffer == tableID + "_available"){
            modeAvailable();
            }
    Secondly, I tried
    Code:
    strstr
    as comparison


    Code:
          if (strstr(packetBuffer, tableID +  "_available")) {
            modeAvailable();
          }
    I also tried it like this:
    Code:
    if (strstr(packetBuffer, tableID +  "_available")== packetBuffer));
    Finally I also tried:


    Code:
          if (strcmp(packetBuffer, "{0}_available")) {
            if(packetBuffer == tableID + "_available"){
            modeAvailable();


    In all cases, I can read the packet just like I want it and how I expect it to be.
    So the only thing that goes wrong is that the If statements are not returning true.
    I'm also sure that the TableID is set correctly (this is programmed in the EEPROM)




    Does anyone know what goes wrong here?

  2. #2
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    This looks like you forgot that string concatenation in C is not done with the + operator, but rather you either need to append a copy of one string to the other, if there's space, or create an entirely new array with enough space to store concatenated copies of the two strings. Hence, you would find yourself calling strcpy, strcat, that sort of thing.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  3. #3
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338

    Question

    maybe try a byte to byte comparison ?

    i.e: instead of using strcmp(), compare:
    Code:
    for (x++) { if string[x] == other[x] }
    "without goto we would be wtf'd"

  4. #4
    Registered User
    Join Date
    Sep 2020
    Posts
    20
    Quote Originally Posted by Structure View Post
    maybe try a byte to byte comparison ?

    i.e: instead of using strcmp(), compare:
    Code:
    for (x++) { if string[x] == other[x] }
    Sorry, I'm not sure how to implement this

  5. #5
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338

    Post

    Code:
    #include <stdio.h>
    #include <string.h>
    
    char *string = "string one";
    char *other = "string one";
    
    int compare( char *string1, char *string2 ) {    
        if ( strlen(string1) != strlen(string2) ) {
            return 0;
        }
        for (int i=0; i<strlen(string1); i++) {
            if ( string1[i] != string2[i] ) {
                return 0;
            }
        }
        return 1;
    };
    
    int main( int argc, char *argv[] ) {
    
        printf( "IsMatch?: %i", compare(string,other) );
    
        return 0;
    }
    the compare() functions returns 1 if equal, 0 if not equal.
    Last edited by Structure; 09-11-2020 at 08:20 AM.
    "without goto we would be wtf'd"

  6. #6
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338
    you could also return 2 if they are are not the same length.
    This way you can find out if you have trailing bytes at the end or beginning.

    Code:
    int compare( char *string1, char *string2 ) { 
       
        if ( strlen(string1) != strlen(string2) ) {
            return 2;
        }
    
        for (int i=0; i<strlen(string1); i++) {
            if ( string1[i] != string2[i] ) {
                return 0;
            }
        }
    
        return 1;
    }
    Last edited by Structure; 09-11-2020 at 08:28 AM.
    "without goto we would be wtf'd"

  7. #7
    Registered User
    Join Date
    Sep 2020
    Posts
    20
    Quote Originally Posted by Structure View Post
    you could also return 2 if they are are not the same length.
    This way you can find out if you have trailing bytes at the end or beginning.

    Code:
    int compare( char *string1, char *string2 ) { 
       
        if ( strlen(string1) != strlen(string2) ) {
            return 2;
        }
    
        for (int i=0; i<strlen(string1); i++) {
            if ( string1[i] != string2[i] ) {
                return 0;
            }
        }
    
        return 1;
    }

    Hmm okay, sorry first of all, sorry for not completely understanding.
    I've tried this, but no results (can't compile it either), must be wrong on my side.

    This is what I first of all declare, before my setup etc.
    I've added the 'char situationOne...' to test your suggestion.
    The compiler get's stuck now on that line
    Error message: invalid conversion from const char to char [-fpermissive]



    Code:
    /* TABLE VARIABLES */
    char tableID;
    char situationOne = "_available";
    /* END */
    Then I've added this to my loop:
    Code:
    int compare (char tableID, char situationOne){
          
            
            if (strlen(tableID) != strlen(situationOne)){
              return  0;
            }
            for (int i=0; i<strlen(tableID) i++) {
              if (tableID[i] != situationOne[i]){
                return 0;
              }
            }
            return 1;
          }
    
    
          int main( int argc, char *argv[] ){
            printf( "IsMatch?: %i", compare(tableID, situationOne));
          }
    I'm not sure where to put it since it has to react to the incoming udp packet(packetBuffer)

  8. #8
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338
    Code:
    char situationOne = "_available";
    "without goto we would be wtf'd"

  9. #9
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338
    it's expecting a char and you are trying to set it to a string of chars.
    That's why i added the pointer *.

    Code:
    char *situationOne = "_available";
    same for the function, change char to char *

    I've added this to my loop

    oof
    "without goto we would be wtf'd"

  10. #10
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338
    add this as a function above main()

    Code:
    int compare( char *string1, char *string2 ) { 
    
        if ( strlen(string1) != strlen(string2) ) {
            return 2;
        }
    
        for (int i=0; i<strlen(string1); i++) {
            if ( string1[i] != string2[i] ) {
                return 0;
            }
        }
    
        return 1;
    }
    then do the comparison in the loop:
    Code:
    int cmpResult = compare( tableID, situationOne );
    cmpResult should equal 0-2 depending on the two strings.

    you will also need to:
    Code:
    #include <string.h>
    Last edited by Structure; 09-11-2020 at 08:47 AM.
    "without goto we would be wtf'd"

  11. #11
    Registered User
    Join Date
    Sep 2020
    Posts
    20
    Nope, I still receive errors. Now it can't connect to Serial device.
    I've unplugged it and such, but no luck.

    Here is my more complete code, maybe it will clear things up.

    Once again, apologies and thanks for helping me

    Code:
    #include <SPI.h>
    #include <ESP8266WiFi.h>
    #include <WiFiUdp.h>
    #include <FastLED.h>
    #include <EEPROM.h>
    #include <string.h>
    
    
    #include "secret.h"
    
    
    #define LED_PIN     6
    #define COLOR_ORDER GRB
    #define CHIPSET     WS2812B
    #define NUM_LEDS    3
    CRGB leds[NUM_LEDS];
    
    
    /* MAIN SERVER CONFIG */
    IPAddress destinationIP (10, 168, 1, 100);
    unsigned int destinationPort = 9101;
    /* END */
    
    
    /* TABLE VARIABLES */
    char *tableID = "string one";
    char *situationOne = "string one";
    
    
    /*
    char tableID;
    char situationOne = "_available";
    */
    int address = 215;
    /* END */
    
    
    ADC_MODE(ADC_VCC);
    
    
    int status = WL_IDLE_STATUS;
    
    
    /* BOOLEANS */
    bool candleAllowance = false;
    bool connectionLive = false;
    bool dark = false;
    bool light = false;
    bool stateIdle = false;
    bool stateAvailable = false;
    bool stateOrdered = false;
    bool stateOff = true;
    /* END */
    
    
    /* LIGHT SENSOR */
    int lightSensor;
    long makingSureItIsDark = 0;
    long makingSureItIsLight = 0;
    
    
    int sensorState = LOW;
    unsigned long last_time = 0L ;
    unsigned long intervalSensor = 10000;
    /* END */
    
    
    /* BLINK LED VARIABLES */
    const int ledPin =  LED_BUILTIN;// the tableID of the LED pin
    int ledState = HIGH;             // ledState used to set the LED
    unsigned long previousMillis = 0;        // will store last time LED was updated
    unsigned long interval = 5000;           // interval at which to blink (milliseconds)
    /* END */
    
    
    /* WiFi TESTER VARIABLES */
    unsigned long startTime;
    unsigned long comparisonTime = 0;
    /* END */
    
    
    /* STATES */  /*
      struct state {
      strcpy (state, "_available");
      strcpy (state, "_idle");
      strcpy (state, "_ordered");
      strcpy (state, "_off");
      strcpy (state, "_ping");
      };
      /* END */
    
    
    ///////please enter your sensitive data in the Secret tab/arduino_secrets.h
    char ssid[] = SECRET_SSID;        // your network SSID (name)
    char pass[] = SECRET_PASS;    // your network password (use for WPA, or use as key for WEP)
    int keyIndex = 0;            // your network key Index tableID (needed only for WEP)
    
    
    unsigned int localPort = 1821;      // local port to listen on
    
    
    char packetBuffer[256]; //buffer to hold incoming packet
    //char  ReplyBuffer[] = "table 01: acknowledged";       // a string to send back
    
    
    WiFiUDP Udp;
    
    
    void setup() {
    
    
      pinMode(ledPin, OUTPUT);
      FastLED.addLeds<CHIPSET, LED_PIN, COLOR_ORDER>(leds, NUM_LEDS);
      FastLED.clear(true);
      // FastLED.setBrightness( BRIGHTNESS );
    
    
      //Initialize serial and wait for port to open:
      Serial.begin(115200);
      delay(100);
    
    
    
    
    
    
    
    
    
    
    
    
    
    
      
        int compare( char *string1, char *string2 ) { 
    
    
        if ( strlen(string1) != strlen(string2) ) {
            return 2;
        }
    
    
        for (int i=0; i<strlen(string1); i++) {
            if ( string1[i] != string2[i] ) {
                return 0;
            }
        }
    
    
        return 1;
    }
    
    
    
    
    
    
    
    
      
      Serial.println();
      delay(500);
      Serial.println(" ***** NEW SESSION STARTED ***** ");
      delay (500);
      Serial.println("THE BULB. terraslamp -- V01 2020");
      Serial.println("Setting up network now, hold your drinks high..!");
      Serial.println();
      delay(100);
      Serial.print("MAC: ");
      Serial.println(WiFi.macAddress());
      delay(100);
      WiFi.mode(WIFI_STA);
      Serial.print("Connecting");
      WiFi.begin(ssid, pass);
      //WiFi.config(staticIP, gateway, subnet);
    
    
      // attempt to connect to Wifi network:
      while (WiFi.status() != WL_CONNECTED) {
        Serial.print(".");
    
    
        // Connect to WPA/WPA2 network. Change this line if using open or WEP network:
        //status = WiFi.begin(ssid, pass);
    
    
        // wait 10 seconds for connection:  **updated later to 1s -- so far no issues to report.
        delay(1000);
      }
    
    
      Serial.println("Yes! We are connected to WiFi! Cheers all!");
      Serial.println("Connection info:");
      connectionLive = true;  
      printWifiStatus();
      Serial.printf("UDP server on port %d\n", localPort);
      Serial.println();
      Serial.println("Almost there, finalizing boot process.. Setting Table ID...");
    
    
      //Serial.println("\nStarting connection to server...");
      // if you get a connection, report back via serial:
      Udp.begin(localPort);
    
    
      stateOff = false;
      stateAvailable = true;
    
    
      EEPROM.begin(512);
    
    
      delay(250);
      tableID = EEPROM.read(address);
    
    
      if (tableID <= 001) {
        Serial.println("New device, no table ID is set");
        Udp.beginPacket(destinationIP, destinationPort);
        String ip = WiFi.localIP().toString();
        String text = " : No table ID is set.";
        String toSend = ip + text;
        Udp.print(toSend);
        Udp.endPacket();
      }
      else {
        Udp.beginPacket(destinationIP, destinationPort);
        String text1 = "Table number ";
        String text2 = " is ONLINE";
        String toSend = text1 + tableID + text2;
        Udp.print(toSend);
        Udp.endPacket();
        Serial.println(toSend);
      }
        delay(250);
        Serial.println("Device is ready to use!");
    }
    
    
    void loop() {
    
    
    
    
      connectionStatus();   //CHECK CONNECTION EVERY 10S
      startTime = millis();
      if ((startTime - comparisonTime) > 10000) //every 10s
      {
        comparisonTime = startTime;
        TestWiFiConnection(); //test connection, and reconnect if necessary
      }
      // END
    
    
      if (connectionLive == true) {
    
    
    
    
        if (dark == false) {
          checkSensorDark();
        }
    
    
        if (dark == true) {
          checkSensorLight();
        }
    
    
        // Read packet 
        int packetSize = Udp.parsePacket();
        if (packetSize) {
          Serial.print("Received packet of size ");
          Serial.println(packetSize);
          Serial.print("From ");
          IPAddress remoteIp = Udp.remoteIP();
          Serial.print(remoteIp);
          Serial.print(", port ");
          Serial.println(destinationPort);
    
    
          // Place it in buffer
          int len = Udp.read(packetBuffer, 255);
          if (len > 0) {
            packetBuffer[len] = 0;
          }
          Serial.print("Command: ");
          Serial.print(packetBuffer);
          Serial.println();
          Serial.println("--END--");
    
    
          int cmpResult = compare( tableID, situationOne );}
          
          //if (packetBuffer, strcat(str1, str2)){  //  !strcmp(packetBuffer, "101_available")); 
            //modeAvailable();
            //}
          //}
          else if (strstr(packetBuffer, tableID +  "_ordered")) {
            modeOrdered();
          }
          else if (strcmp(packetBuffer, "{0}_idle")) {
            if(packetBuffer == tableID + "_idle"){
            modeIdle();
            }
          }
          else if (!strcmp(packetBuffer, "all_off")) {   //ORIGINAL FUNCTIONING CODE
            modeOff();
          }
          else if (strstr(packetBuffer, tableID +  "_off")== packetBuffer) {
            modeOff();
          }
          else if (strstr(packetBuffer, tableID +  "_ping")== packetBuffer) {
            Udp.beginPacket(Udp.remoteIP(), destinationPort);
            Udp.write("01 PING");
            Udp.endPacket();
          }
          else if (strstr(packetBuffer, tableID +  "_tableStatus")== packetBuffer) {
            tableStatus();
          }
          else if (strstr(packetBuffer, tableID + "_lightSensor")== packetBuffer) {
            lightStatus();
          }
          else if ( !strcmp(packetBuffer, "tableID")) {
            Serial.print("You have requested the table ID: ");
            Serial.println(tableID); 
            Serial.println("If table ID resulted in 0, please assign the device to a table number."); 
            
            Udp.beginPacket(Udp.remoteIP(), destinationPort);
            String ip = WiFi.localIP().toString();
            String text = " : is the IP, the table ID is: "; 
            String toSend = ip + text + tableID;
            Udp.print(toSend);
            Udp.endPacket();
          }
    
    
          else  {
            Serial.println("Captured a message.. Don't know what to do with it. ");
          }
          /*
              HERE SHOULD COME SOME LINES THAT WILL MEASURE THE BATTERY VOLTAGE
              IF THE BATTERY IS RUNNING LOW THEN RUN:
              also see notes
    
    
              run this void: lowBattery();
          */
          FastLED.show();
    
    
          if (sensorState == HIGH) {
            //lightSensor = analogRead(A0);
          }
        }
      }
    }

  12. #12
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338
    ok, this is what i would do... compile this as a seperate program and take a look at it... give me a min.
    "without goto we would be wtf'd"

  13. #13
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338

    Post

    Code:
    #include <stdio.h>
    #include <string.h>
    
    const char *isAvailable = "_available";
    const char *notAvailable = "_disabled";
    
    char tables[10][32];
    
    void enableTable( int table ) {
        strcpy( tables[table], isAvailable );
    }
    void disableTable( int table ) {
        strcpy( tables[table], notAvailable );
    }
    void printTables() {
        for (int i=0; i<10; i++) {
            printf( "{%i}%s \n", i, tables[i] );
        }
    }
    
    int main( int argc, char *argv[] ) {
    
        enableTable( 4 );
        disableTable( 3 );
    
        printTables();
    
        return 0;
    
    }
    "without goto we would be wtf'd"

  14. #14
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338
    I'm looking at your code...

    go back to what you had i have a better idea of what you are trying to do.
    "without goto we would be wtf'd"

  15. #15
    null pointer Structure's Avatar
    Join Date
    May 2019
    Posts
    338
    Where you commented out the comparison, print out the buffer to the console to see what it actually recieves.
    "without goto we would be wtf'd"

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Constructing a Wake On Lan packet (low level packet)
    By kaptsea in forum C++ Programming
    Replies: 3
    Last Post: 01-28-2020, 07:43 AM
  2. Replies: 1
    Last Post: 11-30-2018, 12:41 AM
  3. Incoming phone call program for C++
    By HARLEY78 in forum C++ Programming
    Replies: 4
    Last Post: 02-18-2010, 05:28 AM
  4. Best way to handle incoming commands from a client.
    By ~Kyo~ in forum Game Programming
    Replies: 6
    Last Post: 07-26-2006, 12:24 PM
  5. changing incoming port for firefox
    By digitaltsai in forum Tech Board
    Replies: 1
    Last Post: 05-05-2006, 09:58 AM

Tags for this Thread