📄 libnet_build_ip.c
字号:
{ return (-1); } memset(&ip_hdr, 0, sizeof(ip_hdr)); ip_hdr.ip_v = 4; /* version 4 */ ip_hdr.ip_hl = 5; /* 20 byte header */ /* check to see if there are IP options to include */ if (p->prev) { if (p->prev->type == LIBNET_PBLOCK_IPO_H) { /* * Count up number of 32-bit words in options list, padding if * neccessary. */ for (i = 0, j = 0; i < p->prev->b_len; i++) { (i % 4) ? j : j++; } ip_hdr.ip_hl += j; } } ip_hdr.ip_tos = 0; /* IP tos */ ip_hdr.ip_len = htons(h); /* total length */ ip_hdr.ip_id = htons((l->ptag_state) & 0x0000ffff); /* IP ID */ ip_hdr.ip_off = 0; /* fragmentation flags */ ip_hdr.ip_ttl = 64; /* time to live */ ip_hdr.ip_p = prot; /* transport protocol */ ip_hdr.ip_sum = 0; /* checksum */ ip_hdr.ip_src.s_addr = src; /* source ip */ ip_hdr.ip_dst.s_addr = dst; /* destination ip */ n = libnet_pblock_append(l, p, (u_int8_t *)&ip_hdr, LIBNET_IPV4_H); if (n == -1) { goto bad; } libnet_pblock_setflags(p, LIBNET_PBLOCK_DO_CHECKSUM); return (libnet_pblock_update(l, p, LIBNET_IPV4_H, LIBNET_PBLOCK_IPV4_H));bad: libnet_pblock_delete(l, p); return (-1);}libnet_ptag_tlibnet_build_ipv4_options(u_int8_t *options, u_int32_t options_s, libnet_t *l, libnet_ptag_t ptag){ int offset, underflow; u_int32_t i, j, n, adj_size; libnet_pblock_t *p, *p_temp; struct libnet_ipv4_hdr *ip_hdr; if (l == NULL) { return (-1); } underflow = 0; offset = 0; /* check options list size */ if (options_s > LIBNET_MAXOPTION_SIZE) { snprintf(l->err_buf, LIBNET_ERRBUF_SIZE, "%s(): options list is too large %d\n", __func__, options_s); return (-1); } adj_size = options_s; if (adj_size % 4) { /* size of memory block with padding */ adj_size += 4 - (options_s % 4); } /* if this pblock already exists, determine if there is a size diff */ if (ptag) { p_temp = libnet_pblock_find(l, ptag); if (p_temp) { if (adj_size >= p_temp->b_len) { offset = adj_size - p_temp->b_len; } else { offset = p_temp->b_len - adj_size; underflow = 1; } } else { /* * XXX - When this completes successfully, libnet errbuf contains * an error message so to come correct, we'll clear it. */ memset(l->err_buf, 0, sizeof (l->err_buf)); } } /* * Find the existing protocol block if a ptag is specified, or create * a new one. */ p = libnet_pblock_probe(l, ptag, adj_size, LIBNET_PBLOCK_IPO_H); if (p == NULL) { return (-1); } /* append options */ n = libnet_pblock_append(l, p, options, options_s); if (n == -1) { goto bad; } /* append padding */ n = libnet_pblock_append(l, p, "\0\0\0", adj_size - options_s); if (n == -1) { goto bad; } if (ptag && p->next) { p_temp = p->next; while ((p_temp->next) && (p_temp->type != LIBNET_PBLOCK_IPV4_H)) { p_temp = p_temp->next; } /* fix the IP header size */ if (p_temp->type == LIBNET_PBLOCK_IPV4_H) { /* * Count up number of 32-bit words in options list, padding if * neccessary. */ for (i = 0, j = 0; i < p->b_len; i++) { (i % 4) ? j : j++; } ip_hdr = (struct libnet_ipv4_hdr *) p_temp->buf; ip_hdr->ip_hl = j + 5; if (!underflow) { p_temp->h_len += offset; } else { p_temp->h_len -= offset; } } } return (ptag ? ptag : libnet_pblock_update(l, p, adj_size, LIBNET_PBLOCK_IPO_H));bad: libnet_pblock_delete(l, p); return (-1);}libnet_ptag_tlibnet_build_ipv6(u_int8_t tc, u_int32_t fl, u_int16_t len, u_int8_t nh, u_int8_t hl, struct libnet_in6_addr src, struct libnet_in6_addr dst, u_int8_t *payload, u_int32_t payload_s, libnet_t *l, libnet_ptag_t ptag){ u_int32_t n; libnet_pblock_t *p; struct libnet_ipv6_hdr ip_hdr; if (l == NULL) { return (-1); } n = LIBNET_IPV6_H + payload_s; /* size of memory block */ if (LIBNET_IPV6_H + payload_s > IP_MAXPACKET) { snprintf(l->err_buf, LIBNET_ERRBUF_SIZE, "%s(): IP packet too large\n", __func__); return (-1); } /* * Find the existing protocol block if a ptag is specified, or create * a new one. */ p = libnet_pblock_probe(l, ptag, n, LIBNET_PBLOCK_IPV6_H); if (p == NULL) { return (-1); } memset(&ip_hdr, 0, sizeof(ip_hdr)); ip_hdr.ip_flags[0] = 0x06 << 4; ip_hdr.ip_flags[1] = 0; ip_hdr.ip_flags[2] = 0; ip_hdr.ip_flags[3] = 0; /* XXX: TODO: traffic class, flow label */ ip_hdr.ip_len = htons(len); ip_hdr.ip_nh = nh; ip_hdr.ip_hl = hl; ip_hdr.ip_src = src; ip_hdr.ip_dst = dst; n = libnet_pblock_append(l, p, (u_int8_t *)&ip_hdr, LIBNET_IPV6_H); if (n == -1) { goto bad; } if ((payload && !payload_s) || (!payload && payload_s)) { snprintf(l->err_buf, LIBNET_ERRBUF_SIZE, "%s(): payload inconsistency\n", __func__); goto bad; } if (payload && payload_s) { n = libnet_pblock_append(l, p, payload, payload_s); if (n == -1) { goto bad; } } /* no checksum for IPv6 */ return (ptag ? ptag : libnet_pblock_update(l, p, LIBNET_IPV6_H, LIBNET_PBLOCK_IPV6_H));bad: libnet_pblock_delete(l, p); return (-1);}libnet_ptag_tlibnet_autobuild_ipv6(u_int16_t len, u_int8_t nh, struct libnet_in6_addr dst, libnet_t *l){ /* NYI */ snprintf(l->err_buf, LIBNET_ERRBUF_SIZE, "%s(): not yet implemented\n", __func__); return (-1);#if 0 struct libnet_in6_addr src = libnet_get_ipaddr6(l); if (strncmp((int8_t*)&src, (int8_t*)&in6addr_error, sizeof(in6addr_error)) == 0) { return (-1); } return (libnet_build_ipv6(0, 0, len, nh, 64, src, dst, NULL, 0, l, 0));#endif}/* EOF */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -