I have to deserialize some binary messages coming from another application. I would love to use restruct.io but some fields in the message structure use a "non-standard" number of bits ( 5 bits, 3 bits, ... 10 bits ... ).
Is there any way to handle this type of structs? I have been searching for some time without any success so any help will be very welcomed.
thanks in advance
I wil try to give an example to clarify my question. Given the code:
package main
import (
"encoding/binary"
"fmt"
restruct "gopkg.in/restruct.v1"
)
type MessageType uint8
const (
MessageTypeOne MessageType = iota + 1
MessageTypeTwo
MessageTypeThree
)
// Message is the data to deserialize from the binary stream
type Message struct {
Length uint32 `struct:"uint32"` // message size in bytes (including length)
Type MessageType `struct:"uint8"`
Version uint8 `struct:"uint8:4"` // Just need 4 bits
Subversion uint8 `struct:"uint8:2"` // just need 2 bits
Optional uint8 `struct:"uint8:1"` // just one bit --> '1' means next field is NOT present
NodeName string ``
ANumber uint16 `struct:"uint16:10"` // just need 10 bits
}
// (length(4)+type(1)+(version(4bits)+Subversion(2bits)+Optional(1bit))) = 6 bytes
// need 32bit alignment
func main() {
var inStream = []byte{0x08, // just 8 bytes needed
0x01, // messge type = MessageTypeOne
0x4a, // Version=0100 Subversion=10 Optional=1 ANumber = 0 (MSB bit)
0x00, 0x60, // ANumber(000 0000 011) Padding = 0 0000 for 32 bits alignment
}
var msg Message
err := restruct.Unpack(inStream, binary.BigEndian, &msg)
if err != nil {
panic(err)
}
fmt.Println(msg)
// Expected:
// msg.Length = 8
// msg.Type = 1
// msg.Version = 4
// msg.Subversion = 2
// msg.Optional = 1
// msg.NodeName = ""
// msg.ANumber = 3
}
I will receive inStream from a TCP connection and will want to deserialize the binary data and get a Message struct with the expected values ...
Hope this will clarify my question.
Thanks again ;)