0

I'm writing file save and load functions for a specific file format that I have no control over and the format specifies that at a specific byte position I must write 4 bytes of data to signify a 32bit unsigned value... in my test file this value is 16052, or 0x00003EB4... so I write to the data to the byte array that will be saved in this manner:

data[index] = 0xB4;
data[index+1] = 0x3E;
data[index+2] = 0x00;
data[index+3] = 0x00;

You can see the data is in little-endian format, which is correct... the problem is when I try to load this data with my file load function java sees the data in as such:

-76, 62, 0, 0

the 0xB4 value is being interpreted as -76 because bytes are signed in java... when I try to recompose these 4 bytes into a single 32bit value using the following code the value ends up as -76...

value = data[index+3];
value <<= 8;
value |= data[index+2];
value <<= 8;
value |= data[index+1];
value <<= 8;
value |= data[index];

What this should do is the following: set value to 0x00 (high order byte), shift left 8 bits, or 0x00 onto the lower 8 bits, shift left 8 bits, or 0x3E onto the lower 8 bits, shift left 8 bits, or 0xB4 (low order byte) onto the lower 8 bits.

This should produce the value 0x00003EB4... which is what I started with... however for some reason I cannot figure out it is giving me the value -76 after that operation.

I am convinced this is due to java's interpretation of the 0xB4 byte as the value -76 which is screwing up the bitwise OR operation...

My question is what must I do to get around this?

Thank you.

CHollman82
  • 576
  • 1
  • 8
  • 28
  • possible duplicate of [What is the best way to work around the fact that ALL Java bytes are signed?](http://stackoverflow.com/questions/11088/what-is-the-best-way-to-work-around-the-fact-that-all-java-bytes-are-signed) – Evan Mulawski Jun 26 '12 at 18:24
  • Further info, if I put a break point on the final operation in recomposing the value (value |= data[index];) I see that the value of the "value" variable is 15872, which is 0x00003E00... which is correct and exactly what I expected. The final operation, that I have my breakpoint set on, should bitwise OR the value 0xB4 onto the low order byte of that value... but it is not doing that. After I step once to execute that last operation the value of the "value" variable is -76, that is the problem. – CHollman82 Jun 26 '12 at 18:29

1 Answers1

3

When you are loading the bytes, they are signed. When they are coerced to integers, they are sign extended. To solve this problem, you can do a bitwise AND with 0xFF to take only the 8 LSbs of the signed integer.

In your case value |= (data[index+i]) should become value |= (data[index+i] & 0xFF) (where i is replaced with the index offsets that you have).

RedGreasel
  • 481
  • 2
  • 6