Commit | Line | Data |
---|---|---|
86530b38 AT |
1 | // ========== Copyright Header Begin ========================================== |
2 | // | |
3 | // OpenSPARC T2 Processor File: cPgIf.vr | |
4 | // Copyright (C) 1995-2007 Sun Microsystems, Inc. All Rights Reserved | |
5 | // 4150 Network Circle, Santa Clara, California 95054, U.S.A. | |
6 | // | |
7 | // * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. | |
8 | // | |
9 | // This program is free software; you can redistribute it and/or modify | |
10 | // it under the terms of the GNU General Public License as published by | |
11 | // the Free Software Foundation; version 2 of the License. | |
12 | // | |
13 | // This program is distributed in the hope that it will be useful, | |
14 | // but WITHOUT ANY WARRANTY; without even the implied warranty of | |
15 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
16 | // GNU General Public License for more details. | |
17 | // | |
18 | // You should have received a copy of the GNU General Public License | |
19 | // along with this program; if not, write to the Free Software | |
20 | // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | |
21 | // | |
22 | // For the avoidance of doubt, and except that if any non-GPL license | |
23 | // choice is available it will apply instead, Sun elects to use only | |
24 | // the General Public License version 2 (GPLv2) at this time for any | |
25 | // software where a choice of GPL license versions is made | |
26 | // available with the language indicating that GPLv2 or any later version | |
27 | // may be used, or where a choice of which version of the GPL is applied is | |
28 | // otherwise unspecified. | |
29 | // | |
30 | // Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, | |
31 | // CA 95054 USA or visit www.sun.com if you need additional information or | |
32 | // have any questions. | |
33 | // | |
34 | // ========== Copyright Header End ============================================ | |
35 | #include <vera_defines.vrh> | |
36 | #include <ListMacros.vrh> | |
37 | #include "pcg_token.vrh" | |
38 | #include "flow_db.vrh" | |
39 | #include "flow_vars_defines.vri" | |
40 | ||
41 | ||
42 | extern "C" task genCPacket(integer t, var bit [7:0] flow_vars[*], var bit [7:0] payload[*], var bit[31:0] pkt_fields[*] ); | |
43 | ||
44 | ||
45 | class CPgIf { | |
46 | ||
47 | integer port_id; | |
48 | static event pkt_sync; | |
49 | task genPacket(integer index,integer data_length, flow_desc flow, var bit [7:0] payload[*], var bit[31:0] pkt_fields[*] ); | |
50 | function integer ConstructFlowVars(var bit [7:0] flow_vars[*], flow_desc flow, integer data_length); | |
51 | function integer getLength(flow_desc flow); | |
52 | task new() { | |
53 | trigger(ON,pkt_sync); | |
54 | } | |
55 | ||
56 | } | |
57 | function integer CPgIf::getLength(flow_desc flow) { | |
58 | ||
59 | // getLength = flow.frame.data_length; | |
60 | } | |
61 | ||
62 | function integer CPgIf::ConstructFlowVars(var bit [7:0] flow_vars[*], flow_desc flow, integer data_length) { | |
63 | ||
64 | bit[47:0] l2_da,l2_sa; | |
65 | bit [4:0] frame_type; | |
66 | bit[15:0] tpid; | |
67 | bit [15:0] tci; | |
68 | integer frame_class; | |
69 | integer class_funct; | |
70 | integer frame_class_mask; | |
71 | integer header_length; | |
72 | integer ttl; | |
73 | bit [31:0] spi; | |
74 | bit [7:0] nxthdr; | |
75 | bit [7:0] tos; | |
76 | integer type; | |
77 | bit [128:0] src_ipv6_addr,dst_ipv6_addr; | |
78 | bit [31:0] src_ip_addr,dst_ip_addr; | |
79 | bit [15:0] src_port,dst_port; | |
80 | bit [7:0] tcp_flags; | |
81 | bit [31:0] tcp_seq_no; | |
82 | bit [31:0] rcv_isn; | |
83 | bit [31:0] last_seqno; | |
84 | integer data_type; | |
85 | integer data_seed; | |
86 | integer error_code=0; | |
87 | bit[15:0] error_chksum; | |
88 | bit[7:0] l4_proto_field; | |
89 | bit[15:0] error_type_len=0; | |
90 | bit [31:0] esp_ah_seq_no; | |
91 | ||
92 | /*sctp*/ | |
93 | bit[15:0] src_sctp_port; | |
94 | bit[15:0] dst_sctp_port; | |
95 | bit [31:0] sctp_vtag; | |
96 | ||
97 | /*arp*/ | |
98 | bit[15:0] arp_hw_type; | |
99 | bit[15:0] arp_proto_type; | |
100 | bit[7:0] arp_hw_len; | |
101 | bit[7:0] arp_proto_len; | |
102 | bit[15:0] arp_op_code; | |
103 | bit[47:0] arp_src_ha; | |
104 | bit[47:0] arp_tgt_ha; | |
105 | bit[31:0] arp_src_ip; | |
106 | bit[31:0] arp_tgt_ip; | |
107 | ||
108 | integer gId; | |
109 | bit [63:0] options; | |
110 | integer i; | |
111 | integer l2_pad_length; | |
112 | bit [15:0] frame_length; | |
113 | bit [15:0] ip_frag; | |
114 | ||
115 | flow_vars = new[200/*??*/]; | |
116 | ||
117 | frame_type = flow.frame.frame_type; | |
118 | frame_class = flow.frame.frame_class; | |
119 | l2_pad_length = flow.frame.l2_pad_length; | |
120 | ||
121 | l2_da = flow.dst_node.l2_addr; | |
122 | l2_sa = flow.src_node.l2_addr; | |
123 | ||
124 | tpid = flow.frame.tpid; | |
125 | tci = flow.src_node.tci; | |
126 | ||
127 | //?? class_funct = flow.frame.class_funct; | |
128 | //?? frame_class_mask = flow.frame.class_mask; | |
129 | ||
130 | header_length = flow.frame.header_length ; | |
131 | ||
132 | src_ip_addr = flow.src_node.ip_addr; | |
133 | dst_ip_addr = flow.dst_node.ip_addr; | |
134 | src_port = flow.tup.src_tcp_udp_port; | |
135 | dst_port = flow.tup.dst_tcp_udp_port; | |
136 | tcp_seq_no = flow.tup.tcp_seq_no; | |
137 | tcp_flags = flow.fl_state.tcp_flags; | |
138 | tos = flow.src_node.tos; | |
139 | ||
140 | ip_frag = flow.frame.ip_frag; | |
141 | ||
142 | // ttl = flow.ttl; | |
143 | spi = flow.src_node.spi; | |
144 | ||
145 | esp_ah_seq_no =flow.src_node.esp_ah_seq_no; | |
146 | src_ipv6_addr = flow.src_node.ipv6_addr; | |
147 | dst_ipv6_addr = flow.dst_node.ipv6_addr; | |
148 | nxthdr = flow.src_node.nxthdr; | |
149 | rcv_isn = flow.rx_param.rcv_isn; | |
150 | ||
151 | /*sctp*/ | |
152 | src_sctp_port= flow.sctp.src_sctp_port; | |
153 | dst_sctp_port= flow.sctp.dst_sctp_port; | |
154 | sctp_vtag=flow.sctp.sctp_vtag ; | |
155 | ||
156 | ||
157 | /*arp*/ | |
158 | arp_hw_type = flow.arp.hw_type; | |
159 | arp_proto_type = flow.arp.proto_type; | |
160 | arp_hw_len = flow.arp.hlen; | |
161 | arp_proto_len = flow.arp.plen; | |
162 | arp_op_code = flow.arp.operation; | |
163 | arp_src_ha = flow.arp.src_hw_addr; | |
164 | arp_tgt_ha = flow.arp.dst_hw_addr; | |
165 | arp_src_ip = flow.arp.src_proto_addr; | |
166 | arp_tgt_ip = flow.arp.dst_proto_addr; | |
167 | ||
168 | ||
169 | data_type = flow.frame.data_type; | |
170 | data_seed = flow.frame.data_seed; | |
171 | // flow_id = flow.flow_no; | |
172 | // gId = flow.gId; | |
173 | // options = flow.options; | |
174 | ||
175 | if(data_type===DAT_FC_PAUSE) { | |
176 | error_code = PG_TYPE_LEN_USER_MODE; | |
177 | error_type_len = 16'h8808; | |
178 | } | |
179 | error_code = error_code | flow.frame.error_code; | |
180 | error_chksum = flow.frame.error_chksum; | |
181 | error_type_len = error_type_len | flow.frame.error_type_len; | |
182 | l4_proto_field = flow.frame.l4_proto_field; | |
183 | ||
184 | flow_vars[FRAME_TYPE_INDEX] = frame_type; | |
185 | flow_vars[FRAME_CLASS_INDEX] = frame_class; | |
186 | ||
187 | for(i = 0;i< L2_DA_SIZE ;i++) { | |
188 | flow_vars[L2_DA_INDEX + i] = l2_da[7+ 8*i: 8*i]; | |
189 | // printf(" VERA Index - %d value - %x \n",L2_DA_INDEX + i,flow_vars[L2_DA_INDEX + i]); | |
190 | // printf(" l2_da - %x \n",l2_da); | |
191 | } | |
192 | ||
193 | for(i = 0;i< L2_SA_SIZE;i++) { | |
194 | flow_vars[L2_SA_INDEX + i] = l2_sa[7+ 8*i: 8*i]; | |
195 | // printf(" VERA Index - %d value - %x \n",L2_SA_INDEX + i,flow_vars[L2_SA_INDEX + i]); | |
196 | } | |
197 | ||
198 | for(i = 0;i< TPID_SIZE;i++) | |
199 | flow_vars[TPID_INDEX + i] = tpid[7+ 8*i: 8*i]; | |
200 | ||
201 | for(i = 0;i< TCI_SIZE;i++) | |
202 | flow_vars[TCI_INDEX + i] = tci[7+ 8*i: 8*i]; | |
203 | ||
204 | flow_vars[IP_OPTION_INDEX] = (header_length -5 )*4; // no of bytes of options | |
205 | ||
206 | ||
207 | for(i = 0;i< IPV4_SRC_ADDR_SIZE;i++) | |
208 | flow_vars[IPV4_SRC_ADDR_INDEX + i] = src_ip_addr[7+ 8*i: 8*i]; | |
209 | ||
210 | for(i = 0;i< IPV4_DST_ADDR_SIZE;i++) | |
211 | flow_vars[IPV4_DST_ADDR_INDEX + i] = dst_ip_addr[7+ 8*i: 8*i]; | |
212 | ||
213 | for(i = 0;i< IPV4_SRC_PRT_SIZE;i++) | |
214 | flow_vars[IPV4_SRC_PRT_INDEX + i] = src_port[7+ 8*i: 8*i]; | |
215 | ||
216 | for(i = 0;i< IPV4_DST_PRT_SIZE;i++) | |
217 | flow_vars[IPV4_DST_PRT_INDEX + i] = dst_port[7+ 8*i: 8*i]; | |
218 | ||
219 | for(i = 0;i< TCP_FLAGS_SIZE;i++) | |
220 | flow_vars[TCP_FLAGS_INDEX + i] = tcp_flags[7+ 8*i: 8*i]; | |
221 | ||
222 | for(i = 0;i< TCP_SEQ_NO_SIZE;i++) | |
223 | flow_vars[TCP_SEQ_NO_INDEX + i] = tcp_seq_no[7+ 8*i: 8*i]; | |
224 | ||
225 | for(i = 0;i< SPI_SIZE;i++) | |
226 | flow_vars[SPI_INDEX + i] = spi[7+ 8*i: 8*i]; | |
227 | ||
228 | for(i = 0;i< ESP_AH_SEQ_NO_SIZE;i++) | |
229 | flow_vars[ESP_AH_SEQ_NO_INDEX + i] = esp_ah_seq_no[7+ 8*i: 8*i]; | |
230 | ||
231 | for(i = 0;i< IPV6_SRC_ADDR_SIZE;i++) | |
232 | flow_vars[IPV6_SRC_ADDR_INDEX + i] = src_ipv6_addr[7+ 8*i: 8*i]; | |
233 | ||
234 | for(i = 0;i< IPV6_DST_ADDR_SIZE;i++) { | |
235 | flow_vars[IPV6_DST_ADDR_INDEX + i] = dst_ipv6_addr[7+ 8*i: 8*i]; | |
236 | // printf(" Index - %d Value - %x \n",IPV6_DST_ADDR_INDEX + i,dst_ipv6_addr[7+ 8*i: 8*i]); | |
237 | } | |
238 | ||
239 | flow_vars[IPV6_NXT_HDR ] = nxthdr[7: 0]; | |
240 | ||
241 | flow_vars[TOS_INDEX] = tos; | |
242 | // printf("Index - %d Tos - %x \n",TOS_INDEX,tos); | |
243 | ||
244 | for(i = 0;i< IP_FRAG_SIZE;i++) | |
245 | flow_vars[IP_FRAG_INDEX + i] = ip_frag[7+ 8*i: 8*i]; | |
246 | ||
247 | for(i = 0;i< SCTP_SRC_PRT_SIZE;i++) | |
248 | flow_vars[SCTP_SRC_PRT_INDEX + i] = src_sctp_port[7+ 8*i: 8*i]; | |
249 | ||
250 | for(i = 0;i< SCTP_DST_PRT_SIZE;i++) | |
251 | flow_vars[SCTP_DST_PRT_INDEX + i] = dst_sctp_port[7+ 8*i: 8*i]; | |
252 | ||
253 | for(i = 0;i< SCTP_VTAG_SIZE;i++) | |
254 | flow_vars[SCTP_VTAG_INDEX + i] = sctp_vtag[7+ 8*i: 8*i]; | |
255 | ||
256 | ||
257 | for(i = 0;i< ARP_HW_TYPE_SIZE ;i++) | |
258 | flow_vars[ARP_HW_TYPE_INDEX + i] = arp_hw_type[7+ 8*i: 8*i]; | |
259 | ||
260 | for(i = 0;i< ARP_PROTO_TYPE_SIZE ;i++) | |
261 | flow_vars[ARP_PROTO_TYPE_INDEX +i] = arp_proto_type[7+ 8*i: 8*i]; | |
262 | ||
263 | flow_vars[ARP_HW_LEN_INDEX] = arp_hw_len; | |
264 | flow_vars[ARP_PROTO_LEN_INDEX] = arp_proto_len; | |
265 | ||
266 | for(i = 0;i< ARP_PROTO_TYPE_SIZE ;i++) | |
267 | flow_vars[ ARP_OPCODE_INDEX+ i] = arp_op_code[7+ 8*i: 8*i]; | |
268 | ||
269 | /* Various Address fields in the Arp Packet */ | |
270 | for(i=0;i<ARP_SRC_ADDR_SIZE;i++) { | |
271 | flow_vars[ARP_SRC_ADDR_INDEX + i] = arp_src_ha[7+ 8*i: 8*i]; | |
272 | flow_vars[ARP_TGT_ADDR_INDEX + i] = arp_tgt_ha[7+ 8*i: 8*i]; | |
273 | } | |
274 | for(i=0;i<ARP_SRCIP_ADDR_SIZE;i++) { | |
275 | flow_vars[ARP_SRCIP_ADDR_INDEX + i] =arp_src_ip[7+ 8*i: 8*i]; | |
276 | flow_vars[ARP_TGTIP_ADDR_INDEX + i] = arp_tgt_ip[7+ 8*i: 8*i]; | |
277 | } | |
278 | ||
279 | ||
280 | frame_length = data_length; | |
281 | ||
282 | ||
283 | flow_vars[DATA_LENGTH_INDEX + 0] = ((data_length) & 16'hff) ; | |
284 | flow_vars[DATA_LENGTH_INDEX + 1] = ((data_length) & 16'hff00) >>8; | |
285 | ||
286 | flow_vars[DATA_TYPE_INDEX ] = ((data_type) & 32'hff) ; | |
287 | ||
288 | flow_vars[DATA_SEED_INDEX + 0] = ((data_seed) & 32'hff) ; | |
289 | flow_vars[DATA_SEED_INDEX + 1] = ((data_seed) & 32'hff00) >>8; | |
290 | flow_vars[DATA_SEED_INDEX + 2] = ((data_seed) & 32'hff0000)>>16 ; | |
291 | flow_vars[DATA_SEED_INDEX + 3] = ((data_seed) & 32'hff000000) >>24; | |
292 | ||
293 | flow_vars[DATA_ERR_CODE_INDEX + 0] = ((error_code) & 32'hff) ; | |
294 | flow_vars[DATA_ERR_CODE_INDEX + 1] = ((error_code) & 32'hff00) >>8; | |
295 | flow_vars[DATA_ERR_CODE_INDEX + 2] = ((error_code) & 32'hff0000)>>16 ; | |
296 | flow_vars[DATA_ERR_CODE_INDEX + 3] = ((error_code) & 32'hff000000) >>24; | |
297 | ||
298 | flow_vars[DATA_ERR_DATA_INDEX + 0] = ((error_chksum[7:0]) ) ; | |
299 | flow_vars[DATA_ERR_DATA_INDEX + 1] = (error_chksum[15:8]) ; | |
300 | flow_vars[DATA_ERR_DATA_INDEX + 2] = error_type_len[7:0]; | |
301 | flow_vars[DATA_ERR_DATA_INDEX + 3] = error_type_len[15:8]; | |
302 | ||
303 | flow_vars[L4_PROTO_ERR_INDEX] = l4_proto_field; | |
304 | ||
305 | flow_vars[L2_PAD_LENGTH_INDEX + 0] = ((l2_pad_length) & 16'hff) ; | |
306 | flow_vars[L2_PAD_LENGTH_INDEX + 1] = ((l2_pad_length) & 16'hff00) >>8; | |
307 | ||
308 | ||
309 | // printf(" Vera ErroCode - %x \n",error_code); | |
310 | printf(" Data Length Set to %x \n",data_length+l2_pad_length ); | |
311 | ||
312 | // printf(" Index - %d %d, Value - %x %x\n",DATA_LENGTH_INDEX,DATA_LENGTH_INDEX + 1,flow_vars[DATA_LENGTH_INDEX + 0],flow_vars[DATA_LENGTH_INDEX + 1]); | |
313 | // printf(" Index - %d %d, Value - %x %x\n",L2_PAD_LENGTH_INDEX,L2_PAD_LENGTH_INDEX + 1,flow_vars[L2_PAD_LENGTH_INDEX + 0],flow_vars[L2_PAD_LENGTH_INDEX + 1]); | |
314 | ||
315 | /// | |
316 | ||
317 | ConstructFlowVars = 1; | |
318 | } | |
319 | ||
320 | task CPgIf::genPacket(integer index, integer data_length, flow_desc flow, var bit [7:0] payload[*], var bit[31:0] pkt_fields[*] ) { | |
321 | ||
322 | bit [7:0] flow_vars[*]; | |
323 | integer status; | |
324 | integer i; | |
325 | integer TotalLength; | |
326 | ||
327 | /* Look at various fields of flow and fill it into an array*/ | |
328 | sync(ALL, pkt_sync); | |
329 | trigger(OFF,pkt_sync); | |
330 | ||
331 | status = ConstructFlowVars(flow_vars,flow,data_length); | |
332 | if(status== -1) { | |
333 | printf(" TestBench ERROR\n"); | |
334 | } | |
335 | /* determine the total packet length*/ | |
336 | // TotalLength = getLength(flow); | |
337 | TotalLength = data_length + flow.frame.l2_pad_length ; | |
338 | payload = new[TotalLength]; | |
339 | pkt_fields = new[SIZE_OF_PKT_FIELDS]; | |
340 | ||
341 | /* pass this array along with the index, payload etc to the C function which returns | |
342 | the generated packet*/ | |
343 | ||
344 | genCPacket(index,flow_vars,payload,pkt_fields); | |
345 | ||
346 | trigger(ON,pkt_sync); | |
347 | ||
348 | } |