OpenCores
URL https://opencores.org/ocsvn/pci/pci/trunk

Subversion Repositories pci

[/] [pci/] [trunk/] [rtl/] [verilog/] [pci_master32_sm_if.v] - Blame information for rev 21

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 mihad
//////////////////////////////////////////////////////////////////////
2
////                                                              ////
3
////  File name "pci_master32_sm_if.v"                            ////
4
////                                                              ////
5
////  This file is part of the "PCI bridge" project               ////
6
////  http://www.opencores.org/cores/pci/                         ////
7
////                                                              ////
8
////  Author(s):                                                  ////
9
////      - Miha Dolenc (mihad@opencores.org)                     ////
10
////                                                              ////
11
////  All additional information is avaliable in the README       ////
12
////  file.                                                       ////
13
////                                                              ////
14
////                                                              ////
15
//////////////////////////////////////////////////////////////////////
16
////                                                              ////
17
//// Copyright (C) 2001 Miha Dolenc, mihad@opencores.org          ////
18
////                                                              ////
19
//// This source file may be used and distributed without         ////
20
//// restriction provided that this copyright statement is not    ////
21
//// removed from the file and that any derivative work contains  ////
22
//// the original copyright notice and the associated disclaimer. ////
23
////                                                              ////
24
//// This source file is free software; you can redistribute it   ////
25
//// and/or modify it under the terms of the GNU Lesser General   ////
26
//// Public License as published by the Free Software Foundation; ////
27
//// either version 2.1 of the License, or (at your option) any   ////
28
//// later version.                                               ////
29
////                                                              ////
30
//// This source is distributed in the hope that it will be       ////
31
//// useful, but WITHOUT ANY WARRANTY; without even the implied   ////
32
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR      ////
33
//// PURPOSE.  See the GNU Lesser General Public License for more ////
34
//// details.                                                     ////
35
////                                                              ////
36
//// You should have received a copy of the GNU Lesser General    ////
37
//// Public License along with this source; if not, download it   ////
38
//// from http://www.opencores.org/lgpl.shtml                     ////
39
////                                                              ////
40
//////////////////////////////////////////////////////////////////////
41
//
42
// CVS Revision History
43
//
44
// $Log: not supported by cvs2svn $
45 21 mihad
// Revision 1.2  2001/10/05 08:14:29  mihad
46
// Updated all files with inclusion of timescale file for simulation purposes.
47
//
48 6 mihad
// Revision 1.1.1.1  2001/10/02 15:33:46  mihad
49
// New project directory structure
50 2 mihad
//
51 6 mihad
//
52 2 mihad
 
53 21 mihad
`include "pci_constants.v"
54 2 mihad
`include "bus_commands.v"
55 21 mihad
 
