123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125 |
- #include "../../lib/includes.h"
- #include "../state.h"
- #ifndef PACKET_H
- #define PACKET_H
- #define MAX_PACKET_SIZE 4096
- typedef unsigned short __attribute__((__may_alias__)) alias_unsigned_short;
- void make_eth_header(struct ether_header *ethh, macaddr_t *src, macaddr_t *dst);
- void make_ip_header(struct ip *iph, uint8_t, uint16_t);
- void make_tcp_header(struct tcphdr*, port_h_t);
- void make_icmp_header(struct icmp *);
- void make_udp_header(struct udphdr *udp_header, port_h_t dest_port,
- uint16_t len);
- void fprintf_ip_header(FILE *fp, struct ip *iph);
- void fprintf_eth_header(FILE *fp, struct ether_header *ethh);
- static inline unsigned short in_checksum(unsigned short *ip_pkt, int len)
- {
- unsigned long sum = 0;
- for (int nwords = len/2; nwords > 0; nwords--) {
- sum += *ip_pkt++;
- }
- sum = (sum >> 16) + (sum & 0xffff);
- sum += (sum >> 16);
- return (unsigned short) (~sum);
- }
- static inline uint32_t fletcher32( uint16_t const *data, size_t words )
- {
- // 1 word = 2 Bytes
- uint32_t sum1 = 0xffff, sum2 = 0xffff;
- while (words) {
- unsigned tlen = words > 359 ? 359 : words;
- words -= tlen;
- do {
- //sum2 += sum1 += *data++;
- sum2 += sum1 += htons(*data++);
- } while (--tlen);
- sum1 = (sum1 & 0xffff) + (sum1 >> 16);
- sum2 = (sum2 & 0xffff) + (sum2 >> 16);
- }
- /* Second reduction step to reduce sums to 16 bits */
- sum1 = (sum1 & 0xffff) + (sum1 >> 16);
- sum2 = (sum2 & 0xffff) + (sum2 >> 16);
- return sum2 << 16 | sum1;
- }
- __attribute__((unused)) static inline unsigned short zmap_ip_checksum(
- unsigned short *buf)
- {
- return in_checksum(buf, (int) sizeof(struct ip));
- }
- __attribute__((unused)) static inline unsigned short icmp_checksum(
- unsigned short *buf)
- {
- return in_checksum(buf, (int) sizeof(struct icmp));
- }
- static __attribute__((unused)) uint16_t tcp_checksum(unsigned short len_tcp,
- uint32_t saddr, uint32_t daddr, struct tcphdr *tcp_pkt)
- {
- alias_unsigned_short *src_addr = (alias_unsigned_short *) &saddr;
- alias_unsigned_short *dest_addr = (alias_unsigned_short *) &daddr;
- unsigned char prot_tcp = 6;
- unsigned long sum = 0;
- int nleft = len_tcp;
- unsigned short *w;
- w = (unsigned short *) tcp_pkt;
- // calculate the checksum for the tcp header and tcp data
- while(nleft > 1) {
- sum += *w++;
- nleft -= 2;
- }
- // if nleft is 1 there ist still on byte left.
- // We add a padding byte (0xFF) to build a 16bit word
- if (nleft > 0) {
- sum += *w & ntohs(0xFF00);
- }
- // add the pseudo header
- sum += src_addr[0];
- sum += src_addr[1];
- sum += dest_addr[0];
- sum += dest_addr[1];
- sum += htons(len_tcp);
- sum += htons(prot_tcp);
- sum = (sum >> 16) + (sum & 0xFFFF);
- sum += (sum >> 16);
- // Take the one's complement of sum
- return (unsigned short) (~sum);
- }
- // Returns 0 if dst_port is outside the expected valid range, non-zero otherwise
- static __attribute__((unused)) inline int check_dst_port(uint16_t port,
- int num_ports, uint32_t *validation)
- {
- if (port > zconf.source_port_last
- || port < zconf.source_port_first) {
- return -1;
- }
- int32_t to_validate = port - zconf.source_port_first;
- int32_t min = validation[1] % num_ports;
- int32_t max = (validation[1] + zconf.packet_streams - 1) % num_ports;
- return (((max - min) % num_ports) >= ((to_validate - min) % num_ports));
- }
- static __attribute__((unused)) inline uint16_t get_src_port(int num_ports,
- int probe_num, uint32_t *validation)
- {
- return zconf.source_port_first + ((validation[1] + probe_num) % num_ports);
- }
- // Note: caller must free return value
- char *make_ip_str(uint32_t ip);
- #endif
|