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

Subversion Repositories srdydrdy_lib

[/] [srdydrdy_lib/] [trunk/] [rtl/] [verilog/] [buffers/] [sd_fifo_tail_b.v] - Blame information for rev 6

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

Line No. Rev Author Line
1 2 ghutchis
//----------------------------------------------------------------------
2
// Srdy/Drdy FIFO Tail "B"
3
//
4
// Building block for FIFOs.  The "B" (big) FIFO is design for larger FIFOs
5
// based around memories, with sizes that may not be a power of 2.
6
//
7
// The bound inputs allow multiple FIFO controllers to share a single
8
// memory.  The enable input is for arbitration between multiple FIFO
9
// controllers, or between the fifo head and tail controllers on a
10
// single port memory.
11
//
12
// The commit parameter enables read/commit behavior.  This creates
13
// two read pointers, one which is used for reading from memory and
14
// a commit pointer which is sent to the head block.  The abort behavior
15
// has a 3-cycle performance penalty due to pipeline flush.
16
//
17
// The FIFO tail assumes a memory with one-cycle read latency, and
18
// has output buffering to compensate for this.
19
//
20
// Naming convention: c = consumer, p = producer, i = internal interface
21
//----------------------------------------------------------------------
22
// Author: Guy Hutchison
23
//
24
// This block is uncopyrighted and released into the public domain.
25
//----------------------------------------------------------------------
26
 
27
// Clocking statement for synchronous blocks.  Default is for
28
// posedge clocking and positive async reset
29
`ifndef SDLIB_CLOCKING
30
 `define SDLIB_CLOCKING posedge clk or posedge reset
31
`endif
32
 
33
// delay unit for nonblocking assigns, default is to #1
34
`ifndef SDLIB_DELAY
35
 `define SDLIB_DELAY #1
36
`endif
37
 
38
 
39
module sd_fifo_tail_b
40
  #(parameter width=8,
41
    parameter depth=16,
42
    parameter commit=0,
43
    parameter asz=$clog2(depth))
44
    (
45
     input       clk,
46
     input       reset,
47
     input       enable,
48
 
49
     input [asz-1:0]      bound_low,
50
     input [asz-1:0]      bound_high,
51
 
52
     output reg [asz-1:0]   cur_rdptr,
53
     output reg [asz-1:0]   com_rdptr,
54
     input  [asz-1:0]       wrptr,
55
     output reg           mem_re,
56
 
57
     output reg [asz:0]   usage,
58
 
59
     output               p_srdy,
60
     input                p_drdy,
61
     input                p_commit,
62
     input                p_abort,
63
     input [width-1:0]    mem_rd_data,
64
     output [width-1:0]   p_data
65
     );
66
 
67
  reg [asz-1:0]           nxt_cur_rdptr;
68
  reg [asz-1:0]           cur_rdptr_p1;
69
  reg                   empty, full;
70
 
71
  reg                   nxt_irdy;
72
 
73
  reg [width-1:0]       hold_a, hold_b;
74
  reg                   valid_a, valid_b;
75
  reg                   prev_re;
76
  reg [asz:0]           tmp_usage;
77
  reg [asz:0]           fifo_size;
78 6 ghutchis
  wire                  rbuf1_drdy;
79
  wire                  ip_srdy, ip_drdy;
80
  wire [width-1:0]       ip_data;
81 2 ghutchis
 
82
  // Stage 1 -- Read pipeline
83
  // issue a read if:
84
  //   1) we are enabled
85
  //   2) valid_a is 0, OR
86
  //   3) valid_b is 0, OR
87
  //   4) valid_a && valid_b && trdy
88
  always @*
89
    begin
90
 
91
      if (cur_rdptr[asz-1:0] == (bound_high))
92
        begin
93
          cur_rdptr_p1[asz-1:0] = bound_low;
94
        end
95
      else
96
        cur_rdptr_p1 = cur_rdptr + 1;
97
 
98
      empty = (wrptr == cur_rdptr);
99
 
100
      if (commit && p_abort)
101
        begin
102
          nxt_cur_rdptr = com_rdptr;
103
          mem_re = 0;
104
        end
105 6 ghutchis
//      else if (enable & !empty & (!valid_a | (!prev_re & !valid_b) | 
106
//                             (valid_a & valid_b & p_drdy)))
107
      else if (enable & !empty & ip_drdy)
108 2 ghutchis
        begin
109
          nxt_cur_rdptr = cur_rdptr_p1;
110
          mem_re = 1;
111
        end
112
      else
113
        begin