56
// synopsys translate_off
57 6 mihad
`include "timescale.v"
58 21 mihad
// synopsys translate_on
59 2 mihad
 
60
/*====================================================================
61
Module provides interface between PCI bridge internals and PCI master
62
state machine
63
====================================================================*/
64
module PCI_MASTER32_SM_IF
65
(
66
    clk_in,
67
    reset_in,
68 21 mihad
 
69 2 mihad
    // interconnect to pci master state machine
70
    address_out,
71
    bc_out,
72
    data_out,
73
    data_in,
74
    be_out,
75
    req_out,
76
    rdy_out,
77
    last_out,
78 21 mihad
 
79 2 mihad
    next_data_out,
80
    next_be_out,
81
    next_last_out,
82
 
83
    // status inputs from master SM
84
    wait_in,
85
    wtransfer_in,
86
    rtransfer_in,
87
    retry_in,
88
    rerror_in,
89
    first_in ,
90
    mabort_in,
91
 
92
 
93
    // WISHBONE WRITE fifo inputs and outputs
94
    wbw_renable_out,
95
    wbw_fifo_addr_data_in,
96
    wbw_fifo_cbe_in,
97
    wbw_fifo_control_in,
98
    wbw_fifo_empty_in,
99
    wbw_fifo_transaction_ready_in,
100 21 mihad
 
101 2 mihad
    // WISHBONE READ fifo inputs and outputs
102
    wbr_fifo_wenable_out,
103
    wbr_fifo_data_out,
104
    wbr_fifo_be_out,
105
    wbr_fifo_control_out,
106
 
107
    // delayed transaction control logic inputs and outputs
108
    del_wdata_in,
109
    del_complete_out,
110
    del_req_in,
111
    del_addr_in,
112
    del_bc_in,
113
    del_be_in,
114
    del_burst_in,
115
    del_error_out,
116
    del_rty_exp_out,
117
    del_we_in,
118
 
119
    // configuration space interconnect
120
    // error reporting
121
    err_addr_out,
122
    err_bc_out,
123
    err_signal_out,
124
    err_source_out,
125
    err_rty_exp_out,
126
 
127
    cache_line_size_in,
128 21 mihad
 
129
    // two signals for pci control and status
130 2 mihad
    mabort_received_out,
131 21 mihad
    tabort_received_out,
132
 
133
    posted_write_not_present_out
134 2 mihad
);
135
 
136
// system inputs
137
input clk_in ;
138
input reset_in ;
139
 
140
// PCI master state machine interconnect
141
output  [31:0]  address_out ;   // address output
142
 
143
output  [3:0]   bc_out ;        // bus command output
144 21 mihad
reg     [3:0]   bc_out ;
145 2 mihad
 
146
output  [31:0]  data_out ;      // data output for writes
147
reg     [31:0]  data_out ;
148
 
149
input   [31:0]  data_in ;       // data input for reads
150
output  [3:0]   be_out  ;       // byte enable output
151 21 mihad
reg     [3:0]   be_out  ;
152 2 mihad
 
153
output          req_out ;       // request output
154
 
155
output          rdy_out ;       // ready output
156
reg             rdy_out ;
157
 
158
output          last_out ;      // last data indicator output
159
 
160
output  [31:0]  next_data_out ; // next data output
161
output  [3:0]   next_be_out ;   // next byte enable output
162
output          next_last_out ; // next transfer last indicator
163
 
164
input           wait_in,
165
                wtransfer_in,
166
                rtransfer_in,
167
                retry_in,
168
                rerror_in,
169
                first_in ,
170
                mabort_in ;
171
 
172
// WISHBONE write fifo interconnect
173
output          wbw_renable_out ;          // WBW_FIFO read enable signal
174
 
175
input   [31:0]  wbw_fifo_addr_data_in ;         // WBW_FIFO address/data bus
176
input   [3:0]   wbw_fifo_cbe_in ;               // WBW_FIFO command/byte enable bus
177
input   [3:0]   wbw_fifo_control_in ;           // WBW_FIFO control bus
178
input           wbw_fifo_empty_in ;             // WBW_FIFO's empty status indicator
179
input           wbw_fifo_transaction_ready_in ; // WBW_FIFO transaction ready indicator
180
 
181
// WISHBONE read FIFO interconnect
182
output          wbr_fifo_wenable_out ;          // write enable for WBR_FIFO
183
 
184
output  [31:0]  wbr_fifo_data_out ;             // data output to WBR_FIFO
185
 
186
output  [3:0]   wbr_fifo_be_out ;               // byte enable output for WBR_FIFO
187
 
188
output  [3:0]   wbr_fifo_control_out ;          // WBR_FIFO control output
189
 
190
// delayed transaction control logic inputs and outputs
191
input   [31:0]  del_wdata_in ;                  // delayed write data input
192
output          del_complete_out ;              // delayed transaction completed output
193
 
194
input           del_req_in ;                    // delayed transaction request
195
input   [31:0]  del_addr_in ;                   // delayed transaction address
196
input   [3:0]   del_bc_in ;                     // delayed transaction bus command input
197
input   [3:0]   del_be_in ;                     // delayed transaction byte enables input
198
input           del_burst_in ;                  // delayed transaction burst req. indicator
199
output          del_error_out ;                 // delayed transation error termination signal
200
 
201
output          del_rty_exp_out ;               // retry expired output for delayed transactions
202
 
203
input           del_we_in ;                     // delayed write request indicator
204
 
205
output  [31:0]  err_addr_out ;                  // erroneous address output
206
output  [3:0]   err_bc_out ;                    // erroneous bus command output
207
 
208
output          err_signal_out ;                // error signalization
209
 
210
output          err_source_out ;                // error source indicator
211
 
212
input   [7:0]   cache_line_size_in ;            // cache line size value input
213
 
214
output          err_rty_exp_out ;               // retry expired error output
215
 
216
output          mabort_received_out ;           // master abort signaled to status register
217
output          tabort_received_out ;           // target abort signaled to status register
218
 
219 21 mihad
output          posted_write_not_present_out ;  // used in target state machine - must deny read completions when this signal is 0
220 2 mihad
 
221 21 mihad
 
222 2 mihad
assign err_bc_out   = bc_out ;
223
 
224
// assign read outputs
225
/*==================================================================================================================
226
WISHBONE read FIFO data outputs - just link them to SM data outputs and delayed BE input
227
==================================================================================================================*/
228
assign wbr_fifo_data_out = data_in ;
229
assign wbr_fifo_be_out   = del_be_in ;
230
 
231
// decode if current bus command is configuration command
232
wire conf_cyc_bc = ( bc_out[3:1] == `BC_CONF_RW ) ;
233
 
