Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
tcp_crafter.go
package main
import (
"encoding/binary"
"github.com/google/gopacket"
"github.com/google/gopacket/layers"
"github.com/google/gopacket/pcapgo"
"github.com/miekg/dns"
"log"
"net"
"os"
"time"
)
const pcapFileName = "/tmp/dump.pcap"
func main() {
process_row()
}
func process_row() error {
f, err := os.Create(pcapFileName)
if err != nil {
log.Fatalf("Could not create target pcap file: %s", pcapFileName)
}
pcap_writer := pcapgo.NewWriter(f)
// File pcap file header
pcap_writer.WriteFileHeader(65536, layers.LinkTypeEthernet)
queryName := "testdomain.com"
// A
queryType := 1
srcIPv4 := 2130706433
dstIPv4 := 2130706433
srcPort := 65111
dstPort := 53
dateTime := time.Now()
srcIPv4Slice := make(net.IP, 4)
dstIPv4Slice := make(net.IP, 4)
binary.BigEndian.PutUint32(srcIPv4Slice, uint32(srcIPv4))
binary.BigEndian.PutUint32(dstIPv4Slice, uint32(dstIPv4))
// Let's craft network packets
buf := gopacket.NewSerializeBuffer()
opts := gopacket.SerializeOptions{
FixLengths: true,
}
ethernetLayer := &layers.Ethernet{
SrcMAC: []byte{0, 0, 0, 0, 0, 0},
DstMAC: []byte{0, 0, 0, 0, 0, 0},
}
dnsMessage := new(dns.Msg)
dnsMessage.Id = dns.Id()
dnsMessage.RecursionDesired = true
dnsMessage.Question = make([]dns.Question, 1)
dnsMessage.Question[0] = dns.Question{dns.Fqdn(queryName), uint16(queryType), dns.ClassINET}
dnsBuffer, err := dnsMessage.PackBuffer(nil)
log.Printf("DNS message: %v", dnsMessage)
if err != nil {
log.Fatalf("Could not encode DNS message to wire format: %v", err)
}
ethernetLayer.EthernetType = layers.EthernetTypeIPv4
ipv4 := &layers.IPv4{
Version: 4,
SrcIP: srcIPv4Slice,
DstIP: dstIPv4Slice,
TTL: 128,
}
ipv4.Protocol = layers.IPProtocolTCP
log.Printf("dnsBuffer: %v length: %d", dnsBuffer, len(dnsBuffer))
gopacket.SerializeLayers(buf, opts,
ethernetLayer,
ipv4,
&layers.TCP{
SrcPort: layers.TCPPort(srcPort),
DstPort: layers.TCPPort(dstPort),
PSH: true,
Window: uint16(len(dnsBuffer)),
DataOffset: 0,
},
gopacket.Payload(dnsBuffer))
packetLength := len(buf.Bytes())
// Fill meta information for packet for pcap
cInfo := gopacket.CaptureInfo{
// Timestamp is the time the packet was captured, if that is known.
Timestamp: dateTime,
// CaptureLength is the total number of bytes read off of the wire.
CaptureLength: packetLength,
// Length is the size of the original packet. Should always be >=
// CaptureLength.
Length: packetLength,
// InterfaceIndex, we do not need it
InterfaceIndex: 0,
}
pcap_writer.WritePacket(cInfo, buf.Bytes())
log.Printf("Dump generated at: %s", pcapFileName)
return nil
}
@jianjin

This comment has been minimized.

Copy link

jianjin commented Nov 28, 2017

I am trying to use gopacket to send data also. A question: where is the logic of TCP connection setup?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.