Understand Hex values from string

Hello!

I’m making a WiFi temperature controller using ESP8266 and some DS18B20 sensors.

Part of the code is a webserver, used for OTA configuration and OTA update of the controller.

At some point, the user will fill the form using his browser, the info wil be read and stored to eeprom. Doing that the networking information and the DS18B20 adresses don’t have to be hardcoded to the arduino.

The problem is that DS18B20 adresses will be received by the arduino on the following format:

String probe1_adr = "0x28:0xC2:0x9C:0x69:0x27:0x19:0x01:0x94";

I tokenize the string using strtok:

String probe1_adr = "0x28:0xC2:0x9C:0x69:0x27:0x19:0x01:0x94";
char *probe1_adr_c [8];
int probe1_len = probe1_adr.length() + 1;
char probe1array[probe1_len];
probe1_adr.toCharArray(probe1array, probe1_len);
char *ptr1 = NULL;
byte index1 = 0;
ptr1 = strtok(probe1array, ":");
while(ptr1 != NULL){
   probe1_adr_c[index]= ptr1;
   index++;
   ptr1 = strtok(NULL, ":");
}

The result is an array containing every hex value read on the original string, but still on the string format:

probe1_adr_c[0]= "0x28";
probe1_adr_c[1]= "0xC2";
probe1_adr_c[2]= "0x9C";
probe1_adr_c[3]= "0x69";
probe1_adr_c[4]= "0x27";
probe1_adr_c[5]= "0x19";
probe1_adr_c[6]= "0x01";
probe1_adr_c[7]= "0x94";

How do I translate those hex values to a uint8_t array, like the one below?

uint8_t probe_ferm_uint8[8] =   { 0x28, 0xC2, 0x9C, 0x69, 0x27, 0x19, 0x01, 0x94 };

Why don't you just let the ESP8266 discover the DS18B20s addresses by interrogating them over the OneWire bus?

gfvalvo:
Why don’t you just let the ESP8266 discover the DS18B20s addresses by interrogating them over the OneWire bus?

I’d like to be able to assign a defined order for the sensors(I’ll have up to 3 sensors conected).

On a first case it’d not matter much:

uint8_t probe1[8] =   { 0x28, 0xC2, 0x9C, 0x69, 0x27, 0x19, 0x01, 0x94 };
uint8_t probe2[8] = { 0x28, 0x45, 0xA7, 0x70, 0x27, 0x19, 0x01, 0xA4 };
uint8_t probe3[8] =  { 0x28, 0xDD, 0x51, 0x67, 0x27, 0x19, 0x01, 0x30 };

But at some point I may have to change their assignments, swapping 1 and 2, for example:

uint8_t probe1[8] =   { 0x28, 0x45, 0xA7, 0x70, 0x27, 0x19, 0x01, 0xA4 };
uint8_t probe2[8] = { 0x28, 0xC2, 0x9C, 0x69, 0x27, 0x19, 0x01, 0x94 };
uint8_t probe3[8] =  { 0x28, 0xDD, 0x51, 0x67, 0x27, 0x19, 0x01, 0x30 };

You could use strtol to convert the hex string into an integer?

lhtrevisan:
I'd like to be able to assign a defined order for the sensors(I'll have up to 3 sensors conected).

Simple to do programmatically. You're trying to do things the hard way.

The DS18B20 addresses are fixed. Once you choose a specific device and connected, that's it. Nothing that comes over from a Web Browser is going to change that.

But, it's your project.

‘strtol()’ strtol - C++ Reference

You don’t even have to use strtok() first since strtol() can return a pointer to the character after the number. And if you pass the radix ‘0’, strtol() will interpret the ‘0x’ prefix so you can use decimal, octal, binary, or hex.

Something like this:

void str2addr(const char *str, byte addr[8])
{
  char *ptrEnd = (char *)str;
  for (int i = 0; i < 8; i++)
  {
    addr[i] = strtol(ptrEnd, &ptrEnd, 0);  // Interpret one number and point after it
    ptrEnd++; // Skip the ':' between numbers
  }
}


// Example sketch showing how to use the function:
void setup()
{
  Serial.begin(115200);
  delay(200);
  Serial.println();


  byte address[8];


  str2addr("0x28:0xC2:0x9C:0x69:0x27:0x19:0x01:0x94", address);


  for (int i = 0; i < 8; i++)
  {
    Serial.print(address[i], HEX);
    Serial.print(':');
  }
  Serial.println();
}


void loop() {}