234
// register for indicating that current data is also last in transfer
235
reg current_last ;
236
 
237
// register indicating that last data was transfered OK
238
reg last_transfered ;
239
always@(posedge reset_in or posedge clk_in)
240
begin
241
    if (reset_in)
242
        last_transfered <= #`FF_DELAY 1'b0 ;
243
    else
244
        last_transfered <= #`FF_DELAY ~wait_in && last_out && wtransfer_in ;
245
end
246
 
247
// status signals output assignement
248
assign mabort_received_out = mabort_in ;
249
 
250
wire tabort_ff_in = ~wait_in && rerror_in ;
251
 
252
reg    tabort_received_out ;
253
always@(posedge reset_in or posedge clk_in)
254
begin
255
    if ( reset_in )
256
        tabort_received_out <= #`FF_DELAY 1'b0 ;
257
    else
258
        tabort_received_out <= #`FF_DELAY tabort_ff_in ;
259
end
260
 
261
// error recovery indicator
262
reg err_recovery ;
263
 
264
// operation is locked until error recovery is in progress or error bit is not cleared in configuration space
265 21 mihad
wire err_lock = err_recovery ;
266 2 mihad
 
267
// three requests are possible - posted write, delayed write and delayed read
268
reg del_write_req ;
269
reg posted_write_req ;
270
reg del_read_req ;
271
 
272
// assign request output
273
assign req_out = del_write_req || posted_write_req || del_read_req ;
274
 
275 21 mihad
// posted write is not present, when WB Write Fifo is empty and posted write transaction is not beeing requested at present time
276
assign posted_write_not_present_out = !posted_write_req && wbw_fifo_empty_in ;
277
 
278 2 mihad
// write requests are staged, so data is read from source into current data register and next data register
279
reg write_req_int ;
280
always@(posedge reset_in or posedge clk_in)
281
begin
282
    if ( reset_in )
283
        write_req_int <= #`FF_DELAY 1'b0 ;
284
    else
285
        write_req_int <= #`FF_DELAY posted_write_req || del_write_req ;
286
 
287
end
288
 
289
// ready output is generated one clock after request for reads and two after for writes
290
always@(posedge reset_in or posedge clk_in)
291
begin
292
    if (reset_in)
293
        rdy_out <= #`FF_DELAY 1'b0 ;
294
    else
295
        rdy_out <= #`FF_DELAY del_read_req || ( (posted_write_req || del_write_req) && write_req_int) ;
296
end
297
 
298
// wires with logic used as inputs to request FFs
299
wire do_posted_write = ( wbw_fifo_transaction_ready_in && ~wbw_fifo_empty_in && ~err_lock ) ;
300
wire do_del          = ( del_req_in && ~err_lock && wbw_fifo_empty_in ) ;
301
wire do_del_write    = do_del &&  del_we_in ;
302
wire do_del_read     = do_del && ~del_we_in ;
303
 
304
// register for indicating current operation's data source
305
parameter DELAYED_WRITE = 1'b1 ;
306
parameter POSTED_WRITE  = 1'b0 ;
307
 
