Commit | Line | Data |
---|---|---|
86530b38 AT |
1 | /* |
2 | * Bridge from SPARC Core to Wishbone Master | |
3 | * | |
4 | * (C) 2007 Simply RISC LLP | |
5 | * AUTHOR: Fabrizio Fazzino <fabrizio.fazzino@srisc.com> | |
6 | * | |
7 | * LICENSE: | |
8 | * This is a Free Hardware Design; you can redistribute it and/or | |
9 | * modify it under the terms of the GNU General Public License | |
10 | * version 2 as published by the Free Software Foundation. | |
11 | * The above named program is distributed in the hope that it will | |
12 | * be useful, but WITHOUT ANY WARRANTY; without even the implied | |
13 | * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | |
14 | * See the GNU General Public License for more details. | |
15 | * | |
16 | * DESCRIPTION: | |
17 | * This block implements a bridge from one SPARC Core of the | |
18 | * OpenSPARC T1 to a master interface that makes use of the | |
19 | * Wishbone interconnect protocol. | |
20 | * For informations about Sun Microsystems' OpenSPARC T1 | |
21 | * refer to the web site http://www.opensparc.net | |
22 | * For informations about OpenCores' Wishbone interconnect | |
23 | * please refer to the web site http://www.opencores.org | |
24 | */ | |
25 | ||
26 | ||
27 | ||
28 | module spc2wbm(sys_clock_i, sys_reset_i, sys_interrupt_source_i, spc_req_i, | |
29 | spc_atom_i, spc_packetout_i, spc_grant_o, spc_ready_o, spc_packetin_o, | |
30 | spc_stallreq_o, wbm_ack_i, wbm_data_i, wbm_cycle_o, wbm_strobe_o, | |
31 | wbm_we_o, wbm_addr_o, wbm_data_o, wbm_sel_o); | |
32 | ||
33 | input sys_clock_i; | |
34 | input sys_reset_i; | |
35 | input [5:0] sys_interrupt_source_i; | |
36 | input [4:0] spc_req_i; | |
37 | input spc_atom_i; | |
38 | input [(130 - 1):0] spc_packetout_i; | |
39 | input wbm_ack_i; | |
40 | input [(64 - 1):0] wbm_data_i; | |
41 | output [4:0] spc_grant_o; | |
42 | output spc_ready_o; | |
43 | output [(146 - 1):0] spc_packetin_o; | |
44 | output spc_stallreq_o; | |
45 | output wbm_cycle_o; | |
46 | output wbm_strobe_o; | |
47 | output wbm_we_o; | |
48 | output [(64 - 1):0] wbm_addr_o; | |
49 | output [(64 - 1):0] wbm_data_o; | |
50 | output [((64 / 8) - 1):0] | |
51 | wbm_sel_o; | |
52 | ||
53 | wire [4:0] spc_req_w; | |
54 | wire spc_atom_w; | |
55 | reg spc_atom_r; | |
56 | wire [(130 - 1):0] spc_packetout_w; | |
57 | reg [(130 - 1):0] spc_packetout_i_save; | |
58 | reg [(130 - 1):0] spc_packetout_i_save2; | |
59 | reg [4:0] spc_grant_w; | |
60 | reg spc_ready_o; | |
61 | reg [(146 - 1):0] spc_packetin_o; | |
62 | reg [(146 - 1):0] spc_packetin_w; | |
63 | reg spc_stallreq_w; | |
64 | reg wbm_cycle_o; | |
65 | reg wbm_strobe_o; | |
66 | reg wbm_we_o; | |
67 | reg [(64 - 1):0] wbm_addr_o; | |
68 | reg [(64 - 1):0] wbm_data_o; | |
69 | reg [((64 / 8) - 1):0] | |
70 | wbm_sel_o; | |
71 | reg [3:0] state; | |
72 | reg [4:0] spc2wbm_region; | |
73 | reg spc2wbm_atomic; | |
74 | reg fifo_vld; | |
75 | reg fifo_vld2; | |
76 | reg [(130 - 1):0] spc2wbm_packet; | |
77 | reg wbm2spc_valid; | |
78 | reg [(144 - 141):0] wbm2spc_type; | |
79 | reg wbm2spc_miss; | |
80 | reg [(139 - 138):0] wbm2spc_error; | |
81 | reg wbm2spc_nc; | |
82 | reg [(136 - 134):0] wbm2spc_thread; | |
83 | reg wbm2spc_way_valid; | |
84 | reg [(132 - 131):0] wbm2spc_way; | |
85 | reg wbm2spc_boot_fetch; | |
86 | reg wbm2spc_atomic; | |
87 | reg wbm2spc_pfl; | |
88 | reg [(127 - 0):0] wbm2spc_data; | |
89 | reg [6:0] wbm2spc_interrupt_source; | |
90 | reg wbm2spc_interrupt_new; | |
91 | wire spc2wbm_req; | |
92 | wire spc2wbm_valid; | |
93 | wire [(128 - 124):0] spc2wbm_type; | |
94 | wire spc2wbm_nc; | |
95 | wire [(122 - 120):0] spc2wbm_cpu_id; | |
96 | wire [(119 - 117):0] spc2wbm_thread; | |
97 | wire spc2wbm_invalidate; | |
98 | wire [(113 - 112):0] spc2wbm_way; | |
99 | wire [(111 - 104):0] spc2wbm_size; | |
100 | wire [(103 - 64):0] spc2wbm_addr; | |
101 | wire [(63 - 0):0] spc2wbm_data; | |
102 | wire [(146 - 1):0] wbm2spc_packet; | |
103 | reg dir_rd_en; | |
104 | reg val_ic; | |
105 | reg val_dc; | |
106 | reg [3:0] dc_dir_wen; | |
107 | wire [3:0] dc_dir_hit; | |
108 | reg [3:0] old_dc_hit; | |
109 | reg [4:0] ic_dir_wen; | |
110 | wire [7:0] ic_dir_hit; | |
111 | reg [7:0] old_ic_hit; | |
112 | wire [2:0] ic_dir_hit_way_enc; | |
113 | wire [1:0] dc_dir_hit_way_enc; | |
114 | reg spc2wbm_addr_subword; | |
115 | reg spc_stallreq_d; | |
116 | reg fifo_vld_d; | |
117 | reg cas1_matched; | |
118 | wire [63:0] wbm_sel_o_bytemask = {{8 {spc2wbm_size[7]}}, {8 | |
119 | {spc2wbm_size[6]}}, {8 {spc2wbm_size[5]}}, {8 | |
120 | {spc2wbm_size[4]}}, {8 {spc2wbm_size[3]}}, {8 | |
121 | {spc2wbm_size[2]}}, {8 {spc2wbm_size[1]}}, {8 {spc2wbm_size[0]}} | |
122 | }; | |
123 | wire [1:0] ic_dir_hit_way_enc0; | |
124 | wire [1:0] ic_dir_hit_way_enc1; | |
125 | ||
126 | assign spc2wbm_req = ((((spc_req_w[4] | spc_req_w[3]) | spc_req_w[2]) | | |
127 | spc_req_w[1]) | spc_req_w[0]); | |
128 | assign spc2wbm_valid = spc2wbm_packet[129]; | |
129 | assign spc2wbm_type = spc2wbm_packet[128:124]; | |
130 | assign spc2wbm_nc = spc2wbm_packet[123]; | |
131 | assign spc2wbm_cpu_id = spc2wbm_packet[122:120]; | |
132 | assign spc2wbm_thread = spc2wbm_packet[119:117]; | |
133 | assign spc2wbm_invalidate = spc2wbm_packet[116]; | |
134 | assign spc2wbm_way = spc2wbm_packet[113:112]; | |
135 | assign spc2wbm_size = spc2wbm_packet[111:104]; | |
136 | assign spc2wbm_addr = spc2wbm_packet[103:64]; | |
137 | assign spc2wbm_data = spc2wbm_packet[63:0]; | |
138 | assign wbm2spc_packet = {wbm2spc_valid, wbm2spc_type, wbm2spc_miss, | |
139 | wbm2spc_error, wbm2spc_nc, wbm2spc_thread, wbm2spc_way_valid, | |
140 | wbm2spc_way, wbm2spc_boot_fetch, wbm2spc_atomic, wbm2spc_pfl, | |
141 | wbm2spc_data}; | |
142 | assign spc_grant_o = (spc_grant_w & (!spc_stallreq_o)); | |
143 | assign spc_atom_w = spc_atom_r; | |
144 | assign spc_req_w = (spc_req_i | {4'b0, (fifo_vld & (~spc_stallreq_w))}); | |
145 | assign spc_stallreq_o = ((spc_stallreq_w | fifo_vld) | {(|spc_req_i)}); | |
146 | assign spc_packetout_w = ((fifo_vld | fifo_vld_d) ? spc_packetout_i_save | |
147 | : spc_packetout_i); | |
148 | assign ic_dir_hit_way_enc = ((|ic_dir_hit[3:0]) ? {1'b0, | |
149 | ic_dir_hit_way_enc0} : {1'b1, ic_dir_hit_way_enc1}); | |
150 | ||
151 | l2_dir l2_dird(sys_clock_i, sys_reset_i, spc2wbm_addr[38:11], | |
152 | {spc2wbm_addr[10:5], spc2wbm_addr_subword}, dc_dir_wen, val_dc, | |
153 | dc_dir_hit, dc_dir_hit_way_enc, dir_rd_en); | |
154 | l2_dir l2_diri0(sys_clock_i, sys_reset_i, spc2wbm_addr[38:11], | |
155 | {spc2wbm_addr[10:5], 1'b0}, ({4 {(~ic_dir_wen[4])}} & | |
156 | ic_dir_wen[3:0]), val_ic, ic_dir_hit[3:0], ic_dir_hit_way_enc0, | |
157 | dir_rd_en); | |
158 | l2_dir l2_diri1(sys_clock_i, sys_reset_i, spc2wbm_addr[38:11], | |
159 | {spc2wbm_addr[10:5], 1'b0}, ({4 {ic_dir_wen[4]}} & | |
160 | ic_dir_wen[3:0]), val_ic, ic_dir_hit[7:4], ic_dir_hit_way_enc1, | |
161 | dir_rd_en); | |
162 | ||
163 | always @(posedge sys_clock_i) begin | |
164 | spc_packetout_i_save <= (((spc_packetout_i[(130 - 1)] & spc_stallreq_d | |
165 | ) & (~fifo_vld)) ? spc_packetout_i : ((fifo_vld & | |
166 | spc_stallreq_d) ? spc_packetout_i_save : spc_packetout_i_save2 | |
167 | )); | |
168 | spc_packetout_i_save2 <= ((spc_packetout_i[(130 - 1)] & fifo_vld) ? | |
169 | spc_packetout_i : (fifo_vld2 ? spc_packetout_i_save2 : 0)); | |
170 | fifo_vld <= ((spc_packetout_i[(130 - 1)] & spc_stallreq_d) ? 1 : ( | |
171 | spc_stallreq_w ? fifo_vld : fifo_vld2)); | |
172 | fifo_vld2 <= ((spc_packetout_i[(130 - 1)] & fifo_vld) ? 1 : ( | |
173 | spc_stallreq_w ? fifo_vld2 : 0)); | |
174 | spc_stallreq_d <= spc_stallreq_w; | |
175 | spc_atom_r <= (fifo_vld ? spc_atom_r : spc_atom_i); | |
176 | fifo_vld_d <= fifo_vld; | |
177 | end | |
178 | always @(posedge sys_clock_i) begin | |
179 | spc_packetin_o <= spc_packetin_w; | |
180 | if (sys_reset_i == 1) begin | |
181 | dir_rd_en <= 0; | |
182 | spc_grant_w <= 5'b0; | |
183 | spc_ready_o <= 0; | |
184 | spc_packetin_w <= 0; | |
185 | spc_stallreq_w <= 0; | |
186 | wbm_cycle_o <= 0; | |
187 | wbm_strobe_o <= 0; | |
188 | wbm_we_o <= 0; | |
189 | wbm_addr_o <= 64'b0; | |
190 | wbm_data_o <= 64'b0; | |
191 | wbm_sel_o <= 8'b0; | |
192 | spc2wbm_addr_subword <= 0; | |
193 | wbm2spc_valid <= 1; | |
194 | wbm2spc_type <= 4'd7; | |
195 | wbm2spc_miss <= 0; | |
196 | wbm2spc_error <= 0; | |
197 | wbm2spc_nc <= 0; | |
198 | wbm2spc_thread <= 0; | |
199 | wbm2spc_way_valid <= 0; | |
200 | wbm2spc_way <= 0; | |
201 | wbm2spc_boot_fetch <= 0; | |
202 | wbm2spc_atomic <= 0; | |
203 | wbm2spc_pfl <= 0; | |
204 | wbm2spc_data <= 64'h0000000000010001; | |
205 | wbm2spc_interrupt_source <= 7'b0; | |
206 | wbm2spc_interrupt_new <= 1'b0; | |
207 | val_ic <= 0; | |
208 | val_dc <= 0; | |
209 | state <= 4'b0; | |
210 | end | |
211 | else | |
212 | begin | |
213 | if (state == 4'b0) begin | |
214 | spc_packetin_w <= wbm2spc_packet; | |
215 | state <= 4'b1; | |
216 | end | |
217 | else if (state == 4'b1) begin | |
218 | if (spc2wbm_req == 1) begin | |
219 | spc_ready_o <= 0; | |
220 | spc_packetin_w <= 0; | |
221 | dc_dir_wen <= 0; | |
222 | ic_dir_wen <= 0; | |
223 | wbm2spc_way_valid <= 0; | |
224 | wbm2spc_way <= 0; | |
225 | wbm2spc_pfl <= 0; | |
226 | wbm2spc_data <= 0; | |
227 | spc_stallreq_w <= 1; | |
228 | spc2wbm_region <= spc_req_w; | |
229 | spc2wbm_atomic <= spc_atom_w; | |
230 | state <= 4'd2; | |
231 | end | |
232 | else if (sys_interrupt_source_i != wbm2spc_interrupt_source) | |
233 | begin | |
234 | wbm2spc_interrupt_new <= 1; | |
235 | wbm2spc_valid <= 1; | |
236 | wbm2spc_type <= 4'd7; | |
237 | wbm2spc_miss <= 0; | |
238 | wbm2spc_error <= 0; | |
239 | wbm2spc_nc <= 0; | |
240 | wbm2spc_thread <= 0; | |
241 | wbm2spc_boot_fetch <= 0; | |
242 | wbm2spc_atomic <= 0; | |
243 | wbm2spc_pfl <= 0; | |
244 | spc_stallreq_w <= 1; | |
245 | end | |
246 | else if ((wbm2spc_interrupt_source != 6'b0) && | |
247 | wbm2spc_interrupt_new) begin | |
248 | wbm2spc_interrupt_new <= 0; | |
249 | spc_ready_o <= 1; | |
250 | spc_packetin_w <= wbm2spc_packet; | |
251 | spc_stallreq_w <= 1; | |
252 | state <= 4'b1; | |
253 | end | |
254 | else | |
255 | begin | |
256 | spc_ready_o <= 0; | |
257 | spc_packetin_w <= 0; | |
258 | spc_stallreq_w <= 0; | |
259 | state <= 4'b1; | |
260 | end | |
261 | end | |
262 | else if (state == 4'd2) begin | |
263 | spc2wbm_addr_subword <= spc_packetout_w[4+64]; | |
264 | spc2wbm_packet <= spc_packetout_w; | |
265 | spc_grant_w <= spc2wbm_region; | |
266 | state <= 4'd3; | |
267 | end | |
268 | else if (state == 4'd3) begin | |
269 | spc2wbm_addr_subword <= spc2wbm_addr[4]; | |
270 | spc_grant_w <= 5'b0; | |
271 | wbm_cycle_o <= 1; | |
272 | wbm_strobe_o <= 1; | |
273 | if ((~spc2wbm_addr[39]) && ((spc2wbm_type == 5'b0) || ( | |
274 | spc2wbm_type == 5'b00010))) begin | |
275 | wbm_addr_o <= {spc2wbm_region, 19'b0, spc2wbm_addr[(103 - | |
276 | 64):4], 4'b0}; | |
277 | dc_dir_wen <= ({4 {(~spc2wbm_nc)}} & ((spc2wbm_way == 0) ? | |
278 | 4'b1 : ((spc2wbm_way == 1) ? 4'd2 : ((spc2wbm_way == 2 | |
279 | ) ? 4'd4 : 4'd8)))); | |
280 | val_dc <= 1; | |
281 | end | |
282 | else begin | |
283 | wbm_addr_o <= {spc2wbm_region, 19'b0, spc2wbm_addr[(103 - | |
284 | 64):3], 3'b0}; | |
285 | end | |
286 | wbm_data_o <= spc2wbm_data; | |
287 | if (spc2wbm_type == 5'b10000) begin | |
288 | ic_dir_wen <= ({5 {(~spc2wbm_nc)}} & {spc2wbm_packet[114], | |
289 | ((spc2wbm_way == 0) ? 4'b1 : ((spc2wbm_way == 1) ? | |
290 | 4'd2 : ((spc2wbm_way == 2) ? 4'd4 : 4'd8)))}); | |
291 | val_ic <= 1; | |
292 | wbm_we_o <= 0; | |
293 | if (spc2wbm_region == 5'b10000) begin | |
294 | wbm_sel_o <= (4'b1111 << (spc2wbm_addr[2] << 2)); | |
295 | end | |
296 | else begin | |
297 | wbm_sel_o <= 8'b11111111; | |
298 | end | |
299 | end | |
300 | else if (spc2wbm_type == 5'b01000) begin | |
301 | wbm_sel_o <= 8'b11111111; | |
302 | wbm_we_o <= 0; | |
303 | end | |
304 | else if (((spc2wbm_type == 5'b0) || (spc2wbm_type == 5'b00010)) | |
305 | || (spc2wbm_type == 5'b00111)) begin | |
306 | if (spc2wbm_addr[39]) begin | |
307 | wbm_we_o <= 0; | |
308 | if (spc2wbm_type == 5'b0) begin | |
309 | case (spc2wbm_size) | |
310 | 3'b0: | |
311 | wbm_sel_o <= (1'b1 << spc2wbm_addr[2:0]); | |
312 | 3'b1: | |
313 | wbm_sel_o <= (2'b11 << (spc2wbm_addr[2:1] << 1)); | |
314 | 3'd2: | |
315 | wbm_sel_o <= (4'b1111 << (spc2wbm_addr[2] << 2)); | |
316 | 3'd3: | |
317 | wbm_sel_o <= 8'b11111111; | |
318 | 3'd7: | |
319 | wbm_sel_o <= 8'b11111111; | |
320 | default: | |
321 | wbm_sel_o <= 8'b0; | |
322 | endcase | |
323 | end | |
324 | else begin | |
325 | wbm_sel_o <= spc2wbm_size; | |
326 | end | |
327 | end | |
328 | else | |
329 | begin | |
330 | wbm_sel_o <= 8'b11111111; | |
331 | end | |
332 | end | |
333 | else if ((spc2wbm_type == 5'b1) || ((spc2wbm_type == 5'b00011) | |
334 | && cas1_matched)) begin | |
335 | wbm_we_o <= 1; | |
336 | wbm_sel_o <= spc2wbm_size; | |
337 | end | |
338 | else | |
339 | begin | |
340 | wbm_we_o <= 1; | |
341 | wbm_sel_o <= 8'b0; | |
342 | end | |
343 | ||
344 | begin | |
345 | // synopsys translate_off | |
346 | case (spc2wbm_type) | |
347 | 5'b0: | |
348 | $display("INFO: SPC2WBM: Request of Type LOAD_RQ"); | |
349 | 5'b10000: | |
350 | $display("INFO: SPC2WBM: Request of Type IMISS_RQ"); | |
351 | 5'b1: | |
352 | $display("INFO: SPC2WBM: Request of Type STORE_RQ"); | |
353 | 5'b01000: | |
354 | $display("INFO: SPC2WBM: Request of Type MMU_RQ"); | |
355 | 5'b00010: | |
356 | $display("INFO: SPC2WBM: Request of Type CAS1_RQ"); | |
357 | 5'b00011: | |
358 | $display("INFO: SPC2WBM: Request of Type CAS2_RQ"); | |
359 | 5'b00111: | |
360 | $display("INFO: SPC2WBM: Request of Type SWAP_RQ"); | |
361 | 5'b00100: | |
362 | $display("INFO: SPC2WBM: Request of Type STRLOAD_RQ"); | |
363 | 5'b01001: | |
364 | $display("INFO: SPC2WBM: Request of Type INT_RQ"); | |
365 | 5'b11111: | |
366 | $display("INFO: SPC2WBM: Request of Type RSVD_RQ"); | |
367 | default: | |
368 | $display("INFO: SPC2WBM: ERROR!!! Request of Type Unknown" | |
369 | ); | |
370 | endcase | |
371 | $display("INFO: SPC2WBM: Address is %X", spc2wbm_addr); | |
372 | $display("INFO: SPC2WBM: Data is %X", spc2wbm_data); | |
373 | // synopsys translate_on | |
374 | end | |
375 | state <= 4'd4; | |
376 | end | |
377 | else if (state == 4'd4) begin | |
378 | dc_dir_wen <= 0; | |
379 | ic_dir_wen <= 0; | |
380 | if (wbm_ack_i == 1) begin | |
381 | dir_rd_en <= 1; | |
382 | if (spc2wbm_atomic == 0) begin | |
383 | wbm_cycle_o <= 0; | |
384 | end | |
385 | wbm_strobe_o <= 0; | |
386 | wbm_we_o <= 0; | |
387 | wbm_addr_o <= 64'b0; | |
388 | wbm_data_o <= 64'b0; | |
389 | wbm_sel_o <= 8'b0; | |
390 | wbm2spc_valid <= 1; | |
391 | case (spc2wbm_type) | |
392 | 5'b10000: begin | |
393 | wbm2spc_type <= 4'b1; | |
394 | wbm2spc_way_valid <= (|dc_dir_hit); | |
395 | wbm2spc_way <= dc_dir_hit_way_enc; | |
396 | wbm2spc_atomic <= 0; | |
397 | val_dc <= 0; | |
398 | if (|dc_dir_hit) begin | |
399 | dc_dir_wen <= dc_dir_hit; | |
400 | val_dc <= 0; | |
401 | end | |
402 | end | |
403 | 5'b00111: begin | |
404 | $display("%t, SWAP %x", $time, spc_packetin_w); | |
405 | wbm2spc_type <= 4'b0; | |
406 | wbm2spc_atomic <= 1; | |
407 | end | |
408 | 5'b0: begin | |
409 | wbm2spc_atomic <= 0; | |
410 | if (spc2wbm_addr[39]) begin | |
411 | wbm2spc_type <= 4'd8; | |
412 | end | |
413 | else | |
414 | begin | |
415 | wbm2spc_pfl <= spc2wbm_packet[115]; | |
416 | wbm2spc_type <= 4'b0; | |
417 | wbm2spc_way_valid <= (|ic_dir_hit); | |
418 | wbm2spc_way <= ic_dir_hit_way_enc[2:1]; | |
419 | wbm2spc_boot_fetch <= ic_dir_hit_way_enc[0]; | |
420 | if (|ic_dir_hit) begin | |
421 | ic_dir_wen <= ((|ic_dir_hit[3:0]) ? {1'b0, | |
422 | ic_dir_hit[3:0]} : {1'b1, ic_dir_hit[7:4]}); | |
423 | val_ic <= 0; | |
424 | end | |
425 | end | |
426 | end | |
427 | 5'b01000: begin | |
428 | wbm2spc_type <= 4'd5; | |
429 | wbm2spc_atomic <= spc2wbm_atomic; | |
430 | end | |
431 | 5'b1: begin | |
432 | wbm2spc_type <= 4'd4; | |
433 | wbm2spc_atomic <= spc2wbm_atomic; | |
434 | end | |
435 | 5'b00010: begin | |
436 | wbm2spc_type <= 4'b0; | |
437 | wbm2spc_atomic <= 1'b1; | |
438 | end | |
439 | 5'b00011: begin | |
440 | wbm2spc_type <= 4'd4; | |
441 | wbm2spc_atomic <= 1'b1; | |
442 | end | |
443 | endcase | |
444 | wbm2spc_miss <= 0; | |
445 | wbm2spc_error <= 0; | |
446 | wbm2spc_nc <= spc2wbm_nc; | |
447 | wbm2spc_thread <= spc2wbm_thread; | |
448 | if (spc2wbm_addr[39]) begin | |
449 | if (spc2wbm_region == 5'b10000) begin | |
450 | wbm2spc_boot_fetch <= 1; | |
451 | end | |
452 | else begin | |
453 | wbm2spc_boot_fetch <= 0; | |
454 | end | |
455 | end | |
456 | if ((spc2wbm_type == 5'b1) || (spc2wbm_type == 5'b00011)) | |
457 | begin | |
458 | wbm2spc_data[125] <= spc2wbm_packet[114]; | |
459 | wbm2spc_data[63:0] <= spc2wbm_data[63:0]; | |
460 | if (|ic_dir_hit) begin | |
461 | wbm2spc_data[67:64] <= {ic_dir_hit_way_enc, 1'b1}; | |
462 | ic_dir_wen <= ((|ic_dir_hit[3:0]) ? {1'b0, ic_dir_hit[3:0] | |
463 | } : {1'b1, ic_dir_hit[7:4]}); | |
464 | val_ic <= 0; | |
465 | wbm2spc_data[116:112] <= spc2wbm_addr[10:6]; | |
466 | wbm2spc_data[122:121] <= spc2wbm_addr[5:4]; | |
467 | wbm2spc_data[104] <= spc2wbm_addr[3]; | |
468 | wbm2spc_data[103:96] <= spc2wbm_size[7:0]; | |
469 | end | |
470 | if (|dc_dir_hit) begin | |
471 | wbm2spc_data[116:112] <= spc2wbm_addr[10:6]; | |
472 | wbm2spc_data[122:121] <= spc2wbm_addr[5:4]; | |
473 | wbm2spc_data[104] <= spc2wbm_addr[3]; | |
474 | wbm2spc_data[103:96] <= spc2wbm_size[7:0]; | |
475 | wbm2spc_data[67:64] <= {dc_dir_hit_way_enc, 2'b10}; | |
476 | if (spc2wbm_type == 5'b00011) begin | |
477 | dc_dir_wen <= dc_dir_hit; | |
478 | val_dc <= 0; | |
479 | end | |
480 | end | |
481 | end | |
482 | else | |
483 | begin //DW FIX FIX for mpgen problem | |
484 | if ((spc2wbm_addr[3] == 0) || (spc2wbm_addr[39] == 0 && spc2wbm_type != 5'b00111)) | |
485 | begin | |
486 | wbm2spc_data <= {wbm_data_i, 64'b0}; | |
487 | end | |
488 | else begin | |
489 | wbm2spc_data <= {64'b0, wbm_data_i}; | |
490 | end | |
491 | end | |
492 | if (((((spc2wbm_type == 5'b10000) && (spc2wbm_region != | |
493 | 5'b10000)) || (spc2wbm_type == 5'b01000)) || ( | |
494 | spc2wbm_type == 5'b00010)) || ((spc2wbm_type == 5'b0) | |
495 | && ((spc2wbm_size == 3'd7) || (spc2wbm_addr[39] == 0)) | |
496 | )) begin | |
497 | state <= 4'd5; | |
498 | end | |
499 | else if (spc2wbm_type == 5'b00111) begin | |
500 | state <= 4'd9; | |
501 | $display("%t, SWAP 2 %x", $time, spc_packetin_w); | |
502 | end | |
503 | else begin | |
504 | state <= 4'b1011; | |
505 | end | |
506 | end | |
507 | else begin | |
508 | state <= 4'd4; | |
509 | end | |
510 | end | |
511 | else if (state == 4'd5) begin | |
512 | dir_rd_en <= 0; | |
513 | dc_dir_wen <= 0; | |
514 | ic_dir_wen <= 0; | |
515 | wbm_cycle_o <= 1; | |
516 | wbm_strobe_o <= 1; | |
517 | wbm_we_o <= 0; | |
518 | wbm_addr_o <= {spc2wbm_region, 19'b0, spc2wbm_addr[(103 - | |
519 | 64):4], 4'd8}; | |
520 | wbm_data_o <= 64'b0; | |
521 | wbm_sel_o <= 8'b11111111; | |
522 | state <= 4'd6; | |
523 | end | |
524 | else if (state == 4'd6) begin | |
525 | if (wbm_ack_i == 1) begin | |
526 | if (spc2wbm_atomic == 0) begin | |
527 | wbm_cycle_o <= 0; | |
528 | end | |
529 | wbm_strobe_o <= 0; | |
530 | wbm_we_o <= 0; | |
531 | wbm_addr_o <= 64'b0; | |
532 | wbm_data_o <= 64'b0; | |
533 | wbm_sel_o <= 8'b0; | |
534 | wbm2spc_data[63:0] <= wbm_data_i; | |
535 | if ((spc2wbm_type == 5'b10000) && (spc2wbm_region != 5'b10000) | |
536 | ) begin | |
537 | state <= 4'd7; | |
538 | end | |
539 | else begin | |
540 | state <= 4'b1011; | |
541 | end | |
542 | end | |
543 | else begin | |
544 | state <= 4'd6; | |
545 | end | |
546 | end | |
547 | else if (state == 4'd7) begin | |
548 | spc2wbm_addr_subword <= 2'b1; | |
549 | spc_packetin_w <= wbm2spc_packet; | |
550 | wbm_cycle_o <= 1; | |
551 | wbm_strobe_o <= 1; | |
552 | wbm_we_o <= 0; | |
553 | dir_rd_en <= 1; | |
554 | wbm_addr_o <= {spc2wbm_region, 19'b0, spc2wbm_addr[(103 - | |
555 | 64):5], 5'b10000}; | |
556 | wbm_data_o <= 64'b0; | |
557 | wbm_sel_o <= 8'b11111111; | |
558 | // synopsys translate_off | |
559 | case (wbm2spc_type) | |
560 | 4'b1: | |
561 | $display("INFO: WBM2SPC: Return Packet of Type IFILL_RET"); | |
562 | 4'b0: | |
563 | $display("INFO: WBM2SPC: Return Packet of Type LOAD_RET"); | |
564 | 4'd5: | |
565 | $display("INFO: WBM2SPC: Return Packet of Type MMU_RET"); | |
566 | 4'd4: | |
567 | $display("INFO: WBM2SPC: Return Packet of Type ST_ACK"); | |
568 | default: | |
569 | $display("INFO: WBM2SPC: Return Packet of Type Unknown"); | |
570 | endcase | |
571 | $display("INFO: WBM2SPC: Data is %X", wbm2spc_data); | |
572 | // synopsys translate_on | |
573 | state <= 4'd8; | |
574 | end | |
575 | else if (state == 4'd8) begin | |
576 | if (|dc_dir_hit) begin | |
577 | dc_dir_wen <= dc_dir_hit; | |
578 | val_dc <= 0; | |
579 | end | |
580 | wbm2spc_way_valid <= (|dc_dir_hit); | |
581 | wbm2spc_way <= dc_dir_hit_way_enc; | |
582 | spc_ready_o <= 0; | |
583 | if (wbm_ack_i == 1) begin | |
584 | if (spc2wbm_atomic == 0) begin | |
585 | wbm_cycle_o <= 0; | |
586 | end | |
587 | wbm_strobe_o <= 0; | |
588 | wbm_we_o <= 0; | |
589 | wbm_addr_o <= 64'b0; | |
590 | wbm_data_o <= 64'b0; | |
591 | wbm_sel_o <= 8'b0; | |
592 | wbm2spc_data <= {wbm_data_i, 64'b0}; | |
593 | wbm2spc_way_valid <= (|dc_dir_hit); | |
594 | wbm2spc_way <= dc_dir_hit_way_enc; | |
595 | dir_rd_en <= 1; | |
596 | state <= 4'd9; | |
597 | end | |
598 | else begin | |
599 | state <= 4'd8; | |
600 | end | |
601 | end | |
602 | else if (state == 4'd9) begin | |
603 | wbm_cycle_o <= 1; | |
604 | wbm_strobe_o <= 1; | |
605 | if (spc2wbm_type == 5'b00111) begin | |
606 | $display("%t, SWAP 3 %x", $time, spc_packetin_w); | |
607 | spc_ready_o <= 1; | |
608 | spc_packetin_w <= wbm2spc_packet; | |
609 | wbm_we_o <= 1; | |
610 | wbm_data_o <= spc2wbm_data; | |
611 | wbm_sel_o <= spc2wbm_size; | |
612 | wbm_addr_o <= {spc2wbm_region, 19'b0, spc2wbm_addr[(103 - | |
613 | 64):0]}; | |
614 | dir_rd_en <= 1; | |
615 | end | |
616 | else | |
617 | begin | |
618 | wbm_we_o <= 0; | |
619 | wbm_sel_o <= 8'b11111111; | |
620 | wbm_addr_o <= {spc2wbm_region, 19'b0, spc2wbm_addr[(103 - | |
621 | 64):5], 5'b11000}; | |
622 | wbm_data_o <= 64'b0; | |
623 | end | |
624 | state <= 4'd10; | |
625 | end | |
626 | else if (state == 4'd10) begin | |
627 | spc_ready_o <= 0; | |
628 | if (wbm_ack_i == 1) begin | |
629 | if (spc2wbm_atomic == 0) begin | |
630 | wbm_cycle_o <= 0; | |
631 | end | |
632 | wbm_strobe_o <= 0; | |
633 | wbm_we_o <= 0; | |
634 | wbm_addr_o <= 64'b0; | |
635 | wbm_data_o <= 64'b0; | |
636 | wbm_sel_o <= 8'b0; | |
637 | if (spc2wbm_type == 5'b00111) begin | |
638 | wbm2spc_data[127:64] <= 64'b0; | |
639 | wbm2spc_atomic <= 1; | |
640 | wbm2spc_type <= 4'd4; | |
641 | wbm2spc_data[63:0] <= spc2wbm_data[63:0]; | |
642 | if (|ic_dir_hit) begin | |
643 | wbm2spc_data[67:64] <= {ic_dir_hit_way_enc, 1'b1}; | |
644 | ic_dir_wen <= ((|ic_dir_hit[3:0]) ? {1'b0, ic_dir_hit[3:0] | |
645 | } : {1'b1, ic_dir_hit[7:4]}); | |
646 | val_ic <= 0; | |
647 | end | |
648 | if (|dc_dir_hit) begin | |
649 | wbm2spc_data[116:112] <= spc2wbm_addr[10:6]; | |
650 | wbm2spc_data[122:121] <= spc2wbm_addr[5:4]; | |
651 | wbm2spc_data[104] <= spc2wbm_addr[3]; | |
652 | wbm2spc_data[103:96] <= spc2wbm_size[7:0]; | |
653 | wbm2spc_data[67:64] <= {dc_dir_hit_way_enc, 2'b10}; | |
654 | end | |
655 | end | |
656 | else | |
657 | begin | |
658 | spc_ready_o <= 1; | |
659 | wbm2spc_atomic <= 1; | |
660 | wbm2spc_data[63:0] <= wbm_data_i; | |
661 | end | |
662 | state <= 4'b1011; | |
663 | end | |
664 | else begin | |
665 | state <= 4'd10; | |
666 | end | |
667 | end | |
668 | else if (state == 4'b1011) begin | |
669 | if (spc2wbm_type == 5'b00010) begin | |
670 | if (((wbm2spc_data[63:0] & wbm_sel_o_bytemask) == ( | |
671 | spc2wbm_data[63:0] & wbm_sel_o_bytemask)) & | |
672 | spc2wbm_addr[3]) begin | |
673 | cas1_matched <= 1'b1; | |
674 | end | |
675 | else if (((wbm2spc_data[127:64] & wbm_sel_o_bytemask) == ( | |
676 | spc2wbm_data[63:0] & wbm_sel_o_bytemask)) & (~ | |
677 | spc2wbm_addr[3])) begin | |
678 | cas1_matched <= 1'b1; | |
679 | end | |
680 | else | |
681 | begin | |
682 | $display("%t, CAS failed pa:%x Act:%x Exp:%x Mask:%x", | |
683 | $time, spc2wbm_addr, wbm_data_i, spc2wbm_data, | |
684 | wbm_sel_o_bytemask); | |
685 | cas1_matched <= 1'b0; | |
686 | end | |
687 | end | |
688 | dir_rd_en <= 0; | |
689 | dc_dir_wen <= 0; | |
690 | ic_dir_wen <= 0; | |
691 | spc_ready_o <= 1; | |
692 | spc_packetin_w <= wbm2spc_packet; | |
693 | state <= 4'b1; | |
694 | end | |
695 | end | |
696 | end | |
697 | endmodule |