I have a buffer :
buffer := bytes.NewBuffer([]byte{
0x85, 0x02, 0xFF, 0xFF,
0x00, 0x01, 0x00, 0x02,
0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x01,
0x00, 0x00, 0x00, 0x03,
0x41, 0x42, 0x43,
})
I am trying to return the int value of buffer[8:24] I get
[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1]
Not sure how to shift such a large section. of the byte.
new to this. Any help would be great. my initial approach was
requestid := (uint64(buffer.Bytes()[8]&0xff)<<24 + uint64(buffer.Bytes()[9]&0xff)<<16 + uint64(buffer.Bytes()[10]&0xff)<<8 + uint64(buffer.Bytes()[11]&0xff.....)))
but this got tedious, and I know there has to be an easier way.
You have to do the manual bit shifting and OR'ing, but your code can be cleaned up by removing all those buffer.Bytes()
calls.
You also do not need the &0xff
parts. What n&0xff
does, is clear out all bits outside of the 0-255
range. Since each value in the buffer is already a byte (0-255), these operations do nothing at all. If we want to do 22 & 255
, we get the following:
Hexadecimal | Decimal | Binary
--------------|-------------|----------------------
x 0x16 | 22 | 00010110
y 0xff | 255 | 11111111
--------------|-------------|---------------------- AND (&)
0x16 | 22 | 00010110 = x
As you can see, the operation has no effect at all. Replace x
with any 8-bit value and you will see the same result. The outcome of x & 0xff
is always x
.
Additionally, when you assign to the requestId
, you start by shifting by 24 bits. This tells me you are reading a 32-bit integer. Why then do you continue reading values beyond 32 bits and converting it all to a 64 bit integer?
If you are reading a 64-bit int in Big Endian, try this:
data := buf.Bytes()[8:]
requestid := uint64(data[0])<<56 | uint64(data[1])<<48 |
uint64(data[2])<<40 | uint64(data[3])<<32 |
uint64(data[4])<<24 | uint64(data[5])<<16 |
uint64(data[6])<<8 | uint64(data[7])
If you are reading a 64-bit int in Little Endian, try this:
data := buf.Bytes()[8:]
requestid := uint64(data[7])<<56 | uint64(data[6])<<48 |
uint64(data[5])<<40 | uint64(data[4])<<32 |
uint64(data[3])<<24 | uint64(data[2])<<16 |
uint64(data[1])<<8 | uint64(data[0])
If you are reading a 32-bit int in Big Endian, try this:
data := buf.Bytes()[8:]
requestid := uint32(data[0])<<24 | uint32(data[1])<<16 |
uint32(data[2])<<8 | uint32(data[3])
If you are reading a 32-bit int in Little Endian, try this:
data := buf.Bytes()[8:]
requestid := uint32(data[3])<<24 | uint32(data[2])<<16 |
uint32(data[1])<<8 | uint32(data[0])
Alternatively, you can use the encoding/binary package:
var value uint64
err := binary.Read(buf, binary.LittleEndian, &value)
....