308
// new data source - depending on which transaction will be processed next - delayed read is here because source of byte enables must
309
// be specified for delayed reads also - data source is not relevant for delayed reads, so value is don't care anyway
310
wire new_data_source = (do_del_write || do_del_read) ? DELAYED_WRITE : POSTED_WRITE ; // input to data source register
311
wire data_source_change = ~req_out ;    // change (enable) for data source register - when no requests are in progress
312
 
313
reg data_source ;           // data source value
314
always@(posedge reset_in or posedge clk_in)
315
begin
316
    if (reset_in)
317
        // default value is posted write source - wbw_fifo
318
        data_source <= #`FF_DELAY POSTED_WRITE ;
319
    else
320
    if (data_source_change)
321
        // change data source on rising clock edge
322
        data_source <= #`FF_DELAY new_data_source ;
323
end
324
 
325
// multiplexer for data output to PCI MASTER state machine
326
reg [31:0] source_data ;
327
reg [3:0]  source_be ;
328 21 mihad
always@(data_source or wbw_fifo_addr_data_in or wbw_fifo_cbe_in or del_wdata_in or del_be_in or del_burst_in)
329 2 mihad
begin
330
    case (data_source)
331
        POSTED_WRITE:   begin
332
                            source_data = wbw_fifo_addr_data_in ;
333
                            source_be   = wbw_fifo_cbe_in ;
334
                        end
335
        DELAYED_WRITE:  begin
336
                            source_data = del_wdata_in ;
337 21 mihad
                            // read all bytes during delayed burst read!
338
                            source_be   = ~( del_be_in | {4{del_burst_in}} ) ;
339 2 mihad
                        end
340
    endcase
341
end
342
 
343
wire            waddr =  wbw_fifo_control_in[`ADDR_CTRL_BIT] ;
344
 
345
// address change indicator - address is allowed to be loaded only when no transaction is in progress!
346
wire            address_change = ~req_out ; // address change - whenever there is no request in progress
347
 
348
// new address - input to register storing address of current request - if posted write request will be next,
349
// load address and bus command from wbw_fifo, else load data from delayed transaction logic
350
wire     [31:0] new_address = ( ~req_out && do_posted_write ) ? wbw_fifo_addr_data_in[31:0] : del_addr_in[31:0] ;
351
wire     [3:0]  new_bc      = ( ~req_out && do_posted_write ) ? wbw_fifo_cbe_in : del_bc_in ;
352
 
353
// address counter enable - only for posted writes when data is actually transfered
354 21 mihad
wire addr_count_en = ~wait_in && posted_write_req && rtransfer_in ;
355 2 mihad
 
356
always@(posedge reset_in or posedge clk_in)
357
begin
358
    if (reset_in)
359
        bc_out <= #`FF_DELAY `BC_RESERVED0 ;
360
    else
361
    if (address_change)
362
        bc_out <= #`FF_DELAY new_bc ;
363 21 mihad
end
364 2 mihad
 
365 21 mihad
reg [29:0] current_dword_address ;
366 2 mihad
 
367
// DWORD address counter with load
368
always@(posedge reset_in or posedge clk_in)
369
begin
370
    if (reset_in)
371
        current_dword_address <= #`FF_DELAY 30'h0000_0000 ;
372
    else
373
    if (address_change)
374
        current_dword_address <= #`FF_DELAY new_address[31:2] ;
375
    else
376
    if (addr_count_en)
377
        current_dword_address <= #`FF_DELAY current_dword_address + 1'b1 ;
378 21 mihad
end
379 2 mihad
 
380
reg [1:0] current_byte_address ;
381
always@(posedge reset_in or posedge clk_in)
382
begin
383
    if (reset_in)
384
        current_byte_address <= #`FF_DELAY 2'b00 ;
385
    else
386
    if (address_change)
387
        current_byte_address <= #`FF_DELAY new_address[1:0] ;
388 21 mihad
end
389 2 mihad
 
390
// address output to PCI master state machine assignement
391
assign address_out  = { current_dword_address, current_byte_address } ;
392
 
393
// the same for erroneous address assignement
394
assign err_addr_out = { current_dword_address, current_byte_address } ;
395
 
396
// cacheline size counter - for read transaction length control
397
// cache line count is enabled during burst reads when data is actually transfered
398
wire read_count_enable = ~wait_in && del_read_req && del_burst_in && wtransfer_in  ;
399
 
400
// cache line counter is loaded when del read request is not in progress
401 21 mihad
wire read_count_load   = ~del_read_req ;
402 2 mihad
 
403 21 mihad
reg [(`WBR_ADDR_LENGTH - 1):0] max_read_count ;
404 2 mihad
always@(cache_line_size_in or del_bc_in)
405
begin
406
    if ( (cache_line_size_in >= `WBR_DEPTH) || (~del_bc_in[1] && ~del_bc_in[0]) )
407
        max_read_count = `WBR_DEPTH - 1'b1;
408
    else
409
        max_read_count = cache_line_size_in ;
410
end
411
 
412 21 mihad
reg [(`WBR_ADDR_LENGTH - 1):0] read_count ;
413 2 mihad
 
