This repository has been archived by the owner on Nov 21, 2023. It is now read-only.
/
docsismanagementlayer.go
103 lines (83 loc) · 3.19 KB
/
docsismanagementlayer.go
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
package main
import (
"encoding/binary"
"fmt"
"net"
"github.com/google/gopacket"
"github.com/google/gopacket/layers"
)
// LayerTypeDOCSISManagement type registration
var LayerTypeDOCSISManagement = gopacket.RegisterLayerType(1002, gopacket.LayerTypeMetadata{Name: "DOCSIS Management", Decoder: gopacket.DecodeFunc(decodeDOCSISManagement)})
// DocsisManagementRegRsp code for DOCSIS Management Registration Response
const DocsisManagementRegRsp = 7
// DocsisManagementBpkmRsp code for Baseline Privacy Key Management Response
const DocsisManagementBpkmRsp = 13
// DocsisManagementRegRspMp code for DOCSIS Management Multipart Registration Response
const DocsisManagementRegRspMp = 45
// DOCSISManagement is a DOCSIS Management packet header.
type DOCSISManagement struct {
layers.BaseLayer
SrcMAC, DstMAC net.HardwareAddr
MessageLength uint16
DSAP byte
SSAP byte
Control byte
Version byte
Type byte
Reserved byte
}
// LayerType returns LayerTypeDOCSISManagement
func (docsisManagement *DOCSISManagement) LayerType() gopacket.LayerType {
return LayerTypeDOCSISManagement
}
// DecodeFromBytes decodes the given bytes into this layer.
func (docsisManagement *DOCSISManagement) DecodeFromBytes(data []byte, df gopacket.DecodeFeedback) error {
if len(data) < 20 {
return fmt.Errorf("docsis management packet is too small for the header")
}
docsisManagement.DstMAC = net.HardwareAddr(data[0:6])
docsisManagement.SrcMAC = net.HardwareAddr(data[6:12])
docsisManagement.MessageLength = binary.BigEndian.Uint16(data[12:14])
docsisManagement.DSAP = data[14]
docsisManagement.SSAP = data[15]
docsisManagement.Control = data[16]
docsisManagement.Version = data[17]
docsisManagement.Type = data[18]
docsisManagement.Reserved = data[19]
payloadStart := 20
// len(DstMAC) + len(SrcMAC) + len(MessageLength) + MessageLength
payloadEnd := int(6 + 6 + 2 + docsisManagement.MessageLength)
if payloadEnd < payloadStart {
return fmt.Errorf("docsis management packet message length header is too small")
}
if len(data) < payloadEnd {
return fmt.Errorf("docsis management packet is too small for the payload")
}
docsisManagement.Contents = data[:payloadStart]
docsisManagement.Payload = data[payloadStart:payloadEnd]
return nil
}
// CanDecode returns the set of layer types that this DecodingLayer can decode.
func (docsisManagement *DOCSISManagement) CanDecode() gopacket.LayerClass {
return LayerTypeDOCSISManagement
}
// NextLayerType returns the layer type contained by this DecodingLayer.
func (docsisManagement *DOCSISManagement) NextLayerType() gopacket.LayerType {
if docsisManagement.Type == DocsisManagementRegRsp {
return LayerTypeDOCSISRegRsp
} else if docsisManagement.Type == DocsisManagementBpkmRsp {
return LayerTypeDOCSISBpkmRsp
} else if docsisManagement.Type == DocsisManagementRegRspMp {
return LayerTypeDOCSISRegRspMp
}
return gopacket.LayerTypePayload
}
func decodeDOCSISManagement(data []byte, p gopacket.PacketBuilder) error {
docsisManagement := &DOCSISManagement{}
err := docsisManagement.DecodeFromBytes(data, p)
if err != nil {
return err
}
p.AddLayer(docsisManagement)
return p.NextDecoder(docsisManagement.NextLayerType())
}