Initial commit of OpenSPARC T2 design and verification files.
[OpenSPARC-T2-DV] / verif / env / common / vera / niu_ippktgen / C / wrapper / pgLibnetL3.c
CommitLineData
86530b38
AT
1#include "include/libnet.h"
2#include "include/pg.h"
3#include "include/packet.h"
4
5extern unsigned char * genPayload (int data_type, unsigned int seed,
6 int data_length);
7
8int libnet_gen_l3_packet (struct packet_desc *packet_vars, libnet_t *l) {
9
10 libnet_ptag_t t,t1,t2,t3,ipo;
11 char *payload;
12 u_short payload_s;
13 u_long src_ip, dst_ip;
14 u_short src_prt, dst_prt;
15 u_short options =0;
16 int l4_header_length;
17 u_short L4Protocol;
18 u_char opt[40];
19 u_short ip_frag =0;
20 int i,no_of_options_bytes;
21 u_short ipv6_nexthdr=0;
22
23 struct libnet_in6_addr ipv6_src_ip;
24 struct libnet_in6_addr ipv6_dst_ip;
25 int total_length;
26
27 if(packet_vars->l3_pkt_type == 0 ) {
28 /* NO L4 Processing*/
29 return(1);
30 }
31 if((packet_vars->l2_pkt_type == 0) ){
32 printf(" TEST PROGRAM ERROR !! \n");
33 return(-1);
34 }
35
36 if(packet_vars->l3_len) {
37 payload = genPayload(packet_vars->payload.data_type,
38 packet_vars->payload.data_seed,packet_vars->l3_len);
39 payload_s = packet_vars->l3_len;
40 }else {
41 payload = NULL;
42 payload_s = 0;
43 }
44
45 no_of_options_bytes = 0;
46 /* fill up options in case it is needed*/
47 for(i=0;i<40; i ++) {
48 opt[i] = 0xa0 + i; /*load up options with some value*/
49 }
50 no_of_options_bytes = packet_vars->ip.options ;
51
52 if ((packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV4) &&
53 (no_of_options_bytes > 0)) {
54 printf(" Build IPV4 with options - length - %d \n", no_of_options_bytes);
55 ipo = libnet_build_ipv4_options(
56 opt,
57 no_of_options_bytes,
58 l,
59 0);
60 if (ipo == -1)
61 {
62 fprintf(stderr, "Can't build IPV4 options: %s\n", libnet_geterror(l));
63 return(-1);
64 }
65 }
66
67 /* Default value for l4_header and L4_protocol*/
68 l4_header_length = 0;
69 L4Protocol = 0;
70
71 /*Determine L4Protocol field based upon input*/
72 if(packet_vars->l4_pkt_type & L4_PKT_TYPE_TCP) {
73 l4_header_length = LIBNET_TCP_H;
74 L4Protocol = IPPROTO_TCP;
75 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_UDP) {
76 l4_header_length = LIBNET_UDP_H;
77 L4Protocol = IPPROTO_UDP;
78 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_SCTP) {
79 l4_header_length = LIBNET_SCTP_H;
80 L4Protocol = IPPROTO_SCTP;
81 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_AH) {
82 l4_header_length = LIBNET_IPSEC_AH_H;
83 L4Protocol = IPPROTO_AH;
84 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_ESP) {
85 l4_header_length = LIBNET_IPSEC_ESP_HDR_H;
86 L4Protocol = IPPROTO_ESP;
87 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_ICMP) {
88 if(packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV4) {
89 l4_header_length = LIBNET_ICMPV4_H;
90 L4Protocol = IPPROTO_ICMP;
91 } else if(packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV6) {
92 l4_header_length = LIBNET_ICMPV6_H;
93 L4Protocol = IPPROTO_ICMP6;
94 } else {
95 fprintf(stderr, "Incompatible L3 protocol type for ICMP\n");
96 return(-1);
97 }
98 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_IGMP) {
99 l4_header_length = LIBNET_IGMP_H;
100 L4Protocol = IPPROTO_IGMP;
101 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_PIM) {
102 l4_header_length = LIBNET_PIM_H;
103 L4Protocol = IPPROTO_PIM;
104 } else if(packet_vars->l4_pkt_type & L4_PKT_TYPE_RSVP) {
105 l4_header_length = LIBNET_RSVP_H;
106 L4Protocol = IPPROTO_RSVP;
107 } else if((packet_vars->l4_pkt_type & L4_PKT_TYPE_GRE) ||
108 (packet_vars->l4_pkt_type & L4_PKT_TYPE_EGRE)) {
109 l4_header_length = LIBNET_GRE_H;
110 L4Protocol = IPPROTO_GRE;
111 } else {/* MORE TO BE ADDED */}
112
113 // if user wants to override the protocol chosen for error condition
114 //
115 if( ( packet_vars->payload.error_code & PG_L4_PROTO_USER_MODE) )
116 L4Protocol = packet_vars->ip.proto;
117
118 printf("L4PktType - %x L4Protocol Chosen as - 0x%x \n",
119 packet_vars->l4_pkt_type,L4Protocol);
120
121 if ((packet_vars->l3_pkt_type & L3_PKT_TYPE_FRAG) &&
122 (packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV4)) {
123 ip_frag = packet_vars->ip.frag; /* NO SURE WHAT TO CHOOSE TBD */
124 } else ip_frag = 0;
125
126
127 if(packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV4) {
128
129 printf(" BUILDING L3Packet -\n");
130 t1 = libnet_build_ipv4(
131 LIBNET_IPV4_H + l4_header_length + no_of_options_bytes + packet_vars->l4_len + payload_s,/* length */
132 packet_vars->ip.tos, /* TOS */
133 242, /* IP ID */
134 ip_frag, /* IP Frag */
135 64, /* TTL */
136 L4Protocol, /* protocol */
137 0x0, /* checksum */
138 packet_vars->ip.src_addr, /* source IP */
139 packet_vars->ip.dst_addr, /* destination IP */
140 payload, /* payload */
141 payload_s, /* payload size */
142 l, /* libnet handle */
143 0); /* libnet id */
144
145 if (t1 == -1)
146 {
147 fprintf(stderr, "Can't build IPV4 header: %s\n", libnet_geterror(l));
148 return(-1);
149 }
150 } else if (packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV6) {
151 /* Begin addition */
152 /* Need variable nh, ipv6FragId to be supported */
153 /* This is an extension header, the first header must have been formed first */
154#if 0
155 if( (packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV6) &&
156 (no_of_options_bytes > 0)){
157 printf(" Build IPV6 with options - length - %d \n", no_of_options_bytes);
158 /* This needs new src to be cloned in the libnet */
159 ipo = libnet_build_ipv6_options(0, /* ot */
160 no_of_options_bytes, /* ip_ol */
161 opt, /* ip_od */
162 NULL,
163 0,
164 l,
165 0);
166 if (ipo == -1)
167 {
168 fprintf(stderr, "Can't build IPV6 options: %s\n", libnet_geterror(l));
169 return(-1);
170 }
171 } /*end ipv6_options*/
172#endif
173#if 0
174 /* This is an extension header, the first header must have been formed first */
175 if(packet_vars->l3_pkt_type & L3_PKT_TYPE_FRAG) {
176 printf(" Build IPV6 with fragment \n");
177 ipo = libnet_build_ipv6_frag(packet_vars->ipv6.nexthdr,
178 0, /* ip_nh (toberesolved), reserved */
179 1, /* fragment */
180 packet_vars->ipv6.ipv6FragId, /* ip_id (toberesolved)*/
181 NULL, /* payload */
182 0, /* payload */
183 l,
184 0);
185 if (ipo == -1)
186 {
187 fprintf(stderr, "Can't build IPV6 fragment : %s\n", libnet_geterror(l));
188 return(-1);
189 }
190
191 } /*end ipv6_frag*/
192#endif
193
194 if(packet_vars->l3_pkt_type & L3_PKT_TYPE_IPV6) {
195 printf(" Build IPV6 first header \n");
196 /* toberesolved. this needs to be a function - depending on whether there is extension header following. This assumes no ext hdr */
197 total_length = l4_header_length + no_of_options_bytes +
198 packet_vars->l4_len + payload_s;
199
200 // Override from TEST if set to 0xff -
201 if(ipv6_nexthdr != 0xff) {
202 ipv6_nexthdr = L4Protocol;
203 } else ipv6_nexthdr = packet_vars->ipv6.nexthdr;
204
205 for(i=0;i<16;i++) {
206 ipv6_src_ip.libnet_s6_addr[i] = packet_vars->ipv6.src_addr[i];
207 ipv6_dst_ip.libnet_s6_addr[i] = packet_vars->ipv6.dst_addr[i];
208 }
209 ipo = libnet_build_ipv6(
210 packet_vars->ipv6.tc,
211 0,
212 total_length,
213 ipv6_nexthdr,
214 64,
215 ipv6_src_ip,
216 ipv6_dst_ip,
217 payload,
218 payload_s,
219 l,
220 0);
221 if (ipo == -1)
222 {
223 fprintf(stderr, "Can't build IPV6: %s\n", libnet_geterror(l));
224 return(-1);
225 }
226 } /*end first ipv6 header*/
227} else {/*??*/
228 printf(" UNSUPPORTED PROTOCOL !! \n");
229 return(-1);
230}
231
232return(1);
233}
234