How I can parse a string to a hex array

In my arduino I receive a string for example:
FFF1C9S0F9
I need to pass it to a byte array and make it:
byte start[] = {0xFF, 0xF1, 0xC9, 0xS0, 0xF9}
For when you have it in this way, you can print it by serial with the correct hexadecimal data format.
Is there any way to do this?

Are you saving the incoming data as a String (uppercase S, an object of the String library) or as a string (lowercase s, a zero terminated array of chars) ?

Why do you think that you need to save the data to an array of bytes if all you want to do is print it ?

Please post your sketch, using code tags when you do

What numeric value would you imagine corresponds to "0xS0"???

Sure.
The exact way how to do it, may vary of course.

Just to have it clear:
You expect to receive 10 (ten) characters, in the range '0' .. '9' or 'A .. 'F', never any other character
You're sure not to miss any input because your sketch isn't listening currently or ever get more than 10 characters ?
no spaces, no end of line characters or other garbage. Like the character 'S' or 'O'
If the value of one of the 5 bytes is less than 0x10, a leading '0' will be sent?

Decoding is trivial: If you receive a '0', you have to subtract '0' and the result is 0.
If you receive a '1', you have to subtract '0' and the result is 1.
etc.
However, there are some codes between '9' and 'A' , so in case the result of subtracting '0' results in more than 9, you have to get the proper result of 0xa ... 0xf
Best look up a code table and see that '0' equals 0x30 or 48 (decimal) and 'A' equals 0x41 or 65 (decimal)

BTW: I hope you got the difference between the character '0' and 0.
Have fun.

No need to lookup anything:

inchar = toupper(inchar);
if (inchar >= '0' && inchar <= '9')
    outval = (outval * 10) + (inchar - '0')
else if (inchar >= 'A' && inchar <= 'F')
    outval = (outval * 10) + (inchar - 'A' + 10);
else
   Serial.println("Invalid character received");

its only an example, not its the real data

Example of what? You asked to "parse a string to a hex array". How do you want "S0" to be parsed?

You missed his point, that's how you convert each character to it's hex value. What you do after that...

If you already have HEX data as a string, why would you want to convert it to binary in order to convert it back to HEX?

Should that not be times 16?

You could let strtol do the conversions for you:

void strToBin(byte bin[], char const str[]) {
  for (size_t i = 0; str[i] and str[i + 1]; i += 2) {
    char slice[] = {0, 0, 0};
    strncpy(slice, str + i, 2);
    bin[i / 2] = strtol(slice, nullptr, 16);
  }
}

Usage:

char const str[] = "FFF1C950F9";

byte bin[5];  // Maximum length of `str` divided by two.
strToBin(bin, str);
// `bin` now contains 0xff, 0xf1, 0xc9, 0x50 and 0xf9.

Both upper and lower case letters are supported.

Note that when the length of str is not even, the last character is discarded. Also note that str[i] and str[i + 1] looks like it can result in an out of bounds access, but short-circuit evaluation makes sure that this does not happen.

1 Like

Please answer the questions

@jfjlaros thank you very much for your contribution, it was the correct solution to what was breaking my head :sweat_smile: :smiley:

what a waste of bandwidth sending twice the bytes

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