netsniff-ng: Allow to compile without libnl
[netsniff-ng-new.git] / staging / modifications.c
blob1affbbbd1f33783ed3ca432168722afe04b52578
1 /*
2 * Mausezahn - A fast versatile traffic generator
3 * Copyright (C) 2008-2010 Herbert Haas
4 *
5 * This program is free software; you can redistribute it and/or modify it under
6 * the terms of the GNU General Public License version 2 as published by the
7 * Free Software Foundation.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
12 * details.
14 * You should have received a copy of the GNU General Public License along with
15 * this program; if not, see http://www.gnu.org/licenses/gpl-2.0.html
22 // ***************************************************************************
23 //
24 // This sections contains functions to manipulate headers of
25 // Eth, MPLS, 802.1Q, IP, UDP, and TCP:
26 //
27 // int update_Eth_SA (libnet_t *l, libnet_ptag_t t)
28 // int update_IP_SA (libnet_t *l, libnet_ptag_t t)
29 // int update_IP_DA (libnet_t *l, libnet_ptag_t t)
30 // int update_IP6_SA (libnet_t *l, libnet_ptag_t t)
31 // int update_IP6_DA (libnet_t *l, libnet_ptag_t t)
32 // int update_DPORT (libnet_t *l, libnet_ptag_t t)
33 // int update_SPORT (libnet_t *l, libnet_ptag_t t)
34 // int update_TCP_SQNR (libnet_t *l, libnet_ptag_t t)
35 //
36 // and finally:
37 //
38 // int print_frame_details()
40 // ***************************************************************************
42 #include "mz.h"
43 #include "mops.h"
45 ///////////////////////////////////////////////////////////////////////////
46 // Applies another random Ethernet source address to a given Ethernet-PTAG.
47 // (The calling function should check 'tx.eth_src_rand' whether the SA
48 // should be randomized.)
49 //
50 int update_Eth_SA(libnet_t *l, libnet_ptag_t t)
52 tx.eth_src[0] = (u_int8_t) ( ((float) rand()/RAND_MAX)*256) & 0xFE; // keeps bcast-bit zero
53 tx.eth_src[1] = (u_int8_t) ( ((float) rand()/RAND_MAX)*256);
54 tx.eth_src[2] = (u_int8_t) ( ((float) rand()/RAND_MAX)*256);
55 tx.eth_src[3] = (u_int8_t) ( ((float) rand()/RAND_MAX)*256);
56 tx.eth_src[4] = (u_int8_t) ( ((float) rand()/RAND_MAX)*256);
57 tx.eth_src[5] = (u_int8_t) ( ((float) rand()/RAND_MAX)*256);
59 t = libnet_build_ethernet (tx.eth_dst,
60 tx.eth_src,
61 tx.eth_type,
62 NULL, // the payload
63 0,
64 l,
65 t);
67 if (t == -1)
69 fprintf(stderr, " mz/update_Eth_SA: Can't build Ethernet header: %s\n",
70 libnet_geterror(l));
71 exit(EXIT_FAILURE);
74 return 0;
78 // Update official timestamp, own timestamp and sequence number in the RTP header.
79 // The actual RTP message is stored in tx.udp_payload.
80 int update_RTP(libnet_t *l, libnet_ptag_t t)
82 u_int8_t *ptr;
83 struct mz_timestamp ts;
85 tx.rtp_sqnr++;
86 tx.rtp_stmp+=160; // TODO: different values for different codecs
88 // update SQNR
89 ptr = (u_int8_t*) &tx.rtp_sqnr;
90 tx.udp_payload[2] = *(ptr+1);
91 tx.udp_payload[3] = *ptr;
93 // update official timestamp
94 ptr = (u_int8_t*) &tx.rtp_stmp;
95 tx.udp_payload[4] = *(ptr+3);
96 tx.udp_payload[5] = *(ptr+2);
97 tx.udp_payload[6] = *(ptr+1);
98 tx.udp_payload[7] = *ptr;
101 // update own timestamp
102 getcurtime(&ts); // Now add TX timestamp:
103 mops_hton4 ((u_int32_t*) &ts.sec, &tx.udp_payload[16]);
104 mops_hton4 ((u_int32_t*) &ts.nsec, &tx.udp_payload[20]);
106 t = libnet_build_udp(tx.sp,
107 tx.dp,
108 tx.udp_len,
109 tx.udp_sum,
110 tx.udp_payload,
111 tx.udp_payload_s,
115 if (t == -1) {
116 fprintf(stderr," mz/send_frame: RTP header update failed!\n");
117 exit (1);
119 return 0;
123 ///////////////////////////////////////////////////////////////////////////
124 // Applies another SOURCE IP address,
125 // - either a random one (tx.ip_src_rand==1)
126 // - or from a specified range (tx.ip_src_isrange==1)
127 // to a given IP-PTAG.
129 // Note: tx.ip_src MUST be already initialized with tx.ip_src_start.
130 // This is done by 'get_ip_range_src()' in tools.c.
133 // RETURNS '1' if tx.ip_src restarts
135 int update_IP_SA (libnet_t *l, libnet_ptag_t t)
137 u_int8_t *x, *y;
138 int i=0;
140 if (ipv6_mode) {
141 return update_IP6_SA(l, t);
144 if (tx.ip_src_rand)
146 tx.ip_src_h = (u_int32_t) ( ((float) rand()/RAND_MAX)*0xE0000000); //this is 224.0.0.0
147 i=1;
149 else if (tx.ip_src_isrange)
151 tx.ip_src_h++;
152 if (tx.ip_src_h > tx.ip_src_stop) // reached the end of the range => restart!
154 tx.ip_src_h = tx.ip_src_start;
155 i=1;
159 // Now convert "tx.ip_src_h" into "tx.ip_src" which is in 'Network Byte Order':
160 x = (unsigned char*) &tx.ip_src_h;
161 y = (unsigned char*) &tx.ip_src;
163 *y = *(x+3);
164 y++;
165 *y = *(x+2);
166 y++;
167 *y = *(x+1);
168 y++;
169 *y = *x;
171 // TODO: Omit certain IP addresses:
172 // E.g. if (rand_ip == tx.ip_src) goto rand_again; // never use true interface IP
173 // TODO: Check other address exceptions ...
175 t = libnet_build_ipv4 (tx.ip_len,
176 tx.ip_tos,
177 tx.ip_id,
178 tx.ip_frag,
179 tx.ip_ttl,
180 tx.ip_proto,
181 tx.ip_sum,
182 tx.ip_src, // possibly now random
183 tx.ip_dst,
184 (mode==IP) ? (tx.ip_payload_s) ? tx.ip_payload : NULL : NULL, // if e.g. mode=UDP ignore payload argument
185 (mode==IP) ? tx.ip_payload_s : 0,
189 if (t == -1)
191 fprintf(stderr," mz/update_IP_SA: IP address manipulation failed!\n");
192 exit (1);
195 return i;
200 update_IP6_SA(libnet_t *l, libnet_ptag_t t)
202 int i = 0;
203 if (tx.ip_src_rand) {
204 fprintf(stderr, "Random source addresses are not supported in IPv6 mode.\n");
205 exit(1);
206 } else if (tx.ip_src_isrange) {
207 if (incr_in6_addr(tx.ip6_src, &tx.ip6_src)
208 || (in6_addr_cmp(tx.ip6_src, tx.ip6_src_stop) > 0))
210 tx.ip6_src = tx.ip6_src_start;
211 i = 1;
215 t = libnet_build_ipv6(tx.ip_tos,
216 tx.ip_flow,
217 tx.ip_len,
218 tx.ip_proto,
219 tx.ip_ttl,
220 tx.ip6_src,
221 tx.ip6_dst,
222 (mode==IP) ? (tx.ip_payload_s) ? tx.ip_payload : NULL : NULL,
223 (mode==IP) ? tx.ip_payload_s : 0,
227 if (t == -1) {
228 fprintf(stderr," mz/update_IP6_SA: IP address manipulation failed!\n");
229 exit (1);
232 return i;
236 /////////////////////////////////////////////////////////////////////////////////////////
237 // Applies another DESTINATION IP address from a specified range (tx.ip_dst_isrange==1)
238 // to a given IP-PTAG.
240 // Note: tx.ip_dst MUST be already initialized with tx.ip_dst_start.
241 // tx.ip_dst_h 'mirrors' tx.ip_dst
242 // (i. e. tx.ip_dst_h is NOT in network byte order => easy to count)
243 // This is done by 'get_ip_range_dst()' in tools.c.
245 // RETURN VALUE: '1' if tx.ip_dst restarts
247 int update_IP_DA(libnet_t *l, libnet_ptag_t t)
249 u_int8_t *x, *y;
250 int i=0;
252 if (ipv6_mode) {
253 return update_IP6_DA(l, t);
256 if (tx.ip_dst_isrange)
258 tx.ip_dst_h++;
259 if (tx.ip_dst_h > tx.ip_dst_stop) // we reached the end of the range => restart!
261 tx.ip_dst_h = tx.ip_dst_start;
262 i=1;
267 // Now convert "tx.ip_dst_h" into "tx.ip_dst" which is in 'Network Byte Order':
269 x = (unsigned char*) &tx.ip_dst_h;
270 y = (unsigned char*) &tx.ip_dst;
272 *y = *(x+3);
273 y++;
274 *y = *(x+2);
275 y++;
276 *y = *(x+1);
277 y++;
278 *y = *x;
281 // TODO: Omit certain IP addresses:
282 // E.g. if (rand_ip == tx.ip_src) goto rand_again; // never use true interface IP
283 // TODO: Check other address exceptions ...
285 t = libnet_build_ipv4 (tx.ip_len,
286 tx.ip_tos,
287 tx.ip_id,
288 tx.ip_frag,
289 tx.ip_ttl,
290 tx.ip_proto,
291 tx.ip_sum,
292 tx.ip_src,
293 tx.ip_dst,
294 (mode==IP) ? (tx.ip_payload_s) ? tx.ip_payload : NULL : NULL, // if e.g. mode=UDP ignore payload argument
295 (mode==IP) ? tx.ip_payload_s : 0,
299 if (t == -1)
301 fprintf(stderr," mz/update_IP_DA: IP address manipulation failed!\n");
302 exit (1);
305 return i;
310 update_IP6_DA(libnet_t *l, libnet_ptag_t t)
312 int i = 0;
313 if (tx.ip_dst_isrange) {
314 if (incr_in6_addr(tx.ip6_dst, &tx.ip6_dst)
315 || (in6_addr_cmp(tx.ip6_dst, tx.ip6_dst_stop) > 0))
317 tx.ip6_dst = tx.ip6_dst_start;
318 i = 1;
322 t = libnet_build_ipv6(tx.ip_tos,
323 tx.ip_flow,
324 tx.ip_len,
325 tx.ip_proto,
326 tx.ip_ttl,
327 tx.ip6_src,
328 tx.ip6_dst,
329 (mode==IP) ? (tx.ip_payload_s) ? tx.ip_payload : NULL : NULL,
330 (mode==IP) ? tx.ip_payload_s : 0,
334 if (t == -1) {
335 fprintf(stderr," mz/update_IP6_DA: IP address manipulation failed!\n");
336 exit (1);
339 return i;
344 ///////////////////////////////////////////////////////////////////////////////////////
346 // Applies another DESTINATION PORT from a specified range to a given UDP- or TCP-PTAG.
348 // Note: tx.dp MUST be already initialized with tx.dp_start
349 // This is done by 'get_port_range()' in tools.c.
351 // RETURN VALUE: '1' if tx.dp restarts
353 int update_DPORT(libnet_t *l, libnet_ptag_t t)
355 // u_int32_t DP;
356 int i=0;
358 // DP = (u_int32_t) tx.dp;
359 // DP++;
360 tx.dp++;
363 // Exceeded range => restart:
364 if ((tx.dp > tx.dp_stop) || // we exceeded the end of the range
365 (tx.dp == 65535) ) // or exceeded the 16-bit range
367 tx.dp = tx.dp_start;
368 i=1;
372 if (mode==UDP)
374 t = libnet_build_udp(tx.sp,
375 tx.dp,
376 tx.udp_len,
377 tx.udp_sum,
378 (tx.udp_payload_s) ? tx.udp_payload : NULL,
379 tx.udp_payload_s,
383 if (t == -1)
385 fprintf(stderr," mz/send_frame: UDP header manipulation failed!\n");
386 exit (1);
389 else // TCP
391 t = libnet_build_tcp (tx.sp,
392 tx.dp,
393 tx.tcp_seq,
394 tx.tcp_ack,
395 tx.tcp_control,
396 tx.tcp_win,
397 tx.tcp_sum,
398 tx.tcp_urg,
399 tx.tcp_len,
400 (tx.tcp_payload_s) ? tx.tcp_payload : NULL,
401 tx.tcp_payload_s,
405 if (t == -1)
407 fprintf(stderr, " mz/update_DPORT: Can't build TCP header: %s\n", libnet_geterror(l));
408 exit (0);
412 return i;
416 ///////////////////////////////////////////////////////////////////////////////////
418 // Applies another SOURCE PORT from a specified range to a given UDP- or TCP-PTAG.
420 // Note: tx.sp MUST be already initialized with tx.sp_start
421 // This is done by 'get_port_range()' in tools.c.
423 // RETURN VALUE: '1' if tx.sp restarts
425 int update_SPORT(libnet_t *l, libnet_ptag_t t)
428 // u_int32_t SP;
429 int i=0;
431 // SP = (u_int32_t) tx.sp;
432 // SP++;
433 tx.sp++;
436 // Exceeded range => restart:
437 if ((tx.sp > tx.sp_stop) || // we exceeded the end of the range
438 (tx.sp == 65535) ) // or exceeded the 16-bit range
440 tx.sp = tx.sp_start;
441 i=1;
444 if (mode==UDP)
446 t = libnet_build_udp(tx.sp,
447 tx.dp,
448 tx.udp_len,
449 tx.udp_sum,
450 (tx.udp_payload_s) ? tx.udp_payload : NULL,
451 tx.udp_payload_s,
455 if (t == -1)
457 fprintf(stderr," mz/send_frame: UDP header manipulation failed!\n");
458 exit (1);
461 else // TCP
463 t = libnet_build_tcp (tx.sp,
464 tx.dp,
465 tx.tcp_seq,
466 tx.tcp_ack,
467 tx.tcp_control,
468 tx.tcp_win,
469 tx.tcp_sum,
470 tx.tcp_urg,
471 tx.tcp_len,
472 (tx.tcp_payload_s) ? tx.tcp_payload : NULL,
473 tx.tcp_payload_s,
477 if (t == -1)
479 fprintf(stderr, " mz/update_SPORT: Can't build TCP header: %s\n", libnet_geterror(l));
480 exit (0);
484 return i;
487 #define LIBNET_CKSUM_CARRY(x) \
488 (x = (x >> 16) + (x & 0xffff), (~(x + (x >> 16)) & 0xffff))
490 int update_USUM(libnet_t *l, libnet_ptag_t t)
492 int sum = 0;
493 unsigned int tmp;
495 if (tx.udp_sum != 0)
496 return 0;
498 sum += libnet_in_cksum((u_int16_t *) &tx.ip6_src, 16);
499 if (tx.ip_option_s && tx.ip6_segs)
500 sum += libnet_in_cksum((u_int16_t *) &tx.ip_option[tx.ip_option_s - 16], 16); // Use last IP address
501 else
502 sum += libnet_in_cksum((u_int16_t *) &tx.ip6_dst, 16);
504 tmp = htonl(tx.udp_len);
505 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
506 tmp = htonl(IPPROTO_UDP);
507 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
509 tmp = ((htons(tx.sp) << 16) + htons(tx.dp));
510 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
512 tmp = htons(tx.udp_len) << 16;
513 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
515 if (tx.udp_payload_s)
516 sum += libnet_in_cksum((u_int16_t *) tx.udp_payload, tx.udp_payload_s);
518 tx.udp_sum = ntohs(LIBNET_CKSUM_CARRY(sum));
520 t = libnet_build_udp(tx.sp,
521 tx.dp,
522 tx.udp_len,
523 tx.udp_sum,
524 tx.udp_payload_s ? tx.udp_payload : NULL,
525 tx.udp_payload_s,
528 tx.udp_sum = 0;
529 return t;
532 int update_TSUM(libnet_t *l, libnet_ptag_t t)
534 int sum = 0;
535 unsigned int tmp;
537 if (tx.tcp_sum != 0)
538 return 0;
540 sum += libnet_in_cksum((u_int16_t *) &tx.ip6_src, 16);
541 if (tx.ip_option_s && tx.ip6_segs)
542 sum += libnet_in_cksum((u_int16_t *) &tx.ip_option[tx.ip_option_s - 16], 16); // Use last IP address
543 else
544 sum += libnet_in_cksum((u_int16_t *) &tx.ip6_dst, 16);
546 tmp = htonl(tx.tcp_len);
547 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
548 tmp = htonl(IPPROTO_TCP);
549 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
551 tmp = ((htons(tx.sp) << 16) + htons(tx.dp));
552 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
554 tmp = htonl(tx.tcp_seq);
555 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
556 tmp = htonl(tx.tcp_ack);
557 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
559 tmp = ((ntohs(((tx.tcp_offset) << 12) + tx.tcp_control) << 16) + htons(tx.tcp_win));
560 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
562 tmp = htonl(tx.tcp_urg);
563 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
565 sum += tx.tcp_sum_part;
567 if (tx.tcp_payload_s)
568 sum += libnet_in_cksum((u_int16_t *) tx.tcp_payload, tx.tcp_payload_s);
570 tx.tcp_sum = ntohs(LIBNET_CKSUM_CARRY(sum));
572 t = libnet_build_tcp (tx.sp,
573 tx.dp,
574 tx.tcp_seq,
575 tx.tcp_ack,
576 tx.tcp_control,
577 tx.tcp_win,
578 tx.tcp_sum,
579 tx.tcp_urg,
580 tx.tcp_len,
581 tx.tcp_payload_s ? tx.tcp_payload : NULL,
582 tx.tcp_payload_s,
585 tx.tcp_sum = 0;
587 return t;
590 int update_ISUM(libnet_t *l, libnet_ptag_t t)
592 int sum = 0;
593 unsigned int tmp;
595 if (tx.icmp_chksum != 0)
596 return 0;
598 sum += libnet_in_cksum((u_int16_t *) &tx.ip6_src, 16);
599 if (tx.ip_option_s && tx.ip6_segs)
600 sum += libnet_in_cksum((u_int16_t *) &tx.ip_option[tx.ip_option_s - 16], 16); // Use last IP address
601 else
602 sum += libnet_in_cksum((u_int16_t *) &tx.ip6_dst, 16);
604 tmp = htonl(LIBNET_ICMPV6_H + tx.icmp_payload_s);
605 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
606 tmp = htonl(IPPROTO_ICMP6);
607 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
609 tmp = htonl(((tx.icmp_type << 8) + tx.icmp_code));
610 sum += libnet_in_cksum((u_int16_t *) &tmp, 4);
612 if (tx.icmp_payload_s)
613 sum += libnet_in_cksum((u_int16_t *) tx.icmp_payload, tx.icmp_payload_s);
615 tx.icmp_chksum = ntohs(LIBNET_CKSUM_CARRY(sum));
617 t = libnet_build_icmpv4_echo (tx.icmp_type,
618 tx.icmp_code,
619 tx.icmp_chksum,
620 tx.icmp_ident,
621 tx.icmp_sqnr,
622 tx.icmp_payload_s ? tx.icmp_payload : NULL,
623 tx.icmp_payload_s,
626 tx.icmp_chksum = 0;
628 return t;
631 ///////////////////////////////////////////////////////////////////////
633 // Applies another TCP SQNR from a specified range to a given TCP-PTAG
635 // RETURN VALUE: '1' if tx.txp_seq restarts
637 int update_TCP_SQNR(libnet_t *l, libnet_ptag_t t)
640 u_int32_t diff;
641 int i=0;
643 tx.tcp_seq += tx.tcp_seq_delta;
644 diff = tx.tcp_seq_stop - tx.tcp_seq_start;
646 if (diff < tx.tcp_seq_stop) // start < stop
648 if (tx.tcp_seq > tx.tcp_seq_stop)
650 tx.tcp_seq = tx.tcp_seq_start;
651 i=1;
654 else // stop < start
656 if ( (tx.tcp_seq<tx.tcp_seq_start) &&
657 (tx.tcp_seq>tx.tcp_seq_stop) )
659 tx.tcp_seq = tx.tcp_seq_start;
660 i=1;
665 t = libnet_build_tcp (tx.sp,
666 tx.dp,
667 tx.tcp_seq,
668 tx.tcp_ack,
669 tx.tcp_control,
670 tx.tcp_win,
671 tx.tcp_sum,
672 tx.tcp_urg,
673 tx.tcp_len,
674 (tx.tcp_payload_s) ? tx.tcp_payload : NULL,
675 tx.tcp_payload_s,
679 if (t == -1)
681 fprintf(stderr, " mz/update_TCP_SQNR: Can't build TCP header: %s\n", libnet_geterror(l));
682 exit (0);
685 return i;
689 ////////////////////////////////////////////////////////////////////////
693 int print_frame_details(void)
695 unsigned char *dum1, *dum2;
696 char pld[65535];
697 char sa[32], da[32];
699 if (!tx.packet_mode)
701 bs2str(tx.eth_dst, da, 6);
702 bs2str(tx.eth_src, sa, 6);
703 fprintf(stderr, " Eth: DA = %s, SA = %s\n",da,sa);
707 if (tx.dot1Q)
709 fprintf(stderr, " 802.1Q VLAN-TAG = %s\n", tx.dot1Q_txt);
712 if (tx.mpls)
714 fprintf(stderr," MPLS labels (label:exp:bos:ttl): %s\n",tx.mpls_verbose_string);
719 dum1 = (unsigned char*) &tx.ip_src_h;
720 dum2 = (unsigned char*) &tx.ip_dst_h;
721 if (mode==IP) {
722 (void) bs2str(tx.ip_payload, pld, tx.ip_payload_s);
723 } else {
724 strcpy(pld, "[see next layer]");
727 if (ipv6_mode) {
728 char src6[64]; char dst6[64];
729 libnet_addr2name6_r(tx.ip6_src, LIBNET_DONT_RESOLVE, src6, 64);
730 libnet_addr2name6_r(tx.ip6_dst, LIBNET_DONT_RESOLVE, dst6, 64);
732 fprintf(stderr," IP: ver=6, dscp=%u, flow=%u, len=%u, next=%u, hop=%u "
733 "SA=%s, DA=%s\n payload=%s\n", tx.ip_tos, tx.ip_flow,
734 tx.ip_len, tx.ip_proto, tx.ip_ttl, src6, dst6, pld);
736 else {
737 fprintf(stderr," IP: ver=4, len=%u, tos=%u, id=%u, frag=%u, ttl=%u, proto=%u, sum=%u, "
738 "SA=%u.%u.%u.%u, DA=%u.%u.%u.%u,\n"
739 " payload=%s\n", tx.ip_len, tx.ip_tos,
740 tx.ip_id, tx.ip_frag, tx.ip_ttl, tx.ip_proto, tx.ip_sum,
741 *(dum1+3),*(dum1+2),*(dum1+1),*(dum1), *(dum2+3),*(dum2+2),*(dum2+1),*(dum2+0), pld);
744 if ((mode==UDP)||(mode==DNS)||(mode==RTP))
746 bs2str(tx.udp_payload, pld, tx.udp_payload_s);
747 fprintf(stderr, " UDP: sp=%u, dp=%u, len=%u, sum=%u, \n"
748 " payload=%s\n", tx.sp, tx.dp, tx.udp_len, tx.udp_sum, pld);
750 if (mode==TCP) // TODO: Improve message details (flags, ...)
752 bs2str(tx.tcp_payload, pld, tx.tcp_payload_s);
753 fprintf(stderr, " TCP: sp=%u, dp=%u, S=%u, A=%u, flags=%x, win=%u, len=%u, sum=%u, \n"
754 " payload=%s\n",
755 tx.sp, tx.dp, tx.tcp_seq, tx.tcp_ack, tx.tcp_control, tx.tcp_win, tx.tcp_len, tx.tcp_sum, pld);
758 // send_icmp must prepare the verbose string because there are many
759 // different types of ICMP packets...
760 if (mode==ICMP)
762 fprintf(stderr, " %s\n", tx.icmp_verbose_txt);
765 if (mode==ICMP6)
767 fprintf(stderr, " %s\n", tx.icmp_verbose_txt);
770 // libnet_diag_dump_pblock(l);
771 fprintf(stderr,"\n");
773 if (simulate)
775 fprintf(stderr, "*** NOTE: Simulation only! Nothing has been sent! ***\n");
776 exit(0);
780 return 0;