func (icmp *Icmp) ProcessICMPv6( flowID *flows.FlowID, icmp6 *layers.ICMPv6, pkt *protos.Packet, ) { typ := uint8(icmp6.TypeCode >> 8) code := uint8(icmp6.TypeCode) id, seq := extractTrackingData(6, typ, &icmp6.BaseLayer) tuple := &icmpTuple{ IcmpVersion: 6, SrcIp: pkt.Tuple.Src_ip, DstIp: pkt.Tuple.Dst_ip, Id: id, Seq: seq, } msg := &icmpMessage{ Ts: pkt.Ts, Type: typ, Code: code, Length: len(icmp6.BaseLayer.Payload), } if isRequest(tuple, msg) { if flowID != nil { flowID.AddICMPv6Request(id) } icmp.processRequest(tuple, msg) } else { if flowID != nil { flowID.AddICMPv6Response(id) } icmp.processResponse(tuple, msg) } }
func (icmp *icmpPlugin) ProcessICMPv4( flowID *flows.FlowID, icmp4 *layers.ICMPv4, pkt *protos.Packet, ) { typ := uint8(icmp4.TypeCode >> 8) code := uint8(icmp4.TypeCode) id, seq := extractTrackingData(4, typ, &icmp4.BaseLayer) tuple := &icmpTuple{ icmpVersion: 4, srcIP: pkt.Tuple.SrcIP, dstIP: pkt.Tuple.DstIP, id: id, seq: seq, } msg := &icmpMessage{ ts: pkt.Ts, Type: typ, code: code, length: len(icmp4.BaseLayer.Payload), } if isRequest(tuple, msg) { if flowID != nil { flowID.AddICMPv4Request(id) } icmp.processRequest(tuple, msg) } else { if flowID != nil { flowID.AddICMPv4Response(id) } icmp.processResponse(tuple, msg) } }
func (tcp *Tcp) Process(id *flows.FlowID, tcphdr *layers.TCP, pkt *protos.Packet) { // This Recover should catch all exceptions in // protocol modules. defer logp.Recover("Process tcp exception") debugf("tcp flow id: %p", id) stream, created := tcp.getStream(pkt) if stream.conn == nil { return } if id != nil { id.AddConnectionID(uint64(stream.conn.id)) } conn := stream.conn tcp_start_seq := tcphdr.Seq tcp_seq := tcp_start_seq + uint32(len(pkt.Payload)) lastSeq := conn.lastSeq[stream.dir] if isDebug { debugf("pkt.start_seq=%v pkt.last_seq=%v stream.last_seq=%v (len=%d)", tcp_start_seq, tcp_seq, lastSeq, len(pkt.Payload)) } if len(pkt.Payload) > 0 && lastSeq != 0 { if tcpSeqBeforeEq(tcp_seq, lastSeq) { if isDebug { debugf("Ignoring retransmitted segment. pkt.seq=%v len=%v stream.seq=%v", tcphdr.Seq, len(pkt.Payload), lastSeq) } return } if tcpSeqBefore(lastSeq, tcp_start_seq) { if !created { gap := int(tcp_start_seq - lastSeq) logp.Warn("Gap in tcp stream. last_seq: %d, seq: %d, gap: %d", lastSeq, tcp_start_seq, gap) drop := stream.gapInStream(gap) if drop { if isDebug { debugf("Dropping connection state because of gap") } // drop application layer connection state and // update stream_id for app layer analysers using stream_id for lookups conn.id = tcp.getId() conn.data = nil } } } } conn.lastSeq[stream.dir] = tcp_seq stream.addPacket(pkt, tcphdr) }
func (tcp *Tcp) Process(id *flows.FlowID, tcphdr *layers.TCP, pkt *protos.Packet) { // This Recover should catch all exceptions in // protocol modules. defer logp.Recover("Process tcp exception") stream, created := tcp.getStream(pkt) if stream.conn == nil { return } conn := stream.conn if id != nil { id.AddConnectionID(uint64(conn.id)) } if isDebug { debugf("tcp flow id: %p", id) } if len(pkt.Payload) == 0 && !tcphdr.FIN { // return early if packet is not interesting. Still need to find/create // stream first in order to update the TCP stream timer return } tcpStartSeq := tcphdr.Seq tcpSeq := tcpStartSeq + uint32(len(pkt.Payload)) lastSeq := conn.lastSeq[stream.dir] if isDebug { debugf("pkt.start_seq=%v pkt.last_seq=%v stream.last_seq=%v (len=%d)", tcpStartSeq, tcpSeq, lastSeq, len(pkt.Payload)) } if len(pkt.Payload) > 0 && lastSeq != 0 { if tcpSeqBeforeEq(tcpSeq, lastSeq) { if isDebug { debugf("Ignoring retransmitted segment. pkt.seq=%v len=%v stream.seq=%v", tcphdr.Seq, len(pkt.Payload), lastSeq) } return } switch tcpSeqCompare(lastSeq, tcpStartSeq) { case seqLT: // lastSeq < tcpStartSeq => Gap in tcp stream detected if created { break } gap := int(tcpStartSeq - lastSeq) debugf("Gap in tcp stream. last_seq: %d, seq: %d, gap: %d", lastSeq, tcpStartSeq, gap) drop := stream.gapInStream(gap) if drop { if isDebug { debugf("Dropping connection state because of gap") } droppedBecauseOfGaps.Add(1) // drop application layer connection state and // update stream_id for app layer analysers using stream_id for lookups conn.id = tcp.getId() conn.data = nil } case seqGT: // lastSeq > tcpStartSeq => overlapping TCP segment detected. shrink packet delta := lastSeq - tcpStartSeq if isDebug { debugf("Overlapping tcp segment. last_seq %d, seq: %d, delta: %d", lastSeq, tcpStartSeq, delta) } pkt.Payload = pkt.Payload[delta:] tcphdr.Seq += delta } } conn.lastSeq[stream.dir] = tcpSeq stream.addPacket(pkt, tcphdr) }