text: // Copyright 2012 Google, Inc. All rights reserved.
  //
  // Use of this source code is governed by a BSD-style license
  // that can be found in the LICENSE file in the root of the source
  // tree.
  
  package gopacket
  
  import (
  	"errors"
  )
  
  // DecodeFeedback is used by DecodingLayer layers to provide decoding metadata.
  type DecodeFeedback interface {
  	// SetTruncated should be called if during decoding you notice that a packet
  	// is shorter than internal layer variables (HeaderLength, or the like) say it
  	// should be.  It sets packet.Metadata().Truncated.
  	SetTruncated()
  }
  
  type nilDecodeFeedback struct{}
  
  func (nilDecodeFeedback) SetTruncated() {}
  
  // NilDecodeFeedback implements DecodeFeedback by doing nothing.
  var NilDecodeFeedback DecodeFeedback = nilDecodeFeedback{}
  
  // PacketBuilder is used by layer decoders to store the layers they've decoded,
  // and to defer future decoding via NextDecoder.
  // Typically, the pattern for use is:
  //  func (m *myDecoder) Decode(data []byte, p PacketBuilder) error {
  //    if myLayer, err := myDecodingLogic(data); err != nil {
  //      return err
  //    } else {
  //      p.AddLayer(myLayer)
  //    }
  //    // maybe do this, if myLayer is a LinkLayer
  //    p.SetLinkLayer(myLayer)
  //    return p.NextDecoder(nextDecoder)
  //  }
  type PacketBuilder interface {
  	DecodeFeedback
  	// AddLayer should be called by a decoder immediately upon successful
  	// decoding of a layer.
  	AddLayer(l Layer)
  	// The following functions set the various specific layers in the final
  	// packet.  Note that if many layers call SetX, the first call is kept and all
  	// other calls are ignored.
  	SetLinkLayer(LinkLayer)
  	SetNetworkLayer(NetworkLayer)
  	SetTransportLayer(TransportLayer)
  	SetApplicationLayer(ApplicationLayer)
  	SetErrorLayer(ErrorLayer)
  	// NextDecoder should be called by a decoder when they're done decoding a
  	// packet layer but not done with decoding the entire packet.  The next
  	// decoder will be called to decode the last AddLayer's LayerPayload.
  	// Because of this, NextDecoder must only be called once all other
  	// PacketBuilder calls have been made.  Set*Layer and AddLayer calls after
  	// NextDecoder calls will behave incorrectly.
  	NextDecoder(next Decoder) error
  	// DumpPacketData is used solely for decoding.  If you come across an error
  	// you need to diagnose while processing a packet, call this and your packet's
  	// data will be dumped to stderr so you can create a test.  This should never
  	// be called from a production decoder.
  	DumpPacketData()
  	// DecodeOptions returns the decode options
  	DecodeOptions() *DecodeOptions
  }
  
  // Decoder is an interface for logic to decode a packet layer.  Users may
  // implement a Decoder to handle their own strange packet types, or may use one
  // of the many decoders available in the 'layers' subpackage to decode things
  // for them.
  type Decoder interface {
  	// Decode decodes the bytes of a packet, sending decoded values and other
  	// information to PacketBuilder, and returning an error if unsuccessful.  See
  	// the PacketBuilder documentation for more details.
  	Decode([]byte, PacketBuilder) error
  }
  
  // DecodeFunc wraps a function to make it a Decoder.
  type DecodeFunc func([]byte, PacketBuilder) error
  
  // Decode implements Decoder by calling itself.
  func (d DecodeFunc) Decode(data []byte, p PacketBuilder) error {
  	// function, call thyself.
  	return d(data, p)
  }
  
  // DecodePayload is a Decoder that returns a Payload layer containing all
  // remaining bytes.
  var DecodePayload Decoder = DecodeFunc(decodePayload)
  
  // DecodeUnknown is a Decoder that returns an Unknown layer containing all
  // remaining bytes, useful if you run up against a layer that you're unable to
  // decode yet.  This layer is considered an ErrorLayer.
  var DecodeUnknown Decoder = DecodeFunc(decodeUnknown)
  
  // DecodeFragment is a Decoder that returns a Fragment layer containing all
  // remaining bytes.
  var DecodeFragment Decoder = DecodeFunc(decodeFragment)
  
  // LayerTypeZero is an invalid layer type, but can be used to determine whether
  // layer type has actually been set correctly.
  var LayerTypeZero = RegisterLayerType(0, LayerTypeMetadata{Name: "Unknown", Decoder: DecodeUnknown})
  
  // LayerTypeDecodeFailure is the layer type for the default error layer.
  var LayerTypeDecodeFailure = RegisterLayerType(1, LayerTypeMetadata{Name: "DecodeFailure", Decoder: DecodeUnknown})
  
  // LayerTypePayload is the layer type for a payload that we don't try to decode
  // but treat as a success, IE: an application-level payload.
  var LayerTypePayload = RegisterLayerType(2, LayerTypeMetadata{Name: "Payload", Decoder: DecodePayload})
  
  // LayerTypeFragment is the layer type for a fragment of a layer transported
  // by an underlying layer that supports fragmentation.
  var LayerTypeFragment = RegisterLayerType(3, LayerTypeMetadata{Name: "Fragment", Decoder: DecodeFragment})
  
  // DecodeFailure is a packet layer created if decoding of the packet data failed
  // for some reason.  It implements ErrorLayer.  LayerContents will be the entire
  // set of bytes that failed to parse, and Error will return the reason parsing
  // failed.
  type DecodeFailure struct {
  	data  []byte
  	err   error
  	stack []byte
  }
  
  // Error returns the error encountered during decoding.
  func (d *DecodeFailure) Error() error { return d.err }
  
  // LayerContents implements Layer.
  func (d *DecodeFailure) LayerContents() []byte { return d.data }
  
  // LayerPayload implements Layer.
  func (d *DecodeFailure) LayerPayload() []byte { return nil }
  
  // String implements fmt.Stringer.
  func (d *DecodeFailure) String() string {
  	return "Packet decoding error: " + d.Error().Error()
  }
  
  // Dump implements Dumper.
  func (d *DecodeFailure) Dump() (s string) {
  	if d.stack != nil {
  		s = string(d.stack)
  	}
  	return
  }
  
  // LayerType returns LayerTypeDecodeFailure
  func (d *DecodeFailure) LayerType() LayerType { return LayerTypeDecodeFailure }
  
  // decodeUnknown "decodes" unsupported data types by returning an error.
  // This decoder will thus always return a DecodeFailure layer.
  func decodeUnknown(data []byte, p PacketBuilder) error {
  	return errors.New("Layer type not currently supported")
  }
  