Make the full EthernetDecoder available to LogFrame

So that LogFrame can include information about the decoded frame beyond
the ethernet layer.
This commit is contained in:
David Wragg committed 2015-06-25 17:11:20 +01:00
1 parent ea59c6c065
commit 4162dcafd3
5 files changed
+35 -35

No files matched your search

+4 -4
View File
@@ -192,14 +192,14 @@ func options() map[string]string {
func logFrameFunc(debug bool) weave.LogFrameFunc {
if !debug {
return func(prefix string, frame []byte, eth *layers.Ethernet) {}
return func(prefix string, frame []byte, dec *weave.EthernetDecoder) {}
}
return func(prefix string, frame []byte, eth *layers.Ethernet) {
return func(prefix string, frame []byte, dec *weave.EthernetDecoder) {
h := fmt.Sprintf("%x", sha256.Sum256(frame))
if eth == nil {
if dec == nil {
log.Println(prefix, len(frame), "bytes (", h, ")")
} else {
log.Println(prefix, len(frame), "bytes (", h, "):", eth.SrcMAC, "->", eth.DstMAC)
log.Println(prefix, len(frame), "bytes (", h, "):", dec.Eth.SrcMAC, "->", dec.Eth.DstMAC)
}
}
}
+15 -15
View File
@@ -10,15 +10,15 @@ import (
)
type EthernetDecoder struct {
eth layers.Ethernet
ip layers.IPv4
Eth layers.Ethernet
IP layers.IPv4
decoded []gopacket.LayerType
parser *gopacket.DecodingLayerParser
}
func NewEthernetDecoder() *EthernetDecoder {
dec := &EthernetDecoder{}
dec.parser = gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &dec.eth, &dec.ip)
dec.parser = gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &dec.Eth, &dec.IP)
return dec
}
@@ -31,23 +31,23 @@ func (dec *EthernetDecoder) sendICMPFragNeeded(mtu int, sendFrame func([]byte) e
opts := gopacket.SerializeOptions{
FixLengths: true,
ComputeChecksums: true}
ipHeaderSize := int(dec.ip.IHL) * 4 // IHL is the number of 32-byte words in the header
payload := gopacket.Payload(dec.ip.BaseLayer.Contents[:ipHeaderSize+8])
ipHeaderSize := int(dec.IP.IHL) * 4 // IHL is the number of 32-byte words in the header
payload := gopacket.Payload(dec.IP.BaseLayer.Contents[:ipHeaderSize+8])
err := gopacket.SerializeLayers(buf, opts,
&layers.Ethernet{
SrcMAC: dec.eth.DstMAC,
DstMAC: dec.eth.SrcMAC,
EthernetType: dec.eth.EthernetType},
SrcMAC: dec.Eth.DstMAC,
DstMAC: dec.Eth.SrcMAC,
EthernetType: dec.Eth.EthernetType},
&layers.IPv4{
Version: 4,
TOS: dec.ip.TOS,
TOS: dec.IP.TOS,
Id: 0,
Flags: 0,
FragOffset: 0,
TTL: 64,
Protocol: layers.IPProtocolICMPv4,
DstIP: dec.ip.SrcIP,
SrcIP: dec.ip.DstIP},
DstIP: dec.IP.SrcIP,
SrcIP: dec.IP.DstIP},
&layers.ICMPv4{
TypeCode: 0x304,
Id: 0,
@@ -57,7 +57,7 @@ func (dec *EthernetDecoder) sendICMPFragNeeded(mtu int, sendFrame func([]byte) e
return err
}
log.Printf("Sending ICMP 3,4 (%v -> %v): PMTU= %v\n", dec.ip.DstIP, dec.ip.SrcIP, mtu)
log.Printf("Sending ICMP 3,4 (%v -> %v): PMTU= %v\n", dec.IP.DstIP, dec.IP.SrcIP, mtu)
return sendFrame(buf.Bytes())
}
@@ -68,10 +68,10 @@ var (
)
func (dec *EthernetDecoder) DropFrame() bool {
return bytes.Equal(stpMACPrefix, dec.eth.DstMAC[:len(stpMACPrefix)])
return bytes.Equal(stpMACPrefix, dec.Eth.DstMAC[:len(stpMACPrefix)])
}
func (dec *EthernetDecoder) IsSpecial() bool {
return dec.eth.Length == 0 && dec.eth.EthernetType == layers.EthernetTypeLLC &&
bytes.Equal(zeroMAC, dec.eth.SrcMAC) && bytes.Equal(zeroMAC, dec.eth.DstMAC)
return dec.Eth.Length == 0 && dec.Eth.EthernetType == layers.EthernetTypeLLC &&
bytes.Equal(zeroMAC, dec.Eth.SrcMAC) && bytes.Equal(zeroMAC, dec.Eth.DstMAC)
}
+2 -2
View File
@@ -105,11 +105,11 @@ func (conn *LocalConnection) Forward(df bool, frame *ForwardedFrame, dec *Ethern
forwarderDF.Forward(frame)
return nil
}
conn.Router.LogFrame("Fragmenting", frame.frame, &dec.eth)
conn.Router.LogFrame("Fragmenting", frame.frame, dec)
// We can't trust the stack to fragment, we have IP, and we
// have a frame that's too big for the MTU, so we have to
// fragment it ourself.
return fragment(dec.eth, dec.ip, effectivePMTU, frame, func(segFrame *ForwardedFrame) {
return fragment(dec.Eth, dec.IP, effectivePMTU, frame, func(segFrame *ForwardedFrame) {
forwarderDF.Forward(segFrame)
})
}
+1 -1
View File
@@ -70,7 +70,7 @@ func (peer *LocalPeer) RelayBroadcast(srcPeer *Peer, df bool, frame []byte, dec
dec)
if err != nil {
if ftbe, ok := err.(FrameTooBigError); ok {
log.Printf("dropping too big DF broadcast frame (%v -> %v): PMTU= %v\n", dec.ip.DstIP, dec.ip.SrcIP, ftbe.EPMTU)
log.Printf("dropping too big DF broadcast frame (%v -> %v): PMTU= %v\n", dec.IP.DstIP, dec.IP.SrcIP, ftbe.EPMTU)
} else {
log.Println(err)
}
+13 -13
View File
@@ -27,7 +27,7 @@ const (
// against brute-force attacks on the password when encryption is in
// use. It is also a basic DoS defence.
type LogFrameFunc func(string, []byte, *layers.Ethernet)
type LogFrameFunc func(string, []byte, *EthernetDecoder)
type Config struct {
Port int
@@ -151,7 +151,7 @@ func (router *Router) handleCapturedPacket(frameData []byte, dec *EthernetDecode
if decodedLen == 0 {
return
}
srcMac := dec.eth.SrcMAC
srcMac := dec.Eth.SrcMAC
srcPeer, found := router.Macs.Lookup(srcMac)
// We need to filter out frames we injected ourselves. For such
// frames, the srcMAC will have been recorded as associated with a
@@ -165,16 +165,16 @@ func (router *Router) handleCapturedPacket(frameData []byte, dec *EthernetDecode
if dec.DropFrame() {
return
}
dstMac := dec.eth.DstMAC
dstMac := dec.Eth.DstMAC
dstPeer, found := router.Macs.Lookup(dstMac)
if found && dstPeer == router.Ourself.Peer {
return
}
df := decodedLen == 2 && (dec.ip.Flags&layers.IPv4DontFragment != 0)
df := decodedLen == 2 && (dec.IP.Flags&layers.IPv4DontFragment != 0)
if df {
router.LogFrame("Forwarding DF", frameData, &dec.eth)
router.LogFrame("Forwarding DF", frameData, dec)
} else {
router.LogFrame("Forwarding", frameData, &dec.eth)
router.LogFrame("Forwarding", frameData, dec)
}
// at this point we are handing over the frame to forwarders, so
// we need to make a copy of it in order to prevent the next
@@ -316,14 +316,14 @@ func (router *Router) handleUDPPacketFunc(relayConn *LocalConnection, dec *Ether
return
}
df := decodedLen == 2 && (dec.ip.Flags&layers.IPv4DontFragment != 0)
df := decodedLen == 2 && (dec.IP.Flags&layers.IPv4DontFragment != 0)
if dstPeer != router.Ourself.Peer {
// it's not for us, we're just relaying it
if df {
router.LogFrame("Relaying DF", frame, &dec.eth)
router.LogFrame("Relaying DF", frame, dec)
} else {
router.LogFrame("Relaying", frame, &dec.eth)
router.LogFrame("Relaying", frame, dec)
}
err := router.Ourself.Relay(srcPeer, dstPeer, df, frame, dec)
@@ -337,20 +337,20 @@ func (router *Router) handleUDPPacketFunc(relayConn *LocalConnection, dec *Ether
return
}
srcMac := dec.eth.SrcMAC
dstMac := dec.eth.DstMAC
srcMac := dec.Eth.SrcMAC
dstMac := dec.Eth.DstMAC
if router.Macs.Enter(srcMac, srcPeer) {
log.Println("Discovered remote MAC", srcMac, "at", srcPeer)
}
if po != nil {
router.LogFrame("Injecting", frame, &dec.eth)
router.LogFrame("Injecting", frame, dec)
checkWarn(po.WritePacket(frame))
}
dstPeer, found = router.Macs.Lookup(dstMac)
if !found || dstPeer != router.Ourself.Peer {
router.LogFrame("Relaying broadcast", frame, &dec.eth)
router.LogFrame("Relaying broadcast", frame, dec)
router.Ourself.RelayBroadcast(srcPeer, df, frame, dec)
}
}