1
0
mirror of https://github.com/fumiama/aes-rsa-tcp-demo.git synced 2026-06-05 01:20:24 +08:00
Files
aes-rsa-tcp-demo/utils/packet.go
源文雨 f79b275f42 init
2023-12-29 16:29:41 +09:00

78 lines
1.6 KiB
Go

package utils
import (
"encoding/binary"
"errors"
"io"
"math"
)
type PacketType uint8
const (
PacketTypeInit PacketType = iota // PacketTypeInit pass RSA pubkey by AES pre-shared key
PacketTypeComm // PacketTypeComm normal communication
PacketTypeTop // PacketTypeTop for valid checking
)
// Packet is the communicating proxy
type Packet struct {
Len uint16 // Len packet length LE
Typ PacketType // Typ packet type
Dat []byte // Dat payload
}
// ParsePacket from bytes
func ParsePacket(d []byte) (p Packet, err error) {
l := binary.LittleEndian.Uint16(d[:2])
if 2+int(l) != len(d) {
err = errors.New("invalid packet len")
return
}
p.Len = l
p.Typ = PacketType(d[2])
p.Dat = d[3:]
return
}
// ReadPacket from io.Reader
func ReadPacket(r io.Reader) (p Packet, err error) {
var buf [2]byte
_, err = io.ReadFull(r, buf[:])
if err != nil {
return
}
l := binary.LittleEndian.Uint16(buf[:])
data := make([]byte, l)
_, err = io.ReadFull(r, data)
if err != nil {
return
}
p.Len = l
p.Typ = PacketType(data[0])
p.Dat = data[1:]
return
}
// ToBytes marshal packet into bytes
func (p *Packet) ToBytes() ([]byte, error) {
l := 1 + len(p.Dat)
if l > math.MaxUint16 {
return nil, errors.New("packet data too large")
}
if p.Typ >= PacketTypeTop {
return nil, errors.New("invalid packet tpye")
}
p.Len = uint16(l)
return p.MustToBytes(), nil
}
// MustToBytes don't do any check
func (p *Packet) MustToBytes() []byte {
data := make([]byte, 2+1+len(p.Dat))
binary.LittleEndian.PutUint16(data[:2], p.Len)
data[2] = byte(p.Typ)
copy(data[3:], p.Dat)
return data
}