Fix unit tests
[govpp.git] / vendor / github.com / google / gopacket / doc.go
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
7 /*
8 Package gopacket provides packet decoding for the Go language.
9
10 gopacket contains many sub-packages with additional functionality you may find
11 useful, including:
12
13  * layers: You'll probably use this every time.  This contains of the logic
14      built into gopacket for decoding packet protocols.  Note that all example
15      code below assumes that you have imported both gopacket and
16      gopacket/layers.
17  * pcap: C bindings to use libpcap to read packets off the wire.
18  * pfring: C bindings to use PF_RING to read packets off the wire.
19  * afpacket: C bindings for Linux's AF_PACKET to read packets off the wire.
20  * tcpassembly: TCP stream reassembly
21
22 Also, if you're looking to dive right into code, see the examples subdirectory
23 for numerous simple binaries built using gopacket libraries.
24
25 Basic Usage
26
27 gopacket takes in packet data as a []byte and decodes it into a packet with
28 a non-zero number of "layers".  Each layer corresponds to a protocol
29 within the bytes.  Once a packet has been decoded, the layers of the packet
30 can be requested from the packet.
31
32  // Decode a packet
33  packet := gopacket.NewPacket(myPacketData, layers.LayerTypeEthernet, gopacket.Default)
34  // Get the TCP layer from this packet
35  if tcpLayer := packet.Layer(layers.LayerTypeTCP); tcpLayer != nil {
36    fmt.Println("This is a TCP packet!")
37    // Get actual TCP data from this layer
38    tcp, _ := tcpLayer.(*layers.TCP)
39    fmt.Printf("From src port %d to dst port %d\n", tcp.SrcPort, tcp.DstPort)
40  }
41  // Iterate over all layers, printing out each layer type
42  for _, layer := range packet.Layers() {
43    fmt.Println("PACKET LAYER:", layer.LayerType())
44  }
45
46 Packets can be decoded from a number of starting points.  Many of our base
47 types implement Decoder, which allow us to decode packets for which
48 we don't have full data.
49
50  // Decode an ethernet packet
51  ethP := gopacket.NewPacket(p1, layers.LayerTypeEthernet, gopacket.Default)
52  // Decode an IPv6 header and everything it contains
53  ipP := gopacket.NewPacket(p2, layers.LayerTypeIPv6, gopacket.Default)
54  // Decode a TCP header and its payload
55  tcpP := gopacket.NewPacket(p3, layers.LayerTypeTCP, gopacket.Default)
56
57
58 Reading Packets From A Source
59
60 Most of the time, you won't just have a []byte of packet data lying around.
61 Instead, you'll want to read packets in from somewhere (file, interface, etc)
62 and process them.  To do that, you'll want to build a PacketSource.
63
64 First, you'll need to construct an object that implements the PacketDataSource
65 interface.  There are implementations of this interface bundled with gopacket
66 in the gopacket/pcap and gopacket/pfring subpackages... see their documentation
67 for more information on their usage.  Once you have a PacketDataSource, you can
68 pass it into NewPacketSource, along with a Decoder of your choice, to create
69 a PacketSource.
70
71 Once you have a PacketSource, you can read packets from it in multiple ways.
72 See the docs for PacketSource for more details.  The easiest method is the
73 Packets function, which returns a channel, then asynchronously writes new
74 packets into that channel, closing the channel if the packetSource hits an
75 end-of-file.
76
77   packetSource := ...  // construct using pcap or pfring
78   for packet := range packetSource.Packets() {
79     handlePacket(packet)  // do something with each packet
80   }
81
82 You can change the decoding options of the packetSource by setting fields in
83 packetSource.DecodeOptions... see the following sections for more details.
84
85
86 Lazy Decoding
87
88 gopacket optionally decodes packet data lazily, meaning it
89 only decodes a packet layer when it needs to handle a function call.
90
91  // Create a packet, but don't actually decode anything yet
92  packet := gopacket.NewPacket(myPacketData, layers.LayerTypeEthernet, gopacket.Lazy)
93  // Now, decode the packet up to the first IPv4 layer found but no further.
94  // If no IPv4 layer was found, the whole packet will be decoded looking for
95  // it.
96  ip4 := packet.Layer(layers.LayerTypeIPv4)
97  // Decode all layers and return them.  The layers up to the first IPv4 layer
98  // are already decoded, and will not require decoding a second time.
99  layers := packet.Layers()
100
101 Lazily-decoded packets are not concurrency-safe.  Since layers have not all been
102 decoded, each call to Layer() or Layers() has the potential to mutate the packet
103 in order to decode the next layer.  If a packet is used
104 in multiple goroutines concurrently, don't use gopacket.Lazy.  Then gopacket
105 will decode the packet fully, and all future function calls won't mutate the
106 object.
107
108
109 NoCopy Decoding
110
111 By default, gopacket will copy the slice passed to NewPacket and store the
112 copy within the packet, so future mutations to the bytes underlying the slice
113 don't affect the packet and its layers.  If you can guarantee that the
114 underlying slice bytes won't be changed, you can use NoCopy to tell
115 gopacket.NewPacket, and it'll use the passed-in slice itself.
116
117  // This channel returns new byte slices, each of which points to a new
118  // memory location that's guaranteed immutable for the duration of the
119  // packet.
120  for data := range myByteSliceChannel {
121    p := gopacket.NewPacket(data, layers.LayerTypeEthernet, gopacket.NoCopy)
122    doSomethingWithPacket(p)
123  }
124
125 The fastest method of decoding is to use both Lazy and NoCopy, but note from
126 the many caveats above that for some implementations either or both may be
127 dangerous.
128
129
130 Pointers To Known Layers
131
132 During decoding, certain layers are stored in the packet as well-known
133 layer types.  For example, IPv4 and IPv6 are both considered NetworkLayer
134 layers, while TCP and UDP are both TransportLayer layers.  We support 4
135 layers, corresponding to the 4 layers of the TCP/IP layering scheme (roughly
136 anagalous to layers 2, 3, 4, and 7 of the OSI model).  To access these,
137 you can use the packet.LinkLayer, packet.NetworkLayer,
138 packet.TransportLayer, and packet.ApplicationLayer functions.  Each of
139 these functions returns a corresponding interface
140 (gopacket.{Link,Network,Transport,Application}Layer).  The first three
141 provide methods for getting src/dst addresses for that particular layer,
142 while the final layer provides a Payload function to get payload data.
143 This is helpful, for example, to get payloads for all packets regardless
144 of their underlying data type:
145
146  // Get packets from some source
147  for packet := range someSource {
148    if app := packet.ApplicationLayer(); app != nil {
149      if strings.Contains(string(app.Payload()), "magic string") {
150        fmt.Println("Found magic string in a packet!")
151      }
152    }
153  }
154
155 A particularly useful layer is ErrorLayer, which is set whenever there's
156 an error parsing part of the packet.
157
158  packet := gopacket.NewPacket(myPacketData, layers.LayerTypeEthernet, gopacket.Default)
159  if err := packet.ErrorLayer(); err != nil {
160    fmt.Println("Error decoding some part of the packet:", err)
161  }
162
163 Note that we don't return an error from NewPacket because we may have decoded
164 a number of layers successfully before running into our erroneous layer.  You
165 may still be able to get your Ethernet and IPv4 layers correctly, even if
166 your TCP layer is malformed.
167
168
169 Flow And Endpoint
170
171 gopacket has two useful objects, Flow and Endpoint, for communicating in a protocol
172 independent manner the fact that a packet is coming from A and going to B.
173 The general layer types LinkLayer, NetworkLayer, and TransportLayer all provide
174 methods for extracting their flow information, without worrying about the type
175 of the underlying Layer.
176
177 A Flow is a simple object made up of a set of two Endpoints, one source and one
178 destination.  It details the sender and receiver of the Layer of the Packet.
179
180 An Endpoint is a hashable representation of a source or destination.  For
181 example, for LayerTypeIPv4, an Endpoint contains the IP address bytes for a v4
182 IP packet.  A Flow can be broken into Endpoints, and Endpoints can be combined
183 into Flows:
184
185  packet := gopacket.NewPacket(myPacketData, layers.LayerTypeEthernet, gopacket.Lazy)
186  netFlow := packet.NetworkLayer().NetworkFlow()
187  src, dst := netFlow.Endpoints()
188  reverseFlow := gopacket.NewFlow(dst, src)
189
190 Both Endpoint and Flow objects can be used as map keys, and the equality
191 operator can compare them, so you can easily group together all packets
192 based on endpoint criteria:
193
194  flows := map[gopacket.Endpoint]chan gopacket.Packet
195  packet := gopacket.NewPacket(myPacketData, layers.LayerTypeEthernet, gopacket.Lazy)
196  // Send all TCP packets to channels based on their destination port.
197  if tcp := packet.Layer(layers.LayerTypeTCP); tcp != nil {
198    flows[tcp.TransportFlow().Dst()] <- packet
199  }
200  // Look for all packets with the same source and destination network address
201  if net := packet.NetworkLayer(); net != nil {
202    src, dst := net.NetworkFlow().Endpoints()
203    if src == dst {
204      fmt.Println("Fishy packet has same network source and dst: %s", src)
205    }
206  }
207  // Find all packets coming from UDP port 1000 to UDP port 500
208  interestingFlow := gopacket.NewFlow(layers.NewUDPPortEndpoint(1000), layers.NewUDPPortEndpoint(500))
209  if t := packet.NetworkLayer(); t != nil && t.TransportFlow() == interestingFlow {
210    fmt.Println("Found that UDP flow I was looking for!")
211  }
212
213 For load-balancing purposes, both Flow and Endpoint have FastHash() functions,
214 which provide quick, non-cryptographic hashes of their contents.  Of particular
215 importance is the fact that Flow FastHash() is symmetric: A->B will have the same
216 hash as B->A.  An example usage could be:
217
218  channels := [8]chan gopacket.Packet
219  for i := 0; i < 8; i++ {
220    channels[i] = make(chan gopacket.Packet)
221    go packetHandler(channels[i])
222  }
223  for packet := range getPackets() {
224    if net := packet.NetworkLayer(); net != nil {
225      channels[int(net.NetworkFlow().FastHash()) & 0x7] <- packet
226    }
227  }
228
229 This allows us to split up a packet stream while still making sure that each
230 stream sees all packets for a flow (and its bidirectional opposite).
231
232
233 Implementing Your Own Decoder
234
235 If your network has some strange encapsulation, you can implement your own
236 decoder.  In this example, we handle Ethernet packets which are encapsulated
237 in a 4-byte header.
238
239  // Create a layer type, should be unique and high, so it doesn't conflict,
240  // giving it a name and a decoder to use.
241  var MyLayerType = gopacket.RegisterLayerType(12345, gopacket.LayerTypeMetadata{Name: "MyLayerType", Decoder: gopacket.DecodeFunc(decodeMyLayer)})
242
243  // Implement my layer
244  type MyLayer struct {
245    StrangeHeader []byte
246    payload []byte
247  }
248  func (m MyLayer) LayerType() gopacket.LayerType { return MyLayerType }
249  func (m MyLayer) LayerContents() []byte { return m.StrangeHeader }
250  func (m MyLayer) LayerPayload() []byte { return m.payload }
251
252  // Now implement a decoder... this one strips off the first 4 bytes of the
253  // packet.
254  func decodeMyLayer(data []byte, p gopacket.PacketBuilder) error {
255    // Create my layer
256    p.AddLayer(&MyLayer{data[:4], data[4:]})
257    // Determine how to handle the rest of the packet
258    return p.NextDecoder(layers.LayerTypeEthernet)
259  }
260
261  // Finally, decode your packets:
262  p := gopacket.NewPacket(data, MyLayerType, gopacket.Lazy)
263
264 See the docs for Decoder and PacketBuilder for more details on how coding
265 decoders works, or look at RegisterLayerType and RegisterEndpointType to see how
266 to add layer/endpoint types to gopacket.
267
268
269 Fast Decoding With DecodingLayerParser
270
271 TLDR:  DecodingLayerParser takes about 10% of the time as NewPacket to decode
272 packet data, but only for known packet stacks.
273
274 Basic decoding using gopacket.NewPacket or PacketSource.Packets is somewhat slow
275 due to its need to allocate a new packet and every respective layer.  It's very
276 versatile and can handle all known layer types, but sometimes you really only
277 care about a specific set of layers regardless, so that versatility is wasted.
278
279 DecodingLayerParser avoids memory allocation altogether by decoding packet
280 layers directly into preallocated objects, which you can then reference to get
281 the packet's information.  A quick example:
282
283  func main() {
284    var eth layers.Ethernet
285    var ip4 layers.IPv4
286    var ip6 layers.IPv6
287    var tcp layers.TCP
288    parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &eth, &ip4, &ip6, &tcp)
289    decoded := []gopacket.LayerType{}
290    for packetData := range somehowGetPacketData() {
291      err := parser.DecodeLayers(packetData, &decoded)
292      for _, layerType := range decoded {
293        switch layerType {
294          case layers.LayerTypeIPv6:
295            fmt.Println("    IP6 ", ip6.SrcIP, ip6.DstIP)
296          case layers.LayerTypeIPv4:
297            fmt.Println("    IP4 ", ip4.SrcIP, ip4.DstIP)
298        }
299      }
300    }
301  }
302
303 The important thing to note here is that the parser is modifying the passed in
304 layers (eth, ip4, ip6, tcp) instead of allocating new ones, thus greatly
305 speeding up the decoding process.  It's even branching based on layer type...
306 it'll handle an (eth, ip4, tcp) or (eth, ip6, tcp) stack.  However, it won't
307 handle any other type... since no other decoders were passed in, an (eth, ip4,
308 udp) stack will stop decoding after ip4, and only pass back [LayerTypeEthernet,
309 LayerTypeIPv4] through the 'decoded' slice (along with an error saying it can't
310 decode a UDP packet).
311
312 Unfortunately, not all layers can be used by DecodingLayerParser... only those
313 implementing the DecodingLayer interface are usable.  Also, it's possible to
314 create DecodingLayers that are not themselves Layers... see
315 layers.IPv6ExtensionSkipper for an example of this.
316
317
318 Creating Packet Data
319
320 As well as offering the ability to decode packet data, gopacket will allow you
321 to create packets from scratch, as well.  A number of gopacket layers implement
322 the SerializableLayer interface; these layers can be serialized to a []byte in
323 the following manner:
324
325   ip := &layers.IPv4{
326     SrcIP: net.IP{1, 2, 3, 4},
327     DstIP: net.IP{5, 6, 7, 8},
328     // etc...
329   }
330   buf := gopacket.NewSerializeBuffer()
331   opts := gopacket.SerializeOptions{}  // See SerializeOptions for more details.
332   err := ip.SerializeTo(&buf, opts)
333   if err != nil { panic(err) }
334   fmt.Println(buf.Bytes())  // prints out a byte slice containing the serialized IPv4 layer.
335
336 SerializeTo PREPENDS the given layer onto the SerializeBuffer, and they treat
337 the current buffer's Bytes() slice as the payload of the serializing layer.
338 Therefore, you can serialize an entire packet by serializing a set of layers in
339 reverse order (Payload, then TCP, then IP, then Ethernet, for example).  The
340 SerializeBuffer's SerializeLayers function is a helper that does exactly that.
341
342 To generate a (empty and useless, because no fields are set)
343 Ethernet(IPv4(TCP(Payload))) packet, for example, you can run:
344
345   buf := gopacket.NewSerializeBuffer()
346   opts := gopacket.SerializeOptions{}
347   gopacket.SerializeLayers(buf, opts,
348     &layers.Ethernet{},
349     &layers.IPv4{},
350     &layers.TCP{},
351     gopacket.Payload([]byte{1, 2, 3, 4}))
352   packetData := buf.Bytes()
353
354 A Final Note
355
356 If you use gopacket, you'll almost definitely want to make sure gopacket/layers
357 is imported, since when imported it sets all the LayerType variables and fills
358 in a lot of interesting variables/maps (DecodersByLayerName, etc).  Therefore,
359 it's recommended that even if you don't use any layers functions directly, you still import with:
360
361   import (
362     _ "github.com/google/gopacket/layers"
363   )
364 */
365 package gopacket