414
// cache line bound indicator - it signals when data for one complete cacheline was read
415 21 mihad
wire read_bound_comb = ~|(read_count[(`WBR_ADDR_LENGTH - 1):2]) ;
416 2 mihad
reg  read_bound ;
417 21 mihad
always@(posedge clk_in or posedge reset_in)
418 2 mihad
begin
419 21 mihad
    if ( reset_in )
420 2 mihad
        read_bound <= #`FF_DELAY 1'b0 ;
421 21 mihad
    else if (read_count_load)
422
        read_bound <= #`FF_DELAY 1'b0 ;
423 2 mihad
    else if ( read_count_enable )
424
        read_bound <= #`FF_DELAY read_bound_comb ;
425
end
426
 
427
// down counter with load
428
always@(posedge reset_in or posedge clk_in)
429
begin
430
    if (reset_in)
431 21 mihad
        read_count <= #`FF_DELAY 0 ;
432 2 mihad
    else
433
    if (read_count_load)
434
        read_count <= #`FF_DELAY max_read_count ;
435
    else
436
    if (read_count_enable)
437
        read_count <= #`FF_DELAY read_count - 1'b1 ;
438 21 mihad
 
439 2 mihad
end
440
 
441
// flip flop indicating error recovery is in progress
442
reg err_recovery_in ;
443
always@(posedge reset_in or posedge clk_in)
444
begin
445
    if (reset_in)
446
        err_recovery <= #`FF_DELAY 1'b0 ;
447
    else
448
        err_recovery <= #`FF_DELAY err_recovery_in ;
449
end
450
 
451
/*// retry counter implementation
452
reg [7:0] retry_count ;
453
 
454
wire retry_expired = ~|(retry_count[7:1]) ;
455
 
456
// loading of retry counter - whenever no request is present or other termination than retry or wait is signalled
457
wire retry_load = ~req_out || (~wait_in && rtransfer_in) ;
458
 
459
// retry DOWN counter with load
460
always@(posedge reset_in or posedge clk_in)
461
begin
462
    if (reset_in)
463
        retry_count <= #`FF_DELAY 8'hFF ;
464
    else
465
    if ( retry_load )
466
        retry_count <= #`FF_DELAY `PCI_RTY_CNT_MAX ;
467
    else
468
    if (retry_in)
469
        retry_count <= #`FF_DELAY retry_count - 1'b1 ;
470
end*/
471
 
472
/*==================================================================================================================
473
Delayed write requests are always single transfers!
474
Delayed write request starts, when no request is currently beeing processed and it is signaled from other side
475
of the bridge.
476
==================================================================================================================*/
477
// delayed write request FF input control
478
reg del_write_req_input ;
479
 
480
always@(
481 21 mihad
    do_del_write or
482
    del_write_req or
483
    posted_write_req or
484
    del_read_req or
485
    wait_in or
486
    //retry_in or
487 2 mihad
    //retry_expired or
488
    rtransfer_in or
489
    rerror_in or
490
    mabort_in
491
)
492
begin
493
    if (~del_write_req)
494 21 mihad
    begin
495 2 mihad
        // delayed write is not in progress and is requested
496
        // delayed write can be requested when no other request is in progress
497
        del_write_req_input = ~posted_write_req && ~del_read_req && do_del_write ;
498
    end
499
    else
500
    begin
501
        // delayed write request is in progress - assign input
502 21 mihad
        del_write_req_input = wait_in ||
503 2 mihad
                              ( /*~( retry_in && retry_expired) &&*/
504
                                ~rtransfer_in && ~rerror_in && ~mabort_in
505 21 mihad
                              );
506 2 mihad
    end
507
end
508
 
509
// delayed write request FLIP-FLOP
510
always@(posedge reset_in or posedge clk_in)
511
begin
512
    if (reset_in)
513
        del_write_req <= #`FF_DELAY 1'b0 ;
514
    else
515
        del_write_req <= #`FF_DELAY del_write_req_input ;
516
end
517
 
518
/*================================================================================================
519
Posted write request indicator.
520
Posted write starts whenever no request is in progress and one whole posted write is
521 21 mihad
stored in WBW_FIFO. It ends on error terminations ( master, target abort, retry expired) or
522 2 mihad
data transfer terminations if last data is on top of FIFO.
523
Continues on wait, retry, and disconnect without data.
524
================================================================================================*/
525
// posted write request FF input control
526
reg posted_write_req_input ;
527
always@(
528 21 mihad
    do_posted_write or
529
    del_write_req or
530
    posted_write_req or
531
    del_read_req or
532
    wait_in or
533
    //retry_in or
534 2 mihad
    rerror_in or
535
    mabort_in or
536 21 mihad
    //retry_expired or
537
    rtransfer_in or
538 2 mihad
    last_transfered
539
)
540
begin
541
    if (~posted_write_req)
542
    begin
543
        // posted write is not in progress
544
        posted_write_req_input = ~del_write_req && ~del_read_req && do_posted_write ;
545
    end
546
    else
547
    begin
548
        posted_write_req_input = wait_in ||
549
                                 (/*~(retry_in && retry_expired && ~rtransfer_in) &&*/
550
                                  ~rerror_in && ~mabort_in &&
551
                                  ~(last_transfered)
552
                                 ) ;
553 21 mihad
 
554 2 mihad
    end
555
end
556
 
557
// posted write request flip flop
558
always@(posedge reset_in or posedge clk_in)
559
begin
560
    if (reset_in)
561
        posted_write_req <= #`FF_DELAY 1'b0 ;
562
    else
563
        posted_write_req <= #`FF_DELAY posted_write_req_input ;
564 21 mihad
 
565 2 mihad
end
566
 
567
/*================================================================================================
568
Delayed read request indicator.
569
Delayed read starts whenever no request is in progress and delayed read request is signaled from
570 21 mihad
other side of bridge. It ends on error terminations ( master, target abort, retry expired) or
571 2 mihad
data transfer terminations if it is not burst transfer or on cache line bounds on burst transfer.
572
It also ends on disconnects.
573
Continues on wait and retry.
574
================================================================================================*/
575
// delayed read FF input control
576
reg del_read_req_input ;
577
always@(
578 21 mihad
    do_del_read or
579
    del_write_req or
580
    posted_write_req or
581
    del_read_req or
582
    last_transfered or
583
    wait_in or
584
    retry_in or
585
    //retry_expired or
586 2 mihad
    mabort_in or
587 21 mihad
    rtransfer_in or
588 2 mihad
    rerror_in or
589
    first_in or
590
    del_complete_out
591
)
592
begin
593
    if (~del_read_req)
594
    begin
595
        del_read_req_input = ~del_write_req && ~posted_write_req && ~del_complete_out && do_del_read ;
596
    end
597
    else
598
    begin
599
        del_read_req_input = wait_in ||
600
                             ( ~(retry_in && (~first_in /*|| retry_expired */)) &&
601
                               ~mabort_in && ~rerror_in &&
602
                               ~(last_transfered)
603
                             ) ;
604
    end
605
end
606
 
607
// delayed read request FF
608
always@(posedge reset_in or posedge clk_in)
609
begin
610
    if (reset_in)
611
        del_read_req <= #`FF_DELAY 1'b0 ;
612
    else
613
        del_read_req <= #`FF_DELAY del_read_req_input ;
614
end
615
 
616
// wire indicating last entry of transaction on top of fifo
617
wire wlast = wbw_fifo_control_in[`LAST_CTRL_BIT] ;
618
 
619
wire last_int = posted_write_req && wlast || del_write_req ;
620
 
621
// intermidiate data, byte enable and last registers
622
reg [31:0] intermediate_data ;
623
reg  [3:0] intermediate_be ;
624
reg        intermediate_last ;
625
 
626
wire intermediate_enable = ( posted_write_req || del_write_req ) && ( ~write_req_int || (( ~rdy_out || ~wait_in && rtransfer_in ) && ~intermediate_last)) ;
627
 
628
always@(posedge reset_in or posedge clk_in)
629
begin
630
    if ( reset_in )
631
    begin
632
        intermediate_data <= #`FF_DELAY 32'h0000_0000 ;
633 21 mihad
        intermediate_be   <= #`FF_DELAY 4'h0 ;
634 2 mihad
        intermediate_last <= #`FF_DELAY 1'b0 ;
635 21 mihad
    end
636 2 mihad
    else
637
    if ( intermediate_enable )
638
    begin
639
        intermediate_data <= #`FF_DELAY source_data ;
640 21 mihad
        intermediate_be   <= #`FF_DELAY source_be ;
641 2 mihad
        intermediate_last <= #`FF_DELAY last_int ;
642
    end
643
end
644
 
645
// multiplexer for next data
646
reg [31:0] next_data_out ;
647
reg [3:0] next_be_out   ;
648
reg write_next_last ;
649
reg [3:0] write_next_be ;
650
 
651
always@(rtransfer_in or intermediate_data or intermediate_be or intermediate_last or wbw_fifo_addr_data_in or wbw_fifo_cbe_in or wlast)
652
begin
653
    if( rtransfer_in )
654
    begin
655
        next_data_out   = wbw_fifo_addr_data_in ;
656
        write_next_last = wlast ;
657
        write_next_be   = wbw_fifo_cbe_in ;
658
    end
659
    else
660
    begin
661
        next_data_out   = intermediate_data ;
662
        write_next_last = intermediate_last ;
663
        write_next_be   = intermediate_be ;
664
    end
665
end
666
 
667
always@(del_read_req or source_be or write_next_be)
668
begin
669
    if (del_read_req)
670
        next_be_out = source_be ;
671
    else
672
        next_be_out = write_next_be ;
673
end
674
/*================================================================================================
675
WBW_FIFO read enable - read from WBW_FIFO is performed on posted writes, when data transfer
676
termination is received - transfer or disconnect with data. Reads are enabled during error
677
recovery also, since erroneous transaction must be pulled out of FIFO!
678
================================================================================================*/
679
// wbw_fifo read enable input control
680
 
681
assign wbw_renable_out = ~req_out && (do_posted_write || err_recovery) ||
682
                              posted_write_req && ( ~write_req_int || (~rdy_out && ~intermediate_last) || (~wait_in && rtransfer_in && ~intermediate_last)) ;
683
 
684
/*================================================================================================
685 21 mihad
WBR_FIFO write enable control -
686 2 mihad
writes to FIFO are possible only when delayed read request is in progress and data transfer
687
or error termination is signalled. It is not enabled on retry or disconnect without data.
688
================================================================================================*/
689
// wbr_fifo write enable control - enabled when transfer is in progress and data is transfered or error is signalled
690
assign wbr_fifo_wenable_out = del_read_req && ~wait_in && ( rtransfer_in || mabort_in || rerror_in ) ;
691
 
692
/*================================================================================================
693
WBR_FIFO control output for identifying data entries.
694
This is necesary because of prefetched reads, which partially succeed. On error, error entry
695
gets in to signal it on WISHBONE bus if WISHBONE master reads up to this entry.
696
================================================================================================*/
697
assign wbr_fifo_control_out[`ADDR_CTRL_BIT]       = 1'b0 ;
698
assign wbr_fifo_control_out[`LAST_CTRL_BIT]       = last_transfered ;
699
assign wbr_fifo_control_out[`DATA_ERROR_CTRL_BIT] = rerror_in || (mabort_in && ~conf_cyc_bc) ;
700
assign wbr_fifo_control_out[`UNUSED_CTRL_BIT]     = 1'b0 ;
701
 
702
// retry expired error for posted writes control
703
//assign err_rty_exp_out = posted_write_req && ~wait_in && retry_in && retry_expired && ~rtransfer_in;
704
assign err_rty_exp_out = 1'b0 ;
705
 
706
// error source and error signal output control logic - only for posted writes
707
assign err_source_out = mabort_in /*|| err_rty_exp_out*/ ;
708
 
709
assign err_signal_out = /*err_rty_exp_out || */ posted_write_req && ~wait_in && (mabort_in || rerror_in) ;
710
 
711
//assign del_rty_exp_out = (~wait_in && (del_read_req || del_write_req)) && (retry_in && retry_expired && ~rtransfer_in) ;
712
assign del_rty_exp_out = 1'b0 ;
713
 
714
assign del_error_out   = ~wait_in && (del_write_req || del_read_req) && ( (mabort_in && ~conf_cyc_bc) || rerror_in ) ;
715
 
716
wire   del_write_complete = del_write_req && ( rtransfer_in || rerror_in || mabort_in ) ;
717
wire   del_read_complete  = del_read_req  && ( rerror_in || mabort_in || ( last_transfered ) || ( retry_in && ~first_in ) ) ;
718
 
719
assign del_complete_out = ~wait_in && ( del_write_complete || del_read_complete ) ;
720
 
721
// next last output generation
722
assign next_last_out = del_write_req || del_read_req && ( ~del_burst_in || read_bound ) || posted_write_req && ( write_next_last ) ;
723
/*==================================================================================================================
724
Error recovery FF gets a value of one, when during posted write error occurs. It is cleared when all the data provided
725
for erroneous transaction is pulled out of WBW_FIFO
726
==================================================================================================================*/
727
 
728
// error recovery flip flop input - used when posted write is terminated with an error
729
always@(
730
    err_recovery or
731
    last_out or
732
    wlast or
733
    err_signal_out or
734
    intermediate_last
735
)
736
begin
737
    // when error recovery is not set - drive its input so it gets set
738
    if ( ~err_recovery )
739
        err_recovery_in = ~last_out && ~intermediate_last && err_signal_out ;
740
    else
741
        // when error recovery is set, wbw_fifo is enabled - clear err_recovery when last data entry of erroneous transaction is pulled out of fifo
742
        err_recovery_in = ~wlast ;
743
end
744
 
745 21 mihad
wire data_out_load = (posted_write_req || del_write_req) && ( !rdy_out || ( !wait_in && rtransfer_in ) ) ;
746
 
747
wire be_out_load  = (req_out && !rdy_out) || ( posted_write_req && !wait_in && rtransfer_in ) ;
748
 
749 2 mihad
wire last_load  = req_out && ( ~rdy_out || ~wait_in && wtransfer_in ) ;
750
 
751
always@(posedge reset_in or posedge clk_in)
752
begin
753
    if (reset_in)
754
        data_out <= #`FF_DELAY 32'h0000_0000 ;
755 21 mihad
    else
756
    if ( data_out_load )
757
        data_out <= #`FF_DELAY intermediate_data ;
758 2 mihad
end
759
 
760 21 mihad
always@(posedge clk_in or posedge reset_in)
761
begin
762
    if ( reset_in )
763
        be_out <= #`FF_DELAY 4'hF ;
764
    else
765
    if ( be_out_load )
766
        be_out <= #`FF_DELAY posted_write_req ? intermediate_be : source_be ;
767
end
768
 
769 2 mihad
always@(posedge reset_in or posedge clk_in)
770
begin
771
    if (reset_in)
772
        current_last <= #`FF_DELAY 1'b0 ;
773 21 mihad
    else
774 2 mihad
    if ( last_load )
775
        current_last <= #`FF_DELAY next_last_out ;
776
end
777
 
778
assign last_out = current_last ;
779 21 mihad
endmodule

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.