package datastructures import ( "bytes" "errors" "fmt" ) type SignerResponse struct { Version uint8 Action Action Reserved1 uint8 Reserved2 uint8 Content1 string Content2 string Content3 string } func SignerResponseFromData(lengthBytes []byte, blockData []byte, checkSum byte) (*SignerResponse, error) { headerLength := decode24BitLength(lengthBytes) headerBytes := blockData[3 : 3+headerLength] contentBytes := blockData[3+headerLength:] content1Length := decode24BitLength(contentBytes[0:3]) content1 := string(contentBytes[3 : 3+content1Length]) content2Offset := 3 + content1Length content2Length := decode24BitLength(contentBytes[content2Offset : content2Offset+3]) content2 := string(contentBytes[3+content2Offset : 3+content2Offset+content2Length]) content3Offset := 3 + content2Offset + content2Length content3Length := decode24BitLength(contentBytes[content3Offset : content3Offset+3]) content3 := string(contentBytes[3+content3Offset : 3+content3Offset+content3Length]) calculated := CalculateXorCheckSum([][]byte{lengthBytes, blockData}) if checkSum != calculated { return nil, errors.New(fmt.Sprintf("invalid checksum expected 0x%x got 0x%x", calculated, checkSum)) } return &SignerResponse{ Version: headerBytes[0], Action: Action(headerBytes[1]), Reserved1: headerBytes[2], Reserved2: headerBytes[3], Content1: content1, Content2: content2, Content3: content3, }, nil } func (r SignerResponse) Serialize() []byte { headerBytes := []byte{r.Version, byte(r.Action), r.Reserved1, r.Reserved2} content1Bytes := []byte(r.Content1) content2Bytes := []byte(r.Content2) content3Bytes := []byte(r.Content3) blockBytes := bytes.Join([][]byte{ encode24BitLength(headerBytes), headerBytes, encode24BitLength(content1Bytes), content1Bytes, encode24BitLength(content2Bytes), content2Bytes, encode24BitLength(content3Bytes), content3Bytes, }, []byte{}) return bytes.Join([][]byte{encode24BitLength(blockBytes), blockBytes}, []byte{}) }