I am programming a TCP syn flooder (for educational purposes) using WinPcap, but when i send my crafted packets the server does not receive anything. I am currently testing my program on localhost but i also have tried it on internet with Wireshark monitoring my network traffic, the packets are correct according to Wireshark but still the server does not receive anything.
Here are my ethernet/IP/TCP header structures:
#ifdef _MSC_VER
#pragma pack(push, 1)
#else
#pragma pack(1)
#endif
struct ethernet_header {
u8 dst_mac[6];
u8 src_mac[6];
u16 type;
};
struct ipv4_header {
u8 ver_ihl;
u8 tos;
u16 length;
u16 id;
u16 flags_fo;
u8 ttl;
u8 protocol;
u16 checksum;
u32 src_ip;
u32 dst_ip;
};
struct tcp_header {
u16 src_port;
u16 dst_port;
u32 seq_num;
u32 ack_num;
u16 off_flags;
u16 window_size;
u16 checksum;
u16 urgent_ptr;
struct {
struct {
u8 id; /* 0x02 = MSS */
u8 len; /* 0x04 */
u16 data; /* MSS value (1460) */
} mss;
u8 nop; /* 0x01 */
struct {
u8 id; /* 0x03 = Window Scale */
u8 len; /* 0x03 */
u8 data; /* Window Scale value (8) */
} window_scale;
u8 nop2; /* 0x01 */
u8 nop3; /* 0x01 */
struct {
u8 id; /* 0x04 = SACK */
u8 data; /* 0x02 */
} sack;
} options;
};
#ifdef _MSC_VER
#pragma pack(pop)
#else
#pragma pack(0)
#endif
And this is how i initialize them:
/* set ethernet header */
memcpy(ethhdr.dst_mac, dst_mac_address, 6);
memcpy(ethhdr.src_mac, src_mac_address, 6);
ethhdr.type = htons(ETHERTYPE_IPV4);
/* set ipv4 header */
ipv4hdr.ver_ihl |= 0x40; /* version is IPv4 */
ipv4hdr.ver_ihl |= 0x5; /* header size is 20 bytes */
ipv4hdr.tos = 0;
ipv4hdr.length = htons(sizeof(ipv4hdr) + sizeof(tcphdr));
ipv4hdr.id = 0;
ipv4hdr.flags_fo |= IP_CONTROL_FLAG_DF;
ipv4hdr.ttl = 128;
ipv4hdr.protocol = IPPROTOCOL_TCP;
ipv4hdr.checksum = 0;
ipv4hdr.src_ip = spoof_ip_address();
ipv4hdr.dst_ip = inet_addr("127.0.0.1");
/* calculate the checksum of a IP header */
ipv4hdr.checksum = calculate_checksum(&ipv4hdr,
sizeof(ipv4hdr));
/* set tcp header */
tcphdr.src_port = htons(60450);
tcphdr.dst_port = htons(32600);
tcphdr.seq_num = 0;
tcphdr.ack_num = 0;
tcphdr.off_flags |= 0x80; /* header size is 32 bytes */
tcphdr.off_flags |= TCP_CONTROL_FLAG_SYN;
tcphdr.window_size = htons(8192);
tcphdr.checksum = 0;
tcphdr.urgent_ptr = 0;
/* set TCP options */
tcphdr.options.mss.id = 0x02;
tcphdr.options.mss.len = 0x04;
tcphdr.options.mss.data = htons(1460);
tcphdr.options.nop = 0x01;
tcphdr.options.window_scale.id = 0x03;
tcphdr.options.window_scale.len = 0x03;
tcphdr.options.window_scale.data = 2;
tcphdr.options.nop2 = 0x01;
tcphdr.options.nop3 = 0x01;
tcphdr.options.sack.id = 0x04;
tcphdr.options.sack.data = 0x02;
/* calculate the checksum of a TCP header + options */
tcphdr.checksum = calculate_checksum(&tcphdr, sizeof(tcphdr));
The src_mac_address and dst_mac_address are set to the same value, that is the MAC address of the network interface adapter i am using. The spoof_ip_address() function returns a random IPv4 address in network byte order. The other fields (checksum, TCP options etc.) seems to be correct according to Wireshark.
I know that my router will overwrite MAC and IP address fields to its own MAC and IP address when sending packets destined to another network segment so that my IP spoofing is useless, but i am running a test TCP server with a backlog value of 1 on a loopback address, but it does not receive SYN packets. What am i doing wrong?
Thanks in advance.
A user space server application is ONLY going to receive a new connection once the TCP handshake is complete(the TCP/IP stack doesn't return from an accept() call just from a SYN packet).