user2298995
user2298995

Reputation: 2163

Binary data not represented by 1's and 0's in PHP

Let's assume the following hex string: c3b5394f6ea32eb9339ab3f9dd971f85. Using the function hex2bin I receive an error that the hex string must be an even length, so first of all, why is that?

Second, even if I remove the last character, instead of receiving a binary represented by 0's and 1's, I these characters: ��(sl˥�m��. How can I convert it to 0's and 1's? And why can't I convert an odd length hex string to binary?

Upvotes: 5

Views: 2196

Answers (1)

Nigel Ren
Nigel Ren

Reputation: 57131

There are a few problems with what your trying to do.

Firstly, according to the manual for hex2bin (http://php.net/manual/en/function.hex2bin.php) ...

Caution This function does NOT convert a hexadecimal number to a binary number. This can be done using the base_convert() function.

So your trying to use it for something it doesn't do - admittedly, I think this may be seen as a bad naming convention in PHP. Nothing new there.

Secondly - this is expecting to convert the string to a number and a hex string of 'c3b5394f6ea32eb9339ab3f9dd971f85' has way to many digits to be represented as a numeric value (consider that each char gives 4 bits of value).

Following the hint in the manual, If you use some smaller examples - this is what you can get...

echo  hex2bin('71f8').PHP_EOL;
echo base_convert ('71f8' , 16 , 2 ).PHP_EOL;
echo decbin(12);

gives...

q�
111000111111000
1100

As for having to have an even number of chars. As most systems use 2 hex chars to represent a single ascii char, this means it can't use an odd char to do the conversion, so it gives a warning and ignores the last char.

Update:

To convert large numbers, you can write a simple function to convert each char at a time and build up the result as a string...

function strToBin ( $number )    {
    $result = '';
    for ( $i = 0; $i < strlen($number); $i++ ){
        $conv = base_convert($number[$i], 16, 2);
        $result .= str_pad($conv, 4, '0', STR_PAD_LEFT);
    }
    return $result;
}
echo strToBin('d288a775eba4132a982701fa625c9b820').PHP_EOL;
echo '110100101000100010100111011101011110101110100100000100110010101010011000001001110000000111111010011000100101110010011011100000100000';

(The second output is the result from using the conversion page you indicate to check that the result is working.)

Outputs...

110100101000100010100111011101011110101110100100000100110010101010011000001001110000000111111010011000100101110010011011100000100000
110100101000100010100111011101011110101110100100000100110010101010011000001001110000000111111010011000100101110010011011100000100000

Upvotes: 9

Related Questions