blob: 41e50e04a9dca4a3cffbbb3623f3486e87e1ab7b (
about) (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
|
package pktline
import "fmt"
func hexval(b byte) int {
switch {
case b >= '0' && b <= '9':
return int(b - '0')
case b >= 'a' && b <= 'f':
return int(b-'a') + 10
case b >= 'A' && b <= 'F':
return int(b-'A') + 10
default:
return -1
}
}
// ParseLengthHeader parses a 4-byte hexadecimal pkt-line length header.
//
// The returned value is the full on-wire packet size, including the 4-byte
// header. Semantic interpretation (data/control/error) is done by Decoder.
//
// The 4-byte header is only an actual length when above or equal to 4.
// Otherwise, it indicates some control packet.
func ParseLengthHeader(h [4]byte) (int, error) {
a := hexval(h[0])
b := hexval(h[1])
c := hexval(h[2])
d := hexval(h[3])
if a < 0 || b < 0 || c < 0 || d < 0 {
return 0, fmt.Errorf("%w: %q", ErrInvalidLength, string(h[:]))
}
return (a << 12) | (b << 8) | (c << 4) | d, nil
}
// EncodeLengthHeader encodes n as a 4-byte hexadecimal pkt-line header.
//
// n is the full on-wire packet size including the 4-byte header.
//
// The 4-byte header is only an actual length when above or equal to 4.
// Otherwise, it indicates some control packet.
func EncodeLengthHeader(dst *[4]byte, n int) error {
if n < 0 || n > LargePacketMax {
return fmt.Errorf("%w: %d", ErrInvalidLength, n)
}
const hex = "0123456789abcdef"
dst[0] = hex[(n>>12)&0xf]
dst[1] = hex[(n>>8)&0xf]
dst[2] = hex[(n>>4)&0xf]
dst[3] = hex[n&0xf]
return nil
}
|