C Language Examples of IPv4 and IPv6 Raw Sockets for Linux
2013-01-10 11:09
3107 查看
From:http://www.pdbuchan.com/rawsock/rawsock.html
I have recently been investigating raw socket programming in C for linux and I decided to provide a collection of routines I have prepared. The intention here is to be able to arbitrarily set the various parameters within a packet.
Rather than use command-line arguments, each example has hard-coded values, so you need to modify each example to suit your preferences.
You must run these as root to obtain raw sockets.
IPv4
Three combinations of the Domain, Type, and Protocol arguments are shown here. There are other possible combinations you could try. The packet parameters that can be modified are determined by which combination you choose.
In the Table 1 examples below, we tell the kernal the IP header is included (by us) by using setsockopt() and the IP_HDRINCL flag, and we can modify all values within the packet, but the kernal fills out the layer 2 (data link) information (source and next-hop
MAC addresses) for us.
In the Table 2 examples, we fill out all values, including the layer 2 (data link) information (source and next-hop MAC addresses). To do this, we must know the MAC address of the router/host the frames will be routed to next (more
explanation), as well as the MAC address of the network interface ("network card") we're sending the packet from.
In the Table 3 examples, we fill out all values, but only including the destination (i.e., next-hop) layer 2 (data link) information (not source MAC address). This is called a "cooked packet." To do this, we must know the MAC address of the router/host
the frames will be routed to next (more explanation).
To learn the next-hop's MAC address for use in the Table 2 and 3 examples above, you must use the Address Resolution Protocol (ARP). I have included an example which sends an ARP request ethernet frame as well as an example that receives an ARP reply ethernet
frame. Additionally, I have included some router solicitation and advertisement routines.
Table 5 below provides some examples of packet fragmentation. The first file, called "data", contains a list of numbers. The following three routines use it as data for the upper layer protocols. Feel free to provide to the routines your own data in any
manner you prefer.
Table 6 below presents examples of packets with IP and TCP options.
IPv6
In IPv6, we have less options at our disposal for modifying packet values (see
RFC 3542 and
RFC 3493). In particular, IPv6 has no equivalent to using setsockopt() with the IP_HDRINCL flag (see Table 1 in IPv4 section above). Without doing something special (using neighbor discovery), we can only change the hop limit and traffic class values in
the IPv6 header. Neighbor discovery is the IPv6 replacement for ARP in IPv4.
Before we try some neighbor discovery, let's take a quick look at a couple of examples where we don't use neighbor discovery, and thus can only change the hop limit and traffic class values in the IPv6 header.
You can use either the ancillary data method, or a call to setsockopt() with option level IPPROTO_IPV6 and option names IPV6_TCLASS, IPV6_UNICAST_HOPS, or IPV6_MULTICAST_HOPS. Note that changes made to the properties of the socket with setsockopt() will
remain in effect for all packets sent through the socket, whereas ancillary data is associated with a particular packet.
If we wish to have the ability to change any parameter in the IPv6 header, we need to have the source and destination MAC addresses available (more explanation). In this case we have the same sort of
options available to us as we did in Tables 2 and 3 above for IPv4. To recap, these are:
The neighbor discovery process is used to obtain the MAC address of a link-local node's interface card (could be the MAC address of a link-local router or host's interface the frames will be routed through). First we send a
neighbor solicitation with our MAC address to the target node, and then it replies with a
neighbor advertisement that contains its MAC address. The neighbor solicitation is sent to the target node's
solicited-node multicast address.
Some router discovery routines are also included. Router solicitations are issued by a host looking for local routers, and router advertisements are issued by routers announcing their presence on the LAN.
Now that we have used neighbor discovery to determine the MAC address of a link-local router or host, we can go ahead and modify all parameters withinthe ethernet frame.
As in the IPv4 examples of Table 3, in Table 10 below we fill out all values, but only including the
destination (i.e., next hop) layer 2 (data link) information and not the source MAC address. This is called a "cooked packet." As in Table 7 above, we must know the MAC address of the router/host the frames will be routed to next (more
explanation).
For the transition from IPv4 to IPv6, a mechanism of tunneling IPv6 over IPv4 (6to4) has been established. Table 11 presents some 6to4 examples.
The following table provides some examples of packet fragmentation. In IPv6, fragmentation requires the introduction of a
fragment extension header. The first file, called "data", contains a list of numbers. The following routines use it as data for the upper layer protocols. Feel free to provide to the routines your own data in any manner you prefer.
Table 13 below provides examples of sending TCP packets with TCP options. Note that in IPv6, extension headers are used instead of IP header options.
P. David Buchan pdbuchan@yahoo.com
December 17, 2012
I have recently been investigating raw socket programming in C for linux and I decided to provide a collection of routines I have prepared. The intention here is to be able to arbitrarily set the various parameters within a packet.
Rather than use command-line arguments, each example has hard-coded values, so you need to modify each example to suit your preferences.
You must run these as root to obtain raw sockets.
IPv4
Three combinations of the Domain, Type, and Protocol arguments are shown here. There are other possible combinations you could try. The packet parameters that can be modified are determined by which combination you choose.
In the Table 1 examples below, we tell the kernal the IP header is included (by us) by using setsockopt() and the IP_HDRINCL flag, and we can modify all values within the packet, but the kernal fills out the layer 2 (data link) information (source and next-hop
MAC addresses) for us.
Table 1: | sd = socket (AF_INET, SOCK_RAW, IPPROTO_RAW); |
The kernel fills out layer 2 (data link) information (MAC addresses) for us. |
tcp4.c | SYN packet (an example with no TCP data) |
get4.c | HTTP GET (an example with TCP data) (note) |
icmp4.c | ICMP Echo Request with data, “Test” |
udp4.c | UDP packet with data, “Test” |
explanation), as well as the MAC address of the network interface ("network card") we're sending the packet from.
Table 2: | sd = socket (PF_PACKET, SOCK_RAW, htons (ETH_P_ALL)); |
We provide layer 2 (data link) information. i.e., we specify ethernet frame header with MAC addresses. |
tcp4_ll.c | SYN packet (an example with no TCP data) |
get4_ll.c | HTTP GET (an example with TCP data) (note) |
icmp4_ll.c | ICMP Echo Request with data, “Test” |
udp4_ll.c | UDP packet with data, “Test” |
the frames will be routed to next (more explanation).
Table 3: | sd = socket (PF_PACKET, SOCK_DGRAM, htons (ETH_P_ALL)); |
We provide a "cooked" packet with destination MAC address in struct sockaddr_ll. |
tcp4_cooked.c | SYN packet (an example with no TCP data) |
get4_cooked.c | HTTP GET (an example with TCP data) (note) |
icmp4_cooked.c | ICMP Echo Request with data, “Test” |
udp4_cooked.c | UDP packet with data, “Test” |
frame. Additionally, I have included some router solicitation and advertisement routines.
Table 4: | Miscellaneous |
arp.c | Send an ARP request ethernet frame |
receive_arp.c | Receive an ARP reply ethernet frame |
rs4.c | Send a router solicitation |
ra4.c | Send a router advertisement |
receive_ra4.c | Receive a router advertisement |
tr4_ll.c | TCP/ICMP/UDP traceroute |
manner you prefer.
Table 5: | Fragmentation |
data | 12390-byte file to use as upper layer protocol data |
tcp4_frag.c | Send TCP packet with enough data to require fragmentation |
icmp4_frag.c | Send ICMP packet with enough data to require fragmentation |
udp4_frag.c | Send UDP packet with enough data to require fragmentation |
Table 6: | IP and TCP Options |
tcp4_maxseg.c | Send TCP packet with a TCP option which sets maximum segment size |
tcp4_maxseg_tsopt.c | Send TCP packet with two TCP options: set maximum segment size, and provide timestamp |
tcp4_maxseg-timestamp.c | Send TCP packet with IP option to send time stamp, and TCP option to set maximum segment size |
tcp4_maxseg-security.c | Send TCP packet with security IP option and TCP option to set maximum segment size |
tcp4_2ip-opts_2tcp_opts.c | Send TCP packet with two IP options and two TCP options |
In IPv6, we have less options at our disposal for modifying packet values (see
RFC 3542 and
RFC 3493). In particular, IPv6 has no equivalent to using setsockopt() with the IP_HDRINCL flag (see Table 1 in IPv4 section above). Without doing something special (using neighbor discovery), we can only change the hop limit and traffic class values in
the IPv6 header. Neighbor discovery is the IPv6 replacement for ARP in IPv4.
Before we try some neighbor discovery, let's take a quick look at a couple of examples where we don't use neighbor discovery, and thus can only change the hop limit and traffic class values in the IPv6 header.
You can use either the ancillary data method, or a call to setsockopt() with option level IPPROTO_IPV6 and option names IPV6_TCLASS, IPV6_UNICAST_HOPS, or IPV6_MULTICAST_HOPS. Note that changes made to the properties of the socket with setsockopt() will
remain in effect for all packets sent through the socket, whereas ancillary data is associated with a particular packet.
Table 7: | Without Using Neighbor Discovery (ND) |
Ancillary data method |
icmp6_ancillary1.c | Change hop limit in IPv6 header |
icmp6_ancillary2.c | Change hop limit and specify source interface |
options available to us as we did in Tables 2 and 3 above for IPv4. To recap, these are:
Table 2 | sd = socket (PF_PACKET, SOCK_RAW, htons (ETH_P_ALL)); We provide layer 2 (data link) information. i.e., we specify ethernet frame header with MAC addresses. |
Table 3 | sd = socket (PF_PACKET, SOCK_DGRAM, htons (ETH_P_ALL)); We provide a "cooked" packet with destination MAC address in struct sockaddr_ll. |
neighbor solicitation with our MAC address to the target node, and then it replies with a
neighbor advertisement that contains its MAC address. The neighbor solicitation is sent to the target node's
solicited-node multicast address.
Some router discovery routines are also included. Router solicitations are issued by a host looking for local routers, and router advertisements are issued by routers announcing their presence on the LAN.
Table 8: | Neighbor Discovery and Router Discovery |
ns.c | Send a neighbor solicitation |
na.c | Send a neighbor advertisement (this example doesn't detect and respond to a solicitation) |
receive_na.c | Receive a neighbor advertisement and extract lots of info including MAC address |
rs6.c | Send a router solicitation |
ra6.c | Send a router advertisement (this example doesn't detect and respond to a solicitation) |
receive_ra6.c | Receive a router advertisement and extract lots of info including MAC address |
Table 9: | sd = socket (PF_PACKET, SOCK_RAW, htons (ETH_P_ALL)); |
tcp6_ll.c | SYN packet (an example with no TCP data) |
get6_ll.c | HTTP GET (an example with TCP data) (note) |
icmp6_ll.c | ICMP Echo Request with data, “Test” |
udp6_ll.c | UDP packet with data, “Test” |
destination (i.e., next hop) layer 2 (data link) information and not the source MAC address. This is called a "cooked packet." As in Table 7 above, we must know the MAC address of the router/host the frames will be routed to next (more
explanation).
Table 10: | sd = socket (PF_PACKET, SOCK_DGRAM, htons (ETH_P_ALL)); |
tcp6_cooked.c | SYN packet (an example with no TCP data) |
get6_cooked.c | HTTP GET (an example with TCP data) (note) |
icmp6_cooked.c | ICMP Echo Request with data, “Test” |
udp6_cooked.c | UDP packet with data, “Test” |
Table 11: | Tunneling IPv6 over IPv4 (6to4) |
tcp6_6to4.c | SYN packet (an example with no TCP data) |
get6_6to4.c | HTTP GET (an example with TCP data) (note) |
icmp6_6to4.c | ICMP Echo Request with data, “Test” |
udp6_6to4.c | UDP packet with data, “Test” |
fragment extension header. The first file, called "data", contains a list of numbers. The following routines use it as data for the upper layer protocols. Feel free to provide to the routines your own data in any manner you prefer.
Table 12: | Fragmentation |
data | 12390-byte file to use as upper layer protocol data |
tcp6_frag.c | Send TCP packet with enough data to require fragmentation |
icmp6_frag.c | Send ICMP packet with enough data to require fragmentation |
udp6_frag.c | Send UDP packet with enough data to require fragmentation |
tcp6_6to4_frag.c | Send IPv6 TCP packet through IPv4 tunnel with enough data to require fragmentation |
icmp6_6to4_frag.c | Send IPv6 ICMP packet through IPv4 tunnel with enough data to require fragmentation |
udp6_6to4_frag.c | Send IPv6 UDP packet through IPv4 tunnel with enough data to require fragmentation |
Table 13: | TCP Options |
tcp6_maxseg.c | Send TCP packet with a TCP option which sets maximum segment size |
tcp6_maxseg_tsopt.c | Send TCP packet with two TCP options: set maximum segment size, and provide timestamp |
December 17, 2012
相关文章推荐
- C Language Examples of IPv4 and IPv6 Raw Sockets for Linux
- How to enable packet forwarding for IPv4 and IPv6
- Analysing the ASM code of a simple sample of C programming language at Linux Platform by GCC and GDB
- The Linux Page Cache and pdflush:Theory of Operation and Tuning for Write-Heavy Loads
- Netsh Commands for Interface (IPv4 and IPv6)
- How to support both ipv4 and ipv6 address for JAVA code.
- Abuse of the Linux Kernel for Fun and Profit
- Manual Installation and Registration of Java Plugin for Linux
- How to find PID of process listening on a port in Linux? netstat and lsof command examples
- The pros and "conns" of Intel's ConnMan for Linux
- 29 Practical Examples of Nmap Commands for Linux System/Network Administrators
- Handbook of IPv4 to IPv6 Transition: Methodologies for Institutional and Corporate Networks
- gateways for IPv4 and IPv6
- Network interface operations for IPv4 and IPv6 on AIX Version 5.3
- Step by Step Installation of the Subversion 1.x Server for Linux and Solaris 8/9/10 (English)
- Issue 71 - pymssql - Undefined symbols on Mac, CentOS, Redhat with pre-compiled build - A fast MS SQL Server client library for Python directly using C API instead of ODBC. It is Python DB-API 2.0 compliant. Works on Linux, *BSD, Solaris, Mac OS X and Win
- linux_ 25 Useful Basic Commands of APT-GET and APT-CACHE for Package Management
- Massive Collection Of Design Patterns, Frameworks, Components, And Language Features For Delphi
- Shell script for logging cpu and memory usage of a Linux process