![](/media/cache/img/default_profile.jpg.50x50_q85.jpg)
test icmp
Fork of ethspam by
Diff: net/ip.h
- Revision:
- 1:feaa107f56b3
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/net/ip.h Fri Apr 24 03:11:02 2015 +0000 @@ -0,0 +1,115 @@ +#ifndef IP_H +#define IP_H + +#include "net.h" + +/** + \file ip.h + \brief IP Packet header + + This file contains the memory map and associated functions for IP packet header + creation and deconstruction. +*/ + +#define ETHERTYPE_IPV4 0x0800 +#define ETHERTYPE_IPV6 0x86DD + +/// IP Address memory map +typedef struct { + unsigned char octet[4]; ///< Individual address octets +} IP_Address; + +/// IP Packet memory map +typedef struct { + /// 4 bits that contain the version, that specifies if it's an IPv4 or IPv6 packet, + unsigned version:4; // Only 0x4 supported + /// 4 bits that contain the Internet Header Length which is the length of the header in multiples of 4 bytes (eg. 5 means 20 bytes). + unsigned header_bytes_div4:4; + /// 8 bits that contain the Type of Service, also referred to as Quality of Service (QoS), which describes what priority the packet should have, + unsigned tos:8; + /// 16 bits that contain the total length of the IP packet (datagram) in bytes, + u16 packet_bytes; + /// 16 bits that contain an identification tag to help reconstruct the packet from several fragments, + u16 fragment_id; + /// 3 bits that contain a zero, a flag that says whether the packet is allowed to be fragmented or not (DF: Don't fragment), and a flag to state whether more fragments of a packet follow (MF: More Fragments) + unsigned unused_0:1; + unsigned dont_fragment:1; + unsigned more_follow:1; + /// 13 bits that contain the fragment offset, a field to identify position of fragment within original packet + unsigned fragment_offset:13; ///< This and the ones above may not work properly due to endianness + /// 8 bits that contain the Time to live (TTL) which is the number of hops (router, computer or device along a network) the packet is allowed to pass before it dies (for example, a packet with a TTL of 16 will be allowed to go across 16 routers to get to its destination before it is discarded), + unsigned ttl:8; + /// 8 bits that contain the protocol (TCP, UDP, ICMP, etc...) + /// 0x01 ICMP + /// 0x06 TCP + /// 0x11 UDP + unsigned protocol:8; + /// 16 bits that contain the Header Checksum, a number used in error detection, + u16 header_checksum; + /// 32 bits that contain the source IP address, + IP_Address source; + /// 32 bits that contain the destination address. + IP_Address destination; + /// Zero-length field for memory mapping the packet data + unsigned char data[]; +} IP_PacketHeader; + +/// Convert from wire to host or host to wire endianness +inline void fix_endian_ip(IP_PacketHeader *packet) +{ + packet->version ^= packet->header_bytes_div4; + packet->header_bytes_div4 ^= packet->version; + packet->version ^= packet->header_bytes_div4; + fix_endian_u16(&packet->packet_bytes); + fix_endian_u16(&packet->fragment_id); + // Don't fix checksums; they are done bitwise +} + +/// Get a constant string of the given IP protocol (e.g. "ICMP", "TCP", "UDP") if known +inline const char *ipproto2name(u8 proto) +{ + switch (proto) + { + case 0x01: return "ICMP"; + case 0x02: return "IGMP"; + case 0x06: return "TCP"; + case 0x11: return "UDP"; + } + return "<UNKNOWN>"; +} + +/// Print the IP packet +inline void print_ip(IP_PacketHeader *packet) +{ + printf("IPv%d Packet: \n", packet->version); + if (packet->version != 4) + { + printf("Not an IPv4 packet (skipping)"); + return; + } + + u8 *dst = packet->destination.octet; + u8 *src = packet->source.octet; + printf(" Source: IP - %03d.%03d.%03d.%03d \n", src[0], src[1], src[2], src[3]); + printf(" Dest: IP - %03d.%03d.%03d.%03d \n", dst[0], dst[1], dst[2], dst[3]); + printf(" TTL: %d \n", packet->ttl); + printf(" Protocol: 0x%02X (%s) \n", packet->protocol, ipproto2name(packet->protocol)); + printf(" ToS: 0x%02X \n", packet->tos); + printf(" Header: %d bytes \n", packet->header_bytes_div4*4); + printf(" Packet: %d bytes \n", packet->packet_bytes); + printf(" Fragment: 0x%04X DF=%d MF=%d OFFSET=0x04X", packet->fragment_id, packet->dont_fragment, packet->more_follow, packet->fragment_offset); + printf(" Checksum: 0x%04X \n", packet->header_checksum); +} + +/// Parse the string (in decimal triple-dot notation) into the IP address structure +inline void str2ipaddr(const char *ip, IP_Address *addr) +{ + static short a,b,c,d; + sscanf(ip, "%3hd.%3hd.%3hd.%3hd", &a, &b, &c, &d); + addr->octet[0] = a; + addr->octet[1] = b; + addr->octet[2] = c; + addr->octet[3] = d; +} + +#endif \ No newline at end of file