Reading a 32bit integer from Serial port

Hellou, I have come to seek help with a problem I have been experiencing.
Currently, I am trying to send a 32bit Integer from an Arduino Mega 2560 to an Arduino Nano through serial comms. The number that is sent is expected to range from 0 - 99999 (as in five digits for a seven segment display).

Background: I am repurposing an old 7 segment display I found in an old arcade machine. I have code which allows the display to be driven. However, I need a dedicated Arduino to run it in order to get a smooth and flickerless display. So, another Arduino with more pins is running the main sketch and if anything changes to, let's say a highscore, it is sent through serial to the Nano and is then being updated and displayed on repeat without delays.

So far, my biggest concern is just this bit, where I am reading the 32bit Int from serial.
Because a friend recommended it to me, I also asked ChatGPT for help. It did help in creating a few approaches and fixing minor bugs, but in the end it was still not working.
This means I have no working code yet, sadly. And this is why I am asking here if anyone knows an alternative and definitive way of catching this number to display it.
The function which changes the displayed number requires a uint32_t input.

Right now, when the Nano receives a number higher than 32767 it is causing an overflow and returns just that. I know it's ther "toInt()". It's just that I have not found a solution for it.

int lastValue = 0; // Saves the last value

void setup() {
  Serial.begin(115200); // Initialize serial communication
  Serial.println("Hello!");
}

void loop() {
  if (Serial.available()) { // Check if at least 1 character is available
    String inputString = Serial.readStringUntil('\n'); // Read the string until the '\n' delimiter

    if (inputString.length() >= 1 && inputString.length() < 7) { // Check the length of the input string
      long newValue = inputString.toInt(); // Convert the string to an integer

      if (newValue != 0 && newValue != lastValue) { // Check if the new value is valid and not equal to the last value
        lastValue = newValue; // Update the last captured value
        Serial.print("Neuer Wert: ");
        Serial.println(lastValue); // Print the new value on the serial monitor

        // this is where i would tell the LED display to update itself
      }
    }
  }
  delay(5);
}

For testing purposes, I have a Mega 2560 set up next to it with a small sketch to constantly supply five digit numbers. It is connected via Serial1 (RX1 and TX1) to the RX and TX of the Nano.

uint32_t num = 99900;

void setup() {
  Serial.begin(115200);
  Serial1.begin(115200);
  Serial.println("Hello!");
}

void loop() {
  if(num >=99999){
    num = 99900;
  }else{
    num++;
  }
  Serial1.println(num);
  Serial.println(num);
  delay(1000);
}

Please, any help would be greatly appreciated.
Thanks in advance.

Oops.

(It seems that ChatGPT doesn't know a great deal about the AVR)

Receive digits, and add the decimal value to a running total.
Each iteration, multiply the running total by ten before adding in the next digit.

You have a five-digit number in your string. It can easily exceed 32767. Stuffing it in an int conversion is a problem.

  1. process the first character, if it's 1 write 1*10000 to your long int.
  2. replace the first character with ' '(space), then do the conversion as shown, but add the conversion output to your long int.
    Other solutions will be presented, but this will do it if you understand the instructions.

some changes..

long lastValue = 0; // Saves the last value
long newValue = 0;

char buff[80];
int recvd = 0;

void setup() {
  Serial.begin(115200); // Initialize serial communication
  Serial.println("Hello!");
}

void loop() {
  if (Serial.available()) { // Check if at least 1 character is available
    char achar = Serial.read(); // Read the string until the '\n' delimiter
    if (achar != 10)
    {
      buff[recvd] = achar;
      recvd++;
      if (recvd >= sizeof(buff) / sizeof(buff[0])) {
        //too many, drop it all
        recvd = 0;
        memset(buff, 0, sizeof(buff) / sizeof(buff[0]));
      }
    } else {
      //got a newline..
      newValue = atol(buff);
      recvd = 0;
      memset(buff, 0, sizeof(buff) / sizeof(buff[0]));
    }
  }

  if (newValue != 0 && newValue != lastValue) { // Check if the new value is valid and not equal to the last value
    lastValue = newValue; // Update the last captured value
    Serial.print("Neuer Wert: ");
    Serial.println(lastValue); // Print the new value on the serial monitor

    // this is where i would tell the LED display to update itself
  }

}

play it here..

have fun.. ~q

The serial input basics tutorial may be of interest.

This works with Nano, type a number -2147483648 to 2147483647 into Serial Monitor then [ENTER]:

void setup()
{
  Serial.begin(9600); // set Serial Monitor to "Newline"
}
void loop()
{
  static long num = 0;
  if(Serial.available() > 0)
  {
    num = Serial.parseInt();
    if(Serial.read() == '\n') {}; // skip 1 second timeout
    Serial.println(num);
  }  
}

Thank you! I've used your version and my sketch is now finished up.

1 Like

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.