114
          nxt_cur_rdptr = cur_rdptr;
115
          mem_re = 0;
116
        end // else: !if(enable & !empty & (!valid_a | !valid_b |...
117
 
118
      fifo_size = (bound_high - bound_low + 1);
119
      tmp_usage = wrptr[asz-1:0] - cur_rdptr[asz-1:0];
120
      if (~tmp_usage[asz])
121
        usage = tmp_usage[asz-1:0];
122
      else
123
        usage = fifo_size - (cur_rdptr[asz-1:0] - wrptr[asz-1:0]);
124
    end
125
 
126
  always @(posedge clk)
127
    begin
128
      if (reset)
129
        cur_rdptr <= `SDLIB_DELAY bound_low;
130
      else
131
        cur_rdptr <= `SDLIB_DELAY nxt_cur_rdptr;
132
    end
133
 
134
  generate
135
    if (commit == 1)
136
      begin : gen_s0
137
        reg [asz-1:0]  rdaddr_s0, rdaddr_a, rdaddr_b;
138
        reg [asz-1:0]  nxt_com_rdptr;
139
 
140
        always @(posedge clk)
141
          begin
142
            if (reset)
143
              com_rdptr <= `SDLIB_DELAY bound_low;
144
            else
145
              com_rdptr <= `SDLIB_DELAY nxt_com_rdptr;
146
 
147
            if (mem_re)
148
              rdaddr_s0 <= `SDLIB_DELAY cur_rdptr;
149
          end
150
      end
151
    else
152
      begin : gen_ns0
153
        always @*
154
          com_rdptr = cur_rdptr;
155
      end
156
  endgenerate
157
 
158
  // Stage 2 -- read buffering
159
  always @(`SDLIB_CLOCKING)
160
    begin
161
      if (reset)
162
        begin
163
          prev_re <= `SDLIB_DELAY 0;
164 6 ghutchis
        end
165 2 ghutchis
      else
166
        begin
167
          if (commit && p_abort)
168
            prev_re <= `SDLIB_DELAY 0;
169
          else
170
            prev_re <= `SDLIB_DELAY mem_re;
171 6 ghutchis
        end // else: !if(reset)
172
    end // always @ (`SDLIB_CLOCKING)
173 2 ghutchis
 
174
  generate
175
    if (commit == 1)
176 6 ghutchis
      begin
177
        wire [asz-1:0] ip_rdaddr, p_rdaddr;
178 2 ghutchis
 
179 6 ghutchis
        sd_input #(asz+width) rbuf1
180
          (.clk (clk), .reset (p_abort | reset),
181
           .c_srdy (prev_re),
182
           .c_drdy (rbuf1_drdy),
183
           .c_data ({rdaddr_s0,mem_rd_data}),
184
           .ip_srdy (ip_srdy), .ip_drdy (ip_drdy),
185
           .ip_data ({ip_rdaddr,ip_data}));
186
 
187
        sd_output #(asz+width) rbuf2
188
          (.clk (clk), .reset (p_abort | reset),
189
           .ic_srdy (ip_srdy),
190
           .ic_drdy (ip_drdy),
191
           .ic_data ({ip_rdaddr,ip_data}),
192
           .p_srdy (p_srdy), .p_drdy (p_drdy),
193
           .p_data ({p_rdaddr,p_data}));
194 2 ghutchis
 
195
        always @*
196
          begin
197
            if (p_commit)
198 6 ghutchis
              nxt_com_rdptr = p_rdaddr;
199 2 ghutchis
            else
200
              nxt_com_rdptr = com_rdptr;
201
          end
202 6 ghutchis
      end // if (commit == 1)
203
    else
204
      begin
205
        sd_input #(width) rbuf1
206
          (.clk (clk), .reset (p_abort | reset),
207
           .c_srdy (prev_re),
208
           .c_drdy (rbuf1_drdy),
209
           .c_data (mem_rd_data),
210
           .ip_srdy (ip_srdy), .ip_drdy (ip_drdy),
211
           .ip_data (ip_data));
212
 
213
        sd_output #(width) rbuf2
214
          (.clk (clk), .reset (p_abort | reset),
215
           .ic_srdy (ip_srdy),
216
           .ic_drdy (ip_drdy),
217
           .ic_data (ip_data),
218
           .p_srdy (p_srdy), .p_drdy (p_drdy),
219
           .p_data (p_data));
220
      end // else: !if(commit == 1)
221 2 ghutchis
  endgenerate
222
 
223
endmodule // it_fifo

powered by: WebSVN 2.1.0

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