diff --git a/src/arp.c b/src/arp.c index f6b793a..dc00a04 100644 --- a/src/arp.c +++ b/src/arp.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2012 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -18,14 +18,15 @@ #include /* ETHERTYPE_* */ #include /* htons */ -#include /* malloc */ -#include /* memcmp, memset */ +#include /* memcmp */ #include "arp.h" #include "log.h" #include "transmitter.h" #include "wrapper.h" +#define ARP_PACKET_SIZE sizeof(struct s_ethernet) + sizeof(struct s_arp) + /** * Process ARP packets and reply to them. * @@ -39,7 +40,7 @@ int arp(struct s_ethernet *ethq, char *payload) { struct s_arp *arpq, *arpr; /* request and reply */ struct s_ethernet *ethr; - unsigned char *packet; + char packet[ARP_PACKET_SIZE]; arpq = (struct s_arp *) payload; @@ -55,16 +56,6 @@ int arp(struct s_ethernet *ethq, char *payload) return 1; } - /* compute the packet size */ - #define ARP_PACKET_SIZE sizeof(struct s_ethernet) + sizeof(struct s_arp) - - /* allocate enough memory */ - if ((packet = (unsigned char *) malloc(ARP_PACKET_SIZE)) == NULL) { - log_error("Lack of free memory"); - return 1; - } - memset(packet, 0x0, ARP_PACKET_SIZE); - /* define ethernet header and ARP offsets */ ethr = (struct s_ethernet *) packet; arpr = (struct s_arp *) (packet + sizeof(struct s_ethernet)); diff --git a/src/checksum.c b/src/checksum.c index 167285c..62849dd 100644 --- a/src/checksum.c +++ b/src/checksum.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -17,13 +17,13 @@ */ #include /* htonl */ -#include /* malloc */ #include /* memcpy */ #include "checksum.h" #include "ipv4.h" #include "ipv6.h" #include "log.h" +#include "wrapper.h" /** * General checksum computation function. @@ -49,9 +49,9 @@ unsigned short checksum(const void *data, int length) } if (length) { - unsigned char temp[2]; + char temp[2]; - temp[0] = *(unsigned char *) buf; + temp[0] = *(char *) buf; temp[1] = 0; sum += *(unsigned short *) temp; @@ -121,16 +121,10 @@ unsigned short checksum_update(unsigned short old_sum, unsigned short checksum_ipv4(struct s_ipv4_addr ip_src, struct s_ipv4_addr ip_dest, unsigned short length, unsigned char proto, - unsigned char *payload) + char *payload) { - unsigned char *buffer; + char buffer[PACKET_BUFFER]; struct s_ipv4_pseudo *header; - unsigned short sum; - - if ((buffer = malloc(sizeof(struct s_ipv4_pseudo) + length)) == NULL) { - log_error("Lack of free memory"); - return 0; - } header = (struct s_ipv4_pseudo *) buffer; @@ -142,11 +136,7 @@ unsigned short checksum_ipv4(struct s_ipv4_addr ip_src, memcpy(buffer + sizeof(struct s_ipv4_pseudo), payload, (int) length); - sum = checksum(buffer, sizeof(struct s_ipv4_pseudo) + (int) length); - - free(buffer); - - return sum; + return checksum(buffer, sizeof(struct s_ipv4_pseudo) + (int) length); } /** @@ -163,16 +153,10 @@ unsigned short checksum_ipv4(struct s_ipv4_addr ip_src, unsigned short checksum_ipv6(struct s_ipv6_addr ip_src, struct s_ipv6_addr ip_dest, unsigned short length, unsigned char proto, - unsigned char *payload) + char *payload) { - unsigned char *buffer; + char buffer[PACKET_BUFFER]; struct s_ipv6_pseudo *header; - unsigned short sum; - - if ((buffer = malloc(sizeof(struct s_ipv6_pseudo) + length)) == NULL) { - log_error("Lack of free memory"); - return 0; - } header = (struct s_ipv6_pseudo *) buffer; @@ -184,11 +168,7 @@ unsigned short checksum_ipv6(struct s_ipv6_addr ip_src, memcpy(buffer + sizeof(struct s_ipv6_pseudo), payload, (int) length); - sum = checksum(buffer, sizeof(struct s_ipv6_pseudo) + (int) length); - - free(buffer); - - return sum; + return checksum(buffer, sizeof(struct s_ipv6_pseudo) + (int) length); } /** diff --git a/src/checksum.h b/src/checksum.h index 91c6ffc..9911ee3 100644 --- a/src/checksum.h +++ b/src/checksum.h @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2012 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -28,10 +28,10 @@ unsigned short checksum_update(unsigned short old_sum, unsigned short *new_data, short new_len); unsigned short checksum_ipv4(struct s_ipv4_addr ip_src, struct s_ipv4_addr ip_dest, unsigned short length, - unsigned char proto, unsigned char *payload); + unsigned char proto, char *payload); unsigned short checksum_ipv6(struct s_ipv6_addr ip_src, struct s_ipv6_addr ip_dest, unsigned short length, - unsigned char proto, unsigned char *payload); + unsigned char proto, char *payload); unsigned short checksum_ipv4_update(unsigned short old_sum, struct s_ipv6_addr ip6_src, struct s_ipv6_addr ip6_dest, diff --git a/src/icmp.c b/src/icmp.c index f81b09c..1a9f67d 100644 --- a/src/icmp.c +++ b/src/icmp.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 xHire + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -18,7 +18,6 @@ #include /* ETHERTYPE_* */ #include /* htons */ -#include /* malloc */ #include /* memcpy, memset */ #include "checksum.h" @@ -33,12 +32,12 @@ #include "wrapper.h" /* declarations */ -int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, - unsigned char *packet, unsigned short *packet_len, +int sub_icmp4_error(char *payload, unsigned short payload_size, + char *packet, unsigned short *packet_len, struct s_icmp **icmp, struct s_nat **connection); int sub_icmp6_error(struct s_ethernet *eth6, - unsigned char *payload, unsigned short payload_size, - unsigned char *packet, unsigned short *packet_len, + char *payload, unsigned short payload_size, + char *packet, unsigned short *packet_len, struct s_icmp **icmp, struct s_nat **connection); /** @@ -60,11 +59,11 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, struct s_icmp *icmp; unsigned int *icmp_extra; unsigned short *icmp_extra_s; - unsigned char *icmp_extra_c; - unsigned char *icmp_data; + char *icmp_extra_c; + char *icmp_data; struct s_nat *connection; unsigned short orig_checksum; - unsigned char packet[PACKET_BUFFER]; + char packet[PACKET_BUFFER]; unsigned short new_len = sizeof(struct s_ethernet) + sizeof(struct s_ipv6); @@ -83,12 +82,12 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, } icmp = (struct s_icmp *) payload; - icmp_data = (unsigned char *) (payload + sizeof(struct s_icmp)); + icmp_data = payload + sizeof(struct s_icmp); /* ICMP checksum recheck */ orig_checksum = icmp->checksum; icmp->checksum = 0; - icmp->checksum = checksum((unsigned char *) icmp, payload_size); + icmp->checksum = checksum((char *) icmp, payload_size); if (icmp->checksum != orig_checksum) { /* packet is corrupted and shouldn't be processed */ @@ -120,13 +119,13 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, /* copy the payload data */ if (payload_size < mtu - sizeof(struct s_ipv6)) { - memcpy(&packet[new_len], payload, payload_size); - icmp = (struct s_icmp *) &packet[new_len]; + memcpy(packet + new_len, payload, payload_size); + icmp = (struct s_icmp *) (packet + new_len); new_len += payload_size; } else { - memcpy(&packet[new_len], payload, mtu - + memcpy(packet + new_len, payload, mtu - sizeof(struct s_ipv6)); - icmp = (struct s_icmp *) &packet[new_len]; + icmp = (struct s_icmp *) (packet + new_len); new_len += mtu - sizeof(struct s_ipv6); } @@ -142,17 +141,17 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, } eip4 = (struct s_ipv4 *) (icmp_data + 4); - eip6 = (struct s_ipv6 *) &packet[ + eip6 = (struct s_ipv6 *) (packet + sizeof(struct s_ethernet) + sizeof(struct s_ipv6) + - sizeof(struct s_icmp) + 4]; + sizeof(struct s_icmp) + 4); /* translate ICMP type&code */ if (icmp->code == 2) { icmp->type = ICMPV6_PARAM_PROBLEM; icmp->code = 1; icmp_extra = (unsigned int *) - (((unsigned char *) icmp) + + ((char *) icmp + sizeof(struct s_icmp)); if (eip6->next_header == IPPROTO_FRAGMENT) { @@ -166,10 +165,10 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, icmp->type = ICMPV6_PKT_TOO_BIG; icmp->code = 0; icmp_extra = (unsigned int *) - (((unsigned char *) icmp) + + ((char *) icmp + sizeof(struct s_icmp)); icmp_extra_s = (unsigned short *) - (((unsigned char *) icmp) + + ((char *) icmp + sizeof(struct s_icmp) + 2); if (ntohs(*icmp_extra_s) < 68) { *icmp_extra = htonl( @@ -240,9 +239,9 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, if (icmp->code == 0 || icmp->code == 2) { /* update the extra field */ icmp_extra = (unsigned int *) - (((unsigned char *) icmp) + + ((char *) icmp + sizeof(struct s_icmp)); - icmp_extra_c = (unsigned char *) icmp_extra; + icmp_extra_c = (char *) icmp_extra; switch (*icmp_extra_c) { case 0: case 1: @@ -306,7 +305,7 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, } eth6 = (struct s_ethernet *) packet; - ip6 = (struct s_ipv6 *) &packet[sizeof(struct s_ethernet)]; + ip6 = (struct s_ipv6 *) (packet + sizeof(struct s_ethernet)); /* build ethernet header */ eth6->dest = connection->mac; @@ -329,7 +328,7 @@ int icmp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, icmp->checksum = checksum_ipv6(ip6->ip_src, ip6->ip_dest, new_len - sizeof(struct s_ethernet) - sizeof(struct s_ipv6), IPPROTO_ICMPV6, - (unsigned char *) icmp); + (char *) icmp); /* send translated packet */ transmit_raw(packet, new_len); @@ -353,12 +352,12 @@ int icmp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) struct s_icmp *icmp; unsigned int *icmp_extra; unsigned short *icmp_extra_s; - unsigned char *icmp_extra_c; - unsigned char *icmp_data; + char *icmp_extra_c; + char *icmp_data; struct s_nat *connection; unsigned short orig_checksum; unsigned short payload_size; - unsigned char packet[PACKET_BUFFER - sizeof(struct s_ethernet)]; + char packet[PACKET_BUFFER - sizeof(struct s_ethernet)]; unsigned short new_len = sizeof(struct s_ipv4); struct s_icmp_echo *echo; @@ -374,14 +373,14 @@ int icmp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) } icmp = (struct s_icmp *) payload; - icmp_data = (unsigned char *) (payload + sizeof(struct s_icmp)); + icmp_data = payload + sizeof(struct s_icmp); /* checksum recheck */ orig_checksum = icmp->checksum; icmp->checksum = 0; icmp->checksum = checksum_ipv6(ip6->ip_src, ip6->ip_dest, payload_size, IPPROTO_ICMPV6, - (unsigned char *) icmp); + (char *) icmp); if (icmp->checksum != orig_checksum) { /* packet is corrupted and shouldn't be processed */ @@ -418,17 +417,18 @@ int icmp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) /* override information in original ICMP header */ icmp->type = ICMPV4_ECHO_REQUEST; + icmp = (struct s_icmp *) (packet + new_len); + /* copy the payload data */ /* IPv6 node can handle too big packets itself */ if (payload_size < 1500 - sizeof(struct s_ipv4)) { - memcpy(&packet[new_len], payload, payload_size); - icmp = (struct s_icmp *) &packet[new_len]; + memcpy(icmp, payload, payload_size); new_len += payload_size; } else { - memcpy(&packet[new_len], payload, 1500 - - sizeof(struct s_ipv4)); - icmp = (struct s_icmp *) &packet[new_len]; - new_len += 1500 - sizeof(struct s_ipv4); + memcpy(icmp, payload, + 1500 - sizeof(struct s_ipv4)); + /* before new_len was only the size of s_ipv4 */ + new_len = 1500; } break; @@ -497,9 +497,9 @@ int icmp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) /* update the extra field */ icmp_extra = (unsigned int *) - (((unsigned char *) icmp) + + ((char *) icmp + sizeof(struct s_icmp)); - icmp_extra_c = (unsigned char *) icmp_extra; + icmp_extra_c = (char *) icmp_extra; switch (*icmp_extra) { case 0: case 1: @@ -572,11 +572,9 @@ int icmp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) icmp->code = 4; icmp_extra = (unsigned int *) - (((unsigned char *) icmp) + - sizeof(struct s_icmp)); + ((char *) icmp + sizeof(struct s_icmp)); icmp_extra_s = (unsigned short *) - (((unsigned char *) icmp) + - sizeof(struct s_icmp) + 2); + ((char *) icmp + sizeof(struct s_icmp) + 2); if (eip6->next_header != IPPROTO_FRAGMENT) { *icmp_extra_s = htons(ntohl(*icmp_extra) - 20); } else { @@ -617,13 +615,12 @@ int icmp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) /* compute ICMP checksum */ icmp->checksum = 0x0; - icmp->checksum = checksum((unsigned char *) icmp, new_len - + icmp->checksum = checksum((char *) icmp, new_len - sizeof(struct s_ipv4)); /* compute IPv4 checksum */ ip4->checksum = checksum_ipv4(ip4->ip_src, ip4->ip_dest, - new_len, IPPROTO_ICMP, - (unsigned char *) icmp); + new_len, IPPROTO_ICMP, (char *) icmp); /* send translated packet */ transmit_ipv4(&ip4->ip_dest, packet, new_len); @@ -644,7 +641,7 @@ int icmp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) int icmp_ndp(struct s_ethernet *ethq, struct s_ipv6 *ipq, struct s_icmp_ndp_ns *ndp_ns) { - unsigned char *packet; + char packet[PACKET_BUFFER]; struct s_ethernet *ethr; struct s_ipv6 *ipr; struct s_icmp *icmp; @@ -655,15 +652,11 @@ int icmp_ndp(struct s_ethernet *ethq, struct s_ipv6 *ipq, return 1; } - /* allocate memory for reply packet */ + /* prepare memory for reply packet */ #define NDP_PACKET_SIZE sizeof(struct s_ethernet) + \ sizeof(struct s_ipv6) + \ sizeof(struct s_icmp) + \ sizeof(struct s_icmp_ndp_na) - if ((packet = (unsigned char *) malloc(NDP_PACKET_SIZE)) == NULL) { - log_error("Lack of free memory"); - return 1; - } memset(packet, 0x0, NDP_PACKET_SIZE); /* divide reply packet into parts */ @@ -703,14 +696,11 @@ int icmp_ndp(struct s_ethernet *ethq, struct s_ipv6 *ipq, /* compute ICMP checksum */ icmp->checksum = checksum_ipv6(ipr->ip_src, ipr->ip_dest, htons(ipr->len), IPPROTO_ICMPV6, - (unsigned char *) icmp); + (char *) icmp); /* send NDP reply */ transmit_raw(packet, NDP_PACKET_SIZE); - /* clean-up */ - free(packet); - return 0; } @@ -727,12 +717,13 @@ int icmp_ndp(struct s_ethernet *ethq, struct s_ipv6 *ipq, * @return 1 for failure */ int icmp4_error(struct s_ipv4_addr ip_dest, unsigned char type, - unsigned char code, unsigned char *data, unsigned short length) + unsigned char code, char *data, unsigned short length) { - unsigned char *packet, *payload; - unsigned int *unused; - struct s_ipv4 *ip4; - struct s_icmp *icmp; + char packet[PACKET_BUFFER]; + char *payload; + unsigned int *unused; + struct s_ipv4 *ip4; + struct s_icmp *icmp; /* 4 = unused space after ICMP header */ unsigned short payload_size = length > 1500 - sizeof(struct s_ipv4) - @@ -740,18 +731,11 @@ int icmp4_error(struct s_ipv4_addr ip_dest, unsigned char type, 1500 - sizeof(struct s_ipv4) - sizeof(struct s_icmp) - 4 : length; - if ((packet = (unsigned char *) malloc(sizeof(struct s_ipv4) + - sizeof(struct s_icmp) + 4 + payload_size)) == NULL) { - log_error("Lack of free memory"); - return 1; - } - ip4 = (struct s_ipv4 *) packet; icmp = (struct s_icmp *) (packet + sizeof(struct s_ipv4)); unused = (unsigned int *) (packet + sizeof(struct s_ipv4) + sizeof(struct s_icmp)); - payload = (unsigned char *) (packet + sizeof(struct s_ipv4) + - sizeof(struct s_icmp) + 4); + payload = packet + sizeof(struct s_ipv4) + sizeof(struct s_icmp) + 4; /* build IPv4 packet */ ip4->ver_hdrlen = 0x45; /* ver 4, header length 20 B */ @@ -777,20 +761,17 @@ int icmp4_error(struct s_ipv4_addr ip_dest, unsigned char type, memcpy(payload, data, payload_size); /* compute ICMP checksum */ - icmp->checksum = checksum((unsigned char *) icmp, + icmp->checksum = checksum((char *) icmp, payload_size + 4 + sizeof(struct s_icmp)); /* compute IPv4 checksum */ ip4->checksum = checksum_ipv4(ip4->ip_src, ip4->ip_dest, htons(ip4->len), IPPROTO_ICMP, - (unsigned char *) icmp); + (char *) icmp); /* send packet */ transmit_ipv4(&ip4->ip_dest, packet, htons(ip4->len)); - /* clean-up */ - free(packet); - return 0; } @@ -808,14 +789,15 @@ int icmp4_error(struct s_ipv4_addr ip_dest, unsigned char type, * @return 1 for failure */ int icmp6_error(struct s_mac_addr mac_dest, struct s_ipv6_addr ip_dest, - unsigned char type, unsigned char code, unsigned char *data, + unsigned char type, unsigned char code, char *data, unsigned short length) { - unsigned char *packet, *payload; - unsigned int *unused; + char packet[PACKET_BUFFER]; + char *payload; + unsigned int *unused; struct s_ethernet *eth; - struct s_ipv6 *ip6; - struct s_icmp *icmp; + struct s_ipv6 *ip6; + struct s_icmp *icmp; /* 4 = unused space after ICMP header */ /* 1280 -- because RFC on ICMPv6 says so */ @@ -824,13 +806,6 @@ int icmp6_error(struct s_mac_addr mac_dest, struct s_ipv6_addr ip_dest, 1280 - sizeof(struct s_ipv6) - sizeof(struct s_icmp) - 4 : length; - if ((packet = (unsigned char *) malloc(sizeof(struct s_ethernet) + - sizeof(struct s_ipv6) + sizeof(struct s_icmp) + 4 + - payload_size)) == NULL) { - log_error("Lack of free memory"); - return 1; - } - eth = (struct s_ethernet *) packet; ip6 = (struct s_ipv6 *) (packet + sizeof(struct s_ethernet)); icmp = (struct s_icmp *) (packet + sizeof(struct s_ethernet) + @@ -838,9 +813,8 @@ int icmp6_error(struct s_mac_addr mac_dest, struct s_ipv6_addr ip_dest, unused = (unsigned int *) (packet + sizeof(struct s_ethernet) + sizeof(struct s_ipv6) + sizeof(struct s_icmp)); - payload = (unsigned char *) (packet + sizeof(struct s_ethernet) + - sizeof(struct s_ipv6) + - sizeof(struct s_icmp) + 4); + payload = packet + sizeof(struct s_ethernet) + sizeof(struct s_ipv6) + + sizeof(struct s_icmp) + 4; /* ethernet */ eth->dest = mac_dest; @@ -869,16 +843,12 @@ int icmp6_error(struct s_mac_addr mac_dest, struct s_ipv6_addr ip_dest, /* compute ICMP checksum */ icmp->checksum = checksum_ipv6(host_ipv6_addr, ip_dest, sizeof(struct s_icmp) + 4 + payload_size, - IPPROTO_ICMPV6, - (unsigned char *) icmp); + IPPROTO_ICMPV6, (char *) icmp); /* send packet */ transmit_raw(packet, sizeof(struct s_ethernet) + sizeof(struct s_ipv6) + sizeof(struct s_icmp) + 4 + payload_size); - /* clean-up */ - free(packet); - return 0; } @@ -895,18 +865,18 @@ int icmp6_error(struct s_mac_addr mac_dest, struct s_ipv6_addr ip_dest, * @return 0 for success * @return 1 for failure */ -int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, - unsigned char *packet, unsigned short *packet_len, +int sub_icmp4_error(char *payload, unsigned short payload_size, + char *packet, unsigned short *packet_len, struct s_icmp **icmp, struct s_nat **connection) { - struct s_ipv4 *eip4; - struct s_ipv6 *eip6; - struct s_tcp *etcp; - struct s_udp *eudp; - struct s_icmp *eicmp; - unsigned short eip4_hlen; - struct s_ipv6_fragment *eip6_frag; - struct s_icmp_echo *echo; + struct s_ipv4 *eip4; + struct s_ipv6 *eip6; + struct s_tcp *etcp; + struct s_udp *eudp; + struct s_icmp *eicmp; + unsigned short eip4_hlen; + struct s_ipv6_fragment *eip6_frag; + struct s_icmp_echo *echo; /* sanity check */ if (payload_size < 1) { @@ -932,8 +902,8 @@ int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, /* define new inner IPv6 header */ /* new_len+4+4+40=102 < 1280 */ - eip6 = (struct s_ipv6 *) &packet[*packet_len + sizeof(struct s_icmp) + - 4]; + eip6 = (struct s_ipv6 *) (packet + *packet_len + sizeof(struct s_icmp) + + 4); /* we'll need this right now */ ipv4_to_ipv6(&eip4->ip_dest, &eip6->ip_dest); @@ -1016,8 +986,8 @@ int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, } /* copy ICMP header to new packet */ - memcpy(&packet[*packet_len], *icmp, sizeof(struct s_icmp) + 4); - *icmp = (struct s_icmp *) &packet[*packet_len]; + memcpy(packet + *packet_len, *icmp, sizeof(struct s_icmp) + 4); + *icmp = (struct s_icmp *) (packet + *packet_len); /* complete inner IPv6 header */ eip6->ver = 0x60 | (eip4->tos >> 4); @@ -1035,7 +1005,7 @@ int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, /* was the IPv4 packet fragmented? */ if (ntohs(eip4->flags_offset) & 0x1fff) { - eip6_frag = (struct s_ipv6_fragment *) &packet[*packet_len]; + eip6_frag = (struct s_ipv6_fragment *) (packet + *packet_len); if (ntohs(eip4->flags_offset) & IPV4_FLAG_MORE_FRAGMENTS) { eip6_frag->offset_flag = htons(((ntohs(eip4-> @@ -1051,9 +1021,9 @@ int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, eip6->len = htons(ntohs(eip4->len) - eip4_hlen + sizeof(struct s_ipv6_fragment)); - eip6_frag->next_header = eip6->next_header; - eip6->next_header = IPPROTO_FRAGMENT; - eip6_frag->id = htonl(ntohs(eip4->id)); + eip6_frag->next_header = eip6->next_header; + eip6_frag->id = htonl(ntohs(eip4->id)); + eip6->next_header = IPPROTO_FRAGMENT; *packet_len += sizeof(struct s_ipv6_fragment); } else { @@ -1064,11 +1034,11 @@ int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, /* we can afford to use full MTU instead of just 1280 B as admin * warrants this to us */ if (payload_size > mtu + sizeof(struct s_ethernet) - *packet_len) { - memcpy(&packet[*packet_len], payload, + memcpy(packet + *packet_len, payload, mtu + sizeof(struct s_ethernet) - *packet_len); - *packet_len = mtu; + *packet_len = mtu + sizeof(struct s_ethernet); } else { - memcpy(&packet[*packet_len], payload, payload_size); + memcpy(packet + *packet_len, payload, payload_size); *packet_len += payload_size; } @@ -1090,17 +1060,17 @@ int sub_icmp4_error(unsigned char *payload, unsigned short payload_size, * @return 1 for failure */ int sub_icmp6_error(struct s_ethernet *eth6, - unsigned char *payload, unsigned short payload_size, - unsigned char *packet, unsigned short *packet_len, + char *payload, unsigned short payload_size, + char *packet, unsigned short *packet_len, struct s_icmp **icmp, struct s_nat **connection) { - struct s_ipv4 *eip4; - struct s_ipv6 *eip6; - struct s_ipv6_fragment *eip6_frag; - struct s_tcp *etcp; - struct s_udp *eudp; - struct s_icmp *eicmp; - struct s_icmp_echo *echo; + struct s_ipv4 *eip4; + struct s_ipv6 *eip6; + struct s_ipv6_fragment *eip6_frag; + struct s_tcp *etcp; + struct s_udp *eudp; + struct s_icmp *eicmp; + struct s_icmp_echo *echo; unsigned char skip_l4 = 0; @@ -1116,8 +1086,8 @@ int sub_icmp6_error(struct s_ethernet *eth6, /* define new inner IPv4 header */ /* new_len+4+4+20=48 < 576 */ - eip4 = (struct s_ipv4 *) &packet[*packet_len + sizeof(struct s_icmp) + - 4]; + eip4 = (struct s_ipv4 *) (packet + *packet_len + sizeof(struct s_icmp) + + 4); /* we'll need this right now */ ipv6_to_ipv4(&eip6->ip_src, &eip4->ip_src); @@ -1247,8 +1217,8 @@ int sub_icmp6_error(struct s_ethernet *eth6, } /* copy ICMP header to new packet */ - memcpy(&packet[*packet_len], *icmp, sizeof(struct s_icmp) + 4); - *icmp = (struct s_icmp *) &packet[*packet_len]; + memcpy(packet + *packet_len, *icmp, sizeof(struct s_icmp) + 4); + *icmp = (struct s_icmp *) (packet + *packet_len); /* complete inner IPv4 header */ eip4->ver_hdrlen = 0x45; /* ver 4, header length 20 B */ @@ -1263,16 +1233,16 @@ int sub_icmp6_error(struct s_ethernet *eth6, eip4->proto = IPPROTO_ICMP; } - /* packet_len == sizeof(IPv4) */ + /* packet_len == sizeof(outer IPv4 header) */ *packet_len += sizeof(struct s_icmp) + 4 + sizeof(struct s_ipv4); /* copy payload */ /* let's use 576 as an IPv4 MTU */ if (payload_size > 576 - *packet_len) { - memcpy(&packet[*packet_len], payload, 576 - *packet_len); + memcpy(packet + *packet_len, payload, 576 - *packet_len); *packet_len = 576; } else { - memcpy(&packet[*packet_len], payload, payload_size); + memcpy(packet + *packet_len, payload, payload_size); *packet_len += payload_size; } diff --git a/src/icmp.h b/src/icmp.h index 5e6e197..85d0577 100644 --- a/src/icmp.h +++ b/src/icmp.h @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -84,9 +84,9 @@ int icmp_ndp(struct s_ethernet *ethq, struct s_ipv6 *ipq, struct s_icmp_ndp_ns *ndp_ns); int icmp4_error(struct s_ipv4_addr ip_dest, unsigned char type, - unsigned char code, unsigned char *data, unsigned short length); + unsigned char code, char *data, unsigned short length); int icmp6_error(struct s_mac_addr mac_dest, struct s_ipv6_addr ip_dest, - unsigned char type, unsigned char code, unsigned char *data, + unsigned char type, unsigned char code, char *data, unsigned short length); #endif /* ICMP_H */ diff --git a/src/ipv4.c b/src/ipv4.c index 26a0204..48f1e51 100644 --- a/src/ipv4.c +++ b/src/ipv4.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -63,7 +63,7 @@ int ipv4(struct s_ethernet *eth, char *packet) payload[0] & 0x08) && !(ip->flags_offset & htons(0x1fff))) { /* code 0 = ttl exceeded in transmit */ icmp4_error(ip->ip_src, ICMPV4_TIME_EXCEEDED, 0, - (unsigned char *) packet, htons(ip->len)); + packet, htons(ip->len)); } return 1; } else { diff --git a/src/ipv6.c b/src/ipv6.c index 9c5cefa..8dc9f9b 100644 --- a/src/ipv6.c +++ b/src/ipv6.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -56,7 +56,7 @@ int ipv6(struct s_ethernet *eth, char *packet) if (ip->next_header != IPPROTO_ICMPV6 || payload[0] & 0x80) { /* code 0 = hl exceeded in transmit */ icmp6_error(eth->src, ip->ip_src, ICMPV6_TIME_EXCEEDED, - 0, (unsigned char *) packet, + 0, packet, htons(ip->len) + sizeof(struct s_ipv6)); } return 1; diff --git a/src/tcp.c b/src/tcp.c index 2b257f7..d3091ed 100644 --- a/src/tcp.c +++ b/src/tcp.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 xHire + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -48,12 +48,12 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, unsigned short payload_size) { - struct s_tcp *tcp; - struct s_nat *connection; - unsigned short tmp_short; - unsigned char *packet; + struct s_tcp *tcp; + struct s_nat *connection; + unsigned short tmp_short; + char packet[PACKET_BUFFER]; - unsigned char *saved_packet; + char *saved_packet; struct s_nat_fragments *frag_conn; linkedlist_node_t *llnode; @@ -79,7 +79,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, tcp->checksum = 0; tcp->checksum = checksum_ipv4(ip4->ip_src, ip4->ip_dest, payload_size, IPPROTO_TCP, - (unsigned char *) tcp); + (char *) tcp); if (tcp->checksum != tmp_short) { /* packet is corrupted and shouldn't be @@ -184,11 +184,10 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, (char *) llnode->prev->data + sizeof(unsigned short) + sizeof(struct s_ethernet)), - (char *) ( - (char *) llnode->prev->data + + (char *) llnode->prev->data + sizeof(unsigned short) + sizeof(struct s_ethernet) + - sizeof(struct s_ipv4)), + sizeof(struct s_ipv4), tmp_short); free(llnode->prev->data); linkedlist_delete(frag_conn->queue, @@ -197,15 +196,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, } } - /* allocate enough memory for translated packet */ - if ((packet = (unsigned char *) malloc( - payload_size > mtu - sizeof(struct s_ipv6) ? - mtu + sizeof(struct s_ethernet) : - sizeof(struct s_ethernet) + sizeof(struct s_ipv6) + - payload_size)) == NULL) { - log_error("Lack of free memory"); - return 1; - } + /* translated packet */ eth6 = (struct s_ethernet *) packet; ip6 = (struct s_ipv6 *) (packet + sizeof(struct s_ethernet)); @@ -244,8 +235,8 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, ip6->next_header = IPPROTO_FRAGMENT; /* create IPv6 fragment header */ - frag = (struct s_ipv6_fragment *) ((unsigned char *) ip6 - + sizeof(struct s_ipv6)); + frag = (struct s_ipv6_fragment *) ((char *) ip6 + + sizeof(struct s_ipv6)); frag->next_header = IPPROTO_TCP; frag->zeros = 0x0; frag->offset_flag = htons(IPV6_FLAG_MORE_FRAGMENTS); @@ -253,8 +244,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, (unsigned int) rand(); /* copy the payload data */ - memcpy((unsigned char *) frag + - sizeof(struct s_ipv6_fragment), + memcpy((char *) frag + sizeof(struct s_ipv6_fragment), payload, FRAGMENT_LEN); /* send translated packet */ @@ -270,8 +260,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, frag->offset_flag = htons((FRAGMENT_LEN / 8) << 3); /* copy the payload data */ - memcpy((unsigned char *) frag + - sizeof(struct s_ipv6_fragment), + memcpy((char *) frag + sizeof(struct s_ipv6_fragment), payload + FRAGMENT_LEN, payload_size - FRAGMENT_LEN); @@ -285,7 +274,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, ip6->next_header = IPPROTO_TCP; /* copy the payload data */ - memcpy((unsigned char *) ip6 + sizeof(struct s_ipv6), + memcpy((char *) ip6 + sizeof(struct s_ipv6), payload, payload_size); /* send translated packet */ @@ -303,7 +292,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, log_debug("Incoming connection wasn't found in " "fragments table -- saving it"); - if ((saved_packet = (unsigned char *) malloc( + if ((saved_packet = (char *) malloc( sizeof(unsigned short) + sizeof(struct s_ethernet) + sizeof(struct s_ipv4) + payload_size)) == NULL) { log_error("Lack of free memory"); @@ -322,36 +311,25 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, /* save the packet and put it into the queue */ memcpy(saved_packet, &payload_size, sizeof(unsigned short)); - memcpy((unsigned char *) (saved_packet + - sizeof(unsigned short)), eth4, - sizeof(struct s_ethernet)); - memcpy((unsigned char *) (saved_packet + - sizeof(unsigned short) + - sizeof(struct s_ethernet)), ip4, - sizeof(struct s_ipv4)); - memcpy((unsigned char *) (saved_packet + - sizeof(unsigned short) + + memcpy(saved_packet + sizeof(unsigned short), + (char *) eth4, sizeof(struct s_ethernet)); + memcpy(saved_packet + sizeof(unsigned short) + + sizeof(struct s_ethernet), + (char *) ip4, sizeof(struct s_ipv4)); + memcpy(saved_packet + sizeof(unsigned short) + sizeof(struct s_ethernet) + - sizeof(struct s_ipv4)), payload, payload_size); + sizeof(struct s_ipv4), payload, payload_size); linkedlist_append(frag_conn->queue, saved_packet); return 0; } - /* allocate enough memory for translated packet */ - if ((packet = (unsigned char *) malloc( - payload_size > mtu - sizeof(struct s_ipv6) - - sizeof(struct s_ipv6_fragment) ? - mtu + sizeof(struct s_ethernet) : - sizeof(struct s_ethernet) + sizeof(struct s_ipv6) + - sizeof(struct s_ipv6_fragment) + payload_size)) == NULL) { - log_error("Lack of free memory"); - return 1; - } + /* translated packet */ eth6 = (struct s_ethernet *) packet; - ip6 = (struct s_ipv6 *) (packet + sizeof(struct s_ethernet)); - frag = (struct s_ipv6_fragment *) ((unsigned char *) ip6 + + ip6 = (struct s_ipv6 *) (packet + sizeof(struct s_ethernet)); + frag = (struct s_ipv6_fragment *) (packet + + sizeof(struct s_ethernet) + sizeof(struct s_ipv6)); /* build ethernet header */ @@ -386,8 +364,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, IPV6_FLAG_MORE_FRAGMENTS); /* copy the payload data */ - memcpy((unsigned char *) frag + - sizeof(struct s_ipv6_fragment), + memcpy((char *) frag + sizeof(struct s_ipv6_fragment), payload, FRAGMENT_LEN); /* send translated packet */ @@ -407,8 +384,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, } /* copy the payload data */ - memcpy((unsigned char *) frag + - sizeof(struct s_ipv6_fragment), + memcpy((char *) frag + sizeof(struct s_ipv6_fragment), payload + FRAGMENT_LEN, payload_size - FRAGMENT_LEN); @@ -432,7 +408,7 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, } /* copy the payload data */ - memcpy((unsigned char *) ip6 + sizeof(struct s_ipv6) + + memcpy((char *) ip6 + sizeof(struct s_ipv6) + sizeof(struct s_ipv6_fragment), payload, payload_size); @@ -444,9 +420,6 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, } } - /* clean-up */ - free(packet); - return 0; } @@ -463,11 +436,11 @@ int tcp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, */ int tcp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) { - struct s_tcp *tcp; - struct s_nat *connection; - unsigned short orig_checksum; - struct s_ipv4 *ip4; - unsigned char *packet; + struct s_tcp *tcp; + struct s_nat *connection; + unsigned short orig_checksum; + struct s_ipv4 *ip4; + char packet[PACKET_BUFFER]; /* parse TCP header */ tcp = (struct s_tcp *) payload; @@ -477,7 +450,7 @@ int tcp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) tcp->checksum = 0; tcp->checksum = checksum_ipv6(ip6->ip_src, ip6->ip_dest, htons(ip6->len), IPPROTO_TCP, - (unsigned char *) payload); + (char *) payload); if (tcp->checksum != orig_checksum) { /* packet is corrupted and shouldn't be processed */ @@ -560,12 +533,7 @@ int tcp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) } } - /* allocate memory for translated packet */ - if ((packet = (unsigned char *) malloc(sizeof(struct s_ipv4) + - htons(ip6->len))) == NULL) { - log_error("Lack of free memory"); - return 1; - } + /* translated packet */ ip4 = (struct s_ipv4 *) packet; /* build IPv4 packet */ @@ -600,8 +568,5 @@ int tcp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) /* send translated packet */ transmit_ipv4(&ip4->ip_dest, packet, htons(ip4->len)); - /* clean-up */ - free(packet); - return 0; } diff --git a/src/transmitter.c b/src/transmitter.c index bc60b13..d97b5f5 100644 --- a/src/transmitter.c +++ b/src/transmitter.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2012 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -119,7 +119,7 @@ int transmission_quit(void) * @return 0 for success * @return 1 for failure */ -int transmit_raw(unsigned char *data, unsigned int length) +int transmit_raw(char *data, unsigned int length) { if (sendto(sock, data, length, 0, (struct sockaddr *) &socket_address, sizeof(struct sockaddr_ll)) != (int) length) { @@ -142,8 +142,7 @@ int transmit_raw(unsigned char *data, unsigned int length) * @return 0 for success * @return 1 for failure */ -int transmit_ipv4(struct s_ipv4_addr *ip, unsigned char *data, - unsigned int length) +int transmit_ipv4(struct s_ipv4_addr *ip, char *data, unsigned int length) { /* set the destination IPv4 address */ memcpy(&socket_address_ipv4.sin_addr.s_addr, ip, diff --git a/src/transmitter.h b/src/transmitter.h index 81a55fe..36068f1 100644 --- a/src/transmitter.h +++ b/src/transmitter.h @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -23,8 +23,7 @@ int transmission_init(void); int transmission_quit(void); -int transmit_raw(unsigned char *data, unsigned int length); -int transmit_ipv4(struct s_ipv4_addr *ip, unsigned char *data, - unsigned int length); +int transmit_raw(char *data, unsigned int length); +int transmit_ipv4(struct s_ipv4_addr *ip, char *data, unsigned int length); #endif /* TRANSMITTER_H */ diff --git a/src/udp.c b/src/udp.c index 6972129..3e70ea5 100644 --- a/src/udp.c +++ b/src/udp.c @@ -1,6 +1,6 @@ /* * WrapSix - * Copyright (C) 2008-2013 Michal Zima + * Copyright (C) 2008-2017 xHire * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -18,7 +18,6 @@ #include /* ETHERTYPE_* */ #include /* htons */ -#include /* malloc */ #include /* memcpy */ #include "checksum.h" @@ -48,13 +47,13 @@ int udp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, unsigned short payload_size) { - struct s_udp *udp; - struct s_nat *connection; - unsigned short orig_checksum; - unsigned char *packet; + struct s_udp *udp; + struct s_nat *connection; + unsigned short orig_checksum; + char packet[PACKET_BUFFER]; struct s_ethernet *eth6; - struct s_ipv6 *ip6; + struct s_ipv6 *ip6; /* parse UDP header */ udp = (struct s_udp *) payload; @@ -65,7 +64,7 @@ int udp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, udp->checksum = 0; udp->checksum = checksum_ipv4(ip4->ip_src, ip4->ip_dest, payload_size, IPPROTO_UDP, - (unsigned char *) udp); + payload); if (udp->checksum != orig_checksum) { /* packet is corrupted and shouldn't be processed */ @@ -85,13 +84,7 @@ int udp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, linkedlist_move2end(timeout_udp, connection->llnode); - /* allocate memory for translated packet */ - if ((packet = (unsigned char *) malloc(sizeof(struct s_ethernet) + - sizeof(struct s_ipv6) + - payload_size)) == NULL) { - log_error("Lack of free memory"); - return 1; - } + /* translated packet */ eth6 = (struct s_ethernet *) packet; ip6 = (struct s_ipv6 *) (packet + sizeof(struct s_ethernet)); @@ -124,7 +117,7 @@ int udp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, /* if original checksum was 0x0000, we need to compute it */ udp->checksum = checksum_ipv6(ip6->ip_src, ip6->ip_dest, payload_size, IPPROTO_UDP, - (unsigned char *) udp); + (char *) udp); } /* copy the payload data (with new checksum) */ @@ -135,9 +128,6 @@ int udp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, transmit_raw(packet, sizeof(struct s_ethernet) + sizeof(struct s_ipv6) + payload_size); - /* clean-up */ - free(packet); - return 0; } @@ -154,12 +144,12 @@ int udp_ipv4(struct s_ethernet *eth4, struct s_ipv4 *ip4, char *payload, */ int udp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) { - struct s_udp *udp; - struct s_nat *connection; - unsigned short orig_checksum; - struct s_ipv4 *ip4; - unsigned char *packet; - unsigned int packet_size; + struct s_udp *udp; + struct s_nat *connection; + unsigned short orig_checksum; + struct s_ipv4 *ip4; + char packet[PACKET_BUFFER]; + unsigned int packet_size; /* parse UDP header */ udp = (struct s_udp *) payload; @@ -168,8 +158,7 @@ int udp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) orig_checksum = udp->checksum; udp->checksum = 0; udp->checksum = checksum_ipv6(ip6->ip_src, ip6->ip_dest, - htons(ip6->len), IPPROTO_UDP, - (unsigned char *) payload); + htons(ip6->len), IPPROTO_UDP, payload); if (udp->checksum != orig_checksum) { /* packet is corrupted and shouldn't be processed */ @@ -193,13 +182,10 @@ int udp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) linkedlist_move2end(timeout_udp, connection->llnode); } - /* allocate memory for translated packet */ - packet_size = sizeof(struct s_ipv4) + htons(ip6->len); - if ((packet = (unsigned char *) malloc(packet_size)) == NULL) { - log_error("Lack of free memory"); - return 1; - } + + /* translated packet */ ip4 = (struct s_ipv4 *) packet; + packet_size = sizeof(struct s_ipv4) + htons(ip6->len); /* build IPv4 packet */ ip4->ver_hdrlen = 0x45; /* ver 4, header length 20 B */ @@ -233,8 +219,5 @@ int udp_ipv6(struct s_ethernet *eth6, struct s_ipv6 *ip6, char *payload) /* send translated packet */ transmit_ipv4(&ip4->ip_dest, packet, packet_size); - /* clean-up */ - free(packet); - return 0; }