I need a function to convert a 32bit or 24bit signed (in two’s complement) hexadecimal string into a long int. Needs to work on both 32bit and 64bit machines (regardless of the size of long int) and work regardless of whether the machine is a two’s complement machine or not.
SOLUTION:
long int hex2li (char hexStr[], int signedHex)
{
int bits = strlen (hexStr) * 4;
char *pEnd;
long long int result = strtoll (hexStr, &pEnd, 16);
if (pEnd[0] == '\0')
{
if (signedHex)
{
if (result >= (1LL << (bits - 1))) result -= (1LL << bits);
}
return (long int) result;
}
return LONG_MIN;
}
For a 24-bit string:
When you parse the hex string, the standard
strtolfunction will read it as an unsigned value in the range0 -> 2^24 - 1.The range
0 -> 2^23 - 1is correct, but the range2^23 -> 2^24 - 1needs to be mapped to-2^23 -> -1which is a simple subtraction which can be performed as follows.To convert a 32-bit string using the same technique you have to use an intermediate type that can represent a full 32-bit unsigned integer in a signed type for performing the subtraction. A
long long intis guaranteed to be 64-bits so you can use this.E.g.