1// Copyright 2012 Google, Inc. All rights reserved.
2//
3// Use of this source code is governed by a BSD-style license
4// that can be found in the LICENSE file in the root of the source
5// tree.
6
7package gopacket
8
9import (
10	"errors"
11)
12
13// DecodeFeedback is used by DecodingLayer layers to provide decoding metadata.
14type DecodeFeedback interface {
15	// SetTruncated should be called if during decoding you notice that a packet
16	// is shorter than internal layer variables (HeaderLength, or the like) say it
17	// should be.  It sets packet.Metadata().Truncated.
18	SetTruncated()
19}
20
21type nilDecodeFeedback struct{}
22
23func (nilDecodeFeedback) SetTruncated() {}
24
25// NilDecodeFeedback implements DecodeFeedback by doing nothing.
26var NilDecodeFeedback DecodeFeedback = nilDecodeFeedback{}
27
28// PacketBuilder is used by layer decoders to store the layers they've decoded,
29// and to defer future decoding via NextDecoder.
30// Typically, the pattern for use is:
31//  func (m *myDecoder) Decode(data []byte, p PacketBuilder) error {
32//    if myLayer, err := myDecodingLogic(data); err != nil {
33//      return err
34//    } else {
35//      p.AddLayer(myLayer)
36//    }
37//    // maybe do this, if myLayer is a LinkLayer
38//    p.SetLinkLayer(myLayer)
39//    return p.NextDecoder(nextDecoder)
40//  }
41type PacketBuilder interface {
42	DecodeFeedback
43	// AddLayer should be called by a decoder immediately upon successful
44	// decoding of a layer.
45	AddLayer(l Layer)
46	// The following functions set the various specific layers in the final
47	// packet.  Note that if many layers call SetX, the first call is kept and all
48	// other calls are ignored.
49	SetLinkLayer(LinkLayer)
50	SetNetworkLayer(NetworkLayer)
51	SetTransportLayer(TransportLayer)
52	SetApplicationLayer(ApplicationLayer)
53	SetErrorLayer(ErrorLayer)
54	// NextDecoder should be called by a decoder when they're done decoding a
55	// packet layer but not done with decoding the entire packet.  The next
56	// decoder will be called to decode the last AddLayer's LayerPayload.
57	// Because of this, NextDecoder must only be called once all other
58	// PacketBuilder calls have been made.  Set*Layer and AddLayer calls after
59	// NextDecoder calls will behave incorrectly.
60	NextDecoder(next Decoder) error
61	// DumpPacketData is used solely for decoding.  If you come across an error
62	// you need to diagnose while processing a packet, call this and your packet's
63	// data will be dumped to stderr so you can create a test.  This should never
64	// be called from a production decoder.
65	DumpPacketData()
66	// DecodeOptions returns the decode options
67	DecodeOptions() *DecodeOptions
68}
69
70// Decoder is an interface for logic to decode a packet layer.  Users may
71// implement a Decoder to handle their own strange packet types, or may use one
72// of the many decoders available in the 'layers' subpackage to decode things
73// for them.
74type Decoder interface {
75	// Decode decodes the bytes of a packet, sending decoded values and other
76	// information to PacketBuilder, and returning an error if unsuccessful.  See
77	// the PacketBuilder documentation for more details.
78	Decode([]byte, PacketBuilder) error
79}
80
81// DecodeFunc wraps a function to make it a Decoder.
82type DecodeFunc func([]byte, PacketBuilder) error
83
84// Decode implements Decoder by calling itself.
85func (d DecodeFunc) Decode(data []byte, p PacketBuilder) error {
86	// function, call thyself.
87	return d(data, p)
88}
89
90// DecodePayload is a Decoder that returns a Payload layer containing all
91// remaining bytes.
92var DecodePayload Decoder = DecodeFunc(decodePayload)
93
94// DecodeUnknown is a Decoder that returns an Unknown layer containing all
95// remaining bytes, useful if you run up against a layer that you're unable to
96// decode yet.  This layer is considered an ErrorLayer.
97var DecodeUnknown Decoder = DecodeFunc(decodeUnknown)
98
99// DecodeFragment is a Decoder that returns a Fragment layer containing all
100// remaining bytes.
101var DecodeFragment Decoder = DecodeFunc(decodeFragment)
102
103// LayerTypeZero is an invalid layer type, but can be used to determine whether
104// layer type has actually been set correctly.
105var LayerTypeZero = RegisterLayerType(0, LayerTypeMetadata{Name: "Unknown", Decoder: DecodeUnknown})
106
107// LayerTypeDecodeFailure is the layer type for the default error layer.
108var LayerTypeDecodeFailure = RegisterLayerType(1, LayerTypeMetadata{Name: "DecodeFailure", Decoder: DecodeUnknown})
109
110// LayerTypePayload is the layer type for a payload that we don't try to decode
111// but treat as a success, IE: an application-level payload.
112var LayerTypePayload = RegisterLayerType(2, LayerTypeMetadata{Name: "Payload", Decoder: DecodePayload})
113
114// LayerTypeFragment is the layer type for a fragment of a layer transported
115// by an underlying layer that supports fragmentation.
116var LayerTypeFragment = RegisterLayerType(3, LayerTypeMetadata{Name: "Fragment", Decoder: DecodeFragment})
117
118// DecodeFailure is a packet layer created if decoding of the packet data failed
119// for some reason.  It implements ErrorLayer.  LayerContents will be the entire
120// set of bytes that failed to parse, and Error will return the reason parsing
121// failed.
122type DecodeFailure struct {
123	data  []byte
124	err   error
125	stack []byte
126}
127
128// Error returns the error encountered during decoding.
129func (d *DecodeFailure) Error() error { return d.err }
130
131// LayerContents implements Layer.
132func (d *DecodeFailure) LayerContents() []byte { return d.data }
133
134// LayerPayload implements Layer.
135func (d *DecodeFailure) LayerPayload() []byte { return nil }
136
137// String implements fmt.Stringer.
138func (d *DecodeFailure) String() string {
139	return "Packet decoding error: " + d.Error().Error()
140}
141
142// Dump implements Dumper.
143func (d *DecodeFailure) Dump() (s string) {
144	if d.stack != nil {
145		s = string(d.stack)
146	}
147	return
148}
149
150// LayerType returns LayerTypeDecodeFailure
151func (d *DecodeFailure) LayerType() LayerType { return LayerTypeDecodeFailure }
152
153// decodeUnknown "decodes" unsupported data types by returning an error.
154// This decoder will thus always return a DecodeFailure layer.
155func decodeUnknown(data []byte, p PacketBuilder) error {
156	return errors.New("Layer type not currently supported")
157}
158