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

Subversion Repositories sdr_ctrl

[/] [sdr_ctrl/] [trunk/] [rtl/] [core/] [sdrc_req_gen.v] - Blame information for rev 50

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

Line No. Rev Author Line
1 3 dinesha
/*********************************************************************
2
 
3
  SDRAM Controller Request Generation
4
 
5
  This file is part of the sdram controller project
6
  http://www.opencores.org/cores/sdr_ctrl/
7
 
8
  Description: SDRAM Controller Reguest Generation
9 33 dinesha
 
10
  Address Generation Based on cfg_colbits
11
     cfg_colbits= 2'b00
12
            Address[7:0]    - Column Address
13
            Address[9:8]    - Bank Address
14
            Address[21:10]  - Row Address
15
     cfg_colbits= 2'b01
16
            Address[8:0]    - Column Address
17
            Address[10:9]   - Bank Address
18
            Address[22:11]  - Row Address
19
     cfg_colbits= 2'b10
20
            Address[9:0]    - Column Address
21
            Address[11:10]   - Bank Address
22
            Address[23:12]  - Row Address
23
     cfg_colbits= 2'b11
24
            Address[10:0]    - Column Address
25
            Address[12:11]   - Bank Address
26
            Address[24:13]  - Row Address
27
 
28 3 dinesha
  The SDRAMs are operated in 4 beat burst mode.
29 46 dinesha
 
30
  If Wrap = 0;
31
      If the current burst cross the page boundary, then this block split the request into two coressponding change in address and request length
32
 
33
  if the current burst cross the page boundar.
34 33 dinesha
  This module takes requests from the memory controller,
35 3 dinesha
  chops them to page boundaries if wrap=0,
36
  and passes the request to bank_ctl
37 50 dinesha
 
38
  Note: With Wrap = 0, each request from Application layer will be splited into two request,
39
        if the current burst cross the page boundary.
40
 
41 3 dinesha
  To Do:
42
    nothing
43
 
44
  Author(s):
45
      - Dinesh Annayya, dinesha@opencores.org
46 47 dinesha
  Version  : 0.0 - 8th Jan 2012
47
             0.1 - 5th Feb 2012, column/row/bank address are register to improve the timing issue in FPGA synthesis
48 3 dinesha
 
49
 
50
 
51
 Copyright (C) 2000 Authors and OPENCORES.ORG
52
 
53
 This source file may be used and distributed without
54
 restriction provided that this copyright statement is not
55
 removed from the file and that any derivative work contains
56
 the original copyright notice and the associated disclaimer.
57
 
58
 This source file is free software; you can redistribute it
59
 and/or modify it under the terms of the GNU Lesser General
60
 Public License as published by the Free Software Foundation;
61
 either version 2.1 of the License, or (at your option) any
62
later version.
63
 
64
 This source is distributed in the hope that it will be
65
 useful, but WITHOUT ANY WARRANTY; without even the implied
66
 warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
67
 PURPOSE.  See the GNU Lesser General Public License for more
68
 details.
69
 
70
 You should have received a copy of the GNU Lesser General
71
 Public License along with this source; if not, download it
72
 from http://www.opencores.org/lgpl.shtml
73
 
74
*******************************************************************/
75
 
76 37 dinesha
`include "sdrc_define.v"
77 3 dinesha
 
78
module sdrc_req_gen (clk,
79
                    reset_n,
80 47 dinesha
                    cfg_colbits,
81
                    sdr_width,
82 3 dinesha
 
83
                    /* Request from app */
84 46 dinesha
                    req,                // Transfer Request
85
                    req_id,             // ID for this transfer
86
                    req_addr,           // SDRAM Address
87
                    req_len,            // Burst Length (in 32 bit words)
88
                    req_wrap,           // Wrap mode request (xfr_len = 4)
89
                    req_wr_n,           // 0 => Write request, 1 => read req
90
                    req_ack,            // Request has been accepted
91 3 dinesha
 
92 47 dinesha
                    /* Req to xfr_ctl */
93
                    r2x_idle,
94
 
95 3 dinesha
                    /* Req to bank_ctl */
96 47 dinesha
                    r2b_req,            // request
97
                    r2b_req_id,         // ID
98
                    r2b_start,          // First chunk of burst
99
                    r2b_last,           // Last chunk of burst
100
                    r2b_wrap,           // Wrap Mode
101
                    r2b_ba,             // bank address
102
                    r2b_raddr,          // row address
103
                    r2b_caddr,          // col address
104
                    r2b_len,            // length
105
                    r2b_write,          // write request
106 3 dinesha
                    b2r_ack,
107 47 dinesha
                    b2r_arb_ok
108
                    );
109 3 dinesha
 
110
parameter  APP_AW   = 30;  // Application Address Width
111
parameter  APP_DW   = 32;  // Application Data Width 
112
parameter  APP_BW   = 4;   // Application Byte Width
113
parameter  APP_RW   = 9;   // Application Request Width
114
 
115
parameter  SDR_DW   = 16;  // SDR Data Width 
116
parameter  SDR_BW   = 2;   // SDR Byte Width
117
 
118 50 dinesha
parameter  REQ_BW   = 12;   //  Request Width
119 47 dinesha
input                   clk           ;
120
input                   reset_n       ;
121
input [1:0]             cfg_colbits   ; // 2'b00 - 8 Bit column address, 2'b01 - 9 Bit, 10 - 10 bit, 11 - 11Bits
122 3 dinesha
 
123 47 dinesha
/* Request from app */
124
input                   req           ; // Request 
125
input [`SDR_REQ_ID_W-1:0] req_id      ; // Request ID
126
input [APP_AW-1:0]       req_addr      ; // Request Address
127
input [APP_RW-1:0]       req_len       ; // Request length
128
input                   req_wr_n      ; // 0 -Write, 1 - Read
129
input                   req_wrap      ; // 1 - Wrap the Address on page boundary
130
output                  req_ack       ; // Request Ack
131 3 dinesha
 
132 47 dinesha
/* Req to bank_ctl */
133 50 dinesha
output                  r2x_idle      ;
134
output                  r2b_req       ; // Request
135
output                  r2b_start     ; // First Junk of the Burst Access
136
output                  r2b_last      ; // Last Junk of the Burst Access
137
output                  r2b_write     ; // 1 - Write, 0 - Read
138
output                  r2b_wrap      ; // 1 - Wrap the Address at the page boundary.
139 47 dinesha
output [`SDR_REQ_ID_W-1:0]       r2b_req_id;
140 50 dinesha
output [1:0]             r2b_ba        ; // Bank Address
141
output [11:0]            r2b_raddr     ; // Row Address
142
output [11:0]            r2b_caddr     ; // Column Address
143
output [REQ_BW-1:0]      r2b_len       ; // Burst Length
144
input                   b2r_ack       ; // Request Ack
145
input                   b2r_arb_ok    ; // Bank controller fifo is not full and ready to accept the command
146 3 dinesha
//
147 47 dinesha
input [1:0]              sdr_width; // 2'b00 - 32 Bit, 2'b01 - 16 Bit, 2'b1x - 8Bit
148 16 dinesha
 
149 3 dinesha
 
150
   /****************************************************************************/
151
   // Internal Nets
152
 
153
   `define REQ_IDLE        1'b0
154
   `define REQ_ACTIVE      1'b1
155
 
156 47 dinesha
   reg                  req_st, next_req_st;
157
   reg                  r2x_idle, req_ack, r2b_req, r2b_start,
158
                        r2b_write, req_idle, req_ld, lcl_wrap;
159 3 dinesha
   reg [`SDR_REQ_ID_W-1:0]       r2b_req_id;
160 50 dinesha
   reg [REQ_BW-1:0]      lcl_req_len;
161 3 dinesha
 
162 47 dinesha
   wire                 r2b_last, page_ovflw;
163 50 dinesha
   wire [REQ_BW-1:0]     r2b_len, next_req_len;
164
   wire [REQ_BW:0]       max_r2b_len;
165 3 dinesha
 
166 47 dinesha
   reg [1:0]             r2b_ba;
167
   reg [11:0]            r2b_raddr;
168
   reg [11:0]            r2b_caddr;
169 3 dinesha
 
170 46 dinesha
   reg [APP_AW-1:0]      curr_sdr_addr ;
171
   wire [APP_AW-1:0]     next_sdr_addr ;
172 3 dinesha
 
173 45 dinesha
 
174
//--------------------------------------------------------------------
175
// Generate the internal Adress and Burst length Based on sdram width
176
//--------------------------------------------------------------------
177
reg [APP_AW:0]           req_addr_int;
178
reg [APP_RW-1:0]         req_len_int;
179 47 dinesha
 
180 45 dinesha
always @(*) begin
181 46 dinesha
   if(sdr_width == 2'b00) begin // 32 Bit SDR Mode
182
      req_addr_int     = {1'b0,req_addr};
183
      req_len_int      = req_len;
184
   end else if(sdr_width == 2'b01) begin // 16 Bit SDR Mode
185
      // Changed the address and length to match the 16 bit SDR Mode
186
      req_addr_int     = {req_addr,1'b0};
187
      req_len_int      = {req_len,1'b0};
188
   end else  begin // 8 Bit SDR Mode
189
      // Changed the address and length to match the 16 bit SDR Mode
190
      req_addr_int    = {req_addr,2'b0};
191
      req_len_int     = {req_len,2'b0};
192
   end
193 45 dinesha
end
194
 
195 3 dinesha
   //
196 46 dinesha
   // Identify the page over flow.
197
   // Find the Maximum Burst length allowed from the selected column
198
   // address, If the requested burst length is more than the allowed Maximum
199
   // burst length, then we need to handle the bank cross over case and we
200
   // need to split the reuest.
201 3 dinesha
   //
202 13 dinesha
   assign max_r2b_len = (cfg_colbits == 2'b00) ? (12'h100 - r2b_caddr) :
203
                        (cfg_colbits == 2'b01) ? (12'h200 - r2b_caddr) :
204
                        (cfg_colbits == 2'b10) ? (12'h400 - r2b_caddr) : (12'h800 - r2b_caddr);
205 3 dinesha
 
206 46 dinesha
 
207
     // If the wrap = 0 and current application burst length is crossing the page boundary, 
208
     // then request will be split into two with corresponding change in request address and request length.
209
     //
210
     // If the wrap = 0 and current burst length is not crossing the page boundary, 
211
     // then request from application layer will be transparently passed on the bank control block.
212
 
213
     //
214
     // if the wrap = 1, then this block will not modify the request address and length. 
215
     // The wrapping functionality will be handle by the bank control module and 
216
     // column address will rewind back as follows XX -> FF ? 00 ? 1
217
     //
218 50 dinesha
     // Note: With Wrap = 0, each request from Application layer will be spilited into two request, 
219
     // if the current burst cross the page boundary. 
220 3 dinesha
   assign page_ovflw = ({1'b0, lcl_req_len} > max_r2b_len) ? ~lcl_wrap : 1'b0;
221
 
222
   assign r2b_len = (page_ovflw) ? max_r2b_len : lcl_req_len;
223
 
224
   assign next_req_len = lcl_req_len - r2b_len;
225
 
226 46 dinesha
   assign next_sdr_addr = curr_sdr_addr + r2b_len;
227 3 dinesha
 
228
 
229
   assign r2b_wrap = lcl_wrap;
230
 
231
   assign r2b_last = ~page_ovflw;
232
//
233
//
234
//
235
   always @ (posedge clk) begin
236
 
237 47 dinesha
      r2b_start      <= (req_ack) ? 1'b1 :
238
                        (b2r_ack) ? 1'b0 : r2b_start;
239 3 dinesha
 
240 47 dinesha
      r2b_write      <= (req_ack) ? ~req_wr_n : r2b_write;
241 3 dinesha
 
242 47 dinesha
      r2b_req_id     <= (req_ack) ? req_id : r2b_req_id;
243 3 dinesha
 
244 47 dinesha
      lcl_wrap       <= (req_ack) ? req_wrap : lcl_wrap;
245 3 dinesha
 
246 47 dinesha
      lcl_req_len    <= (req_ack) ? req_len_int  :
247
                        (req_ld) ? next_req_len : lcl_req_len;
248 3 dinesha
 
249 47 dinesha
      curr_sdr_addr  <= (req_ack) ? req_addr_int :
250
                        (req_ld) ? next_sdr_addr : curr_sdr_addr;
251 3 dinesha
 
252
   end // always @ (posedge clk)
253
 
254
   always @ (*) begin
255
 
256
      case (req_st)      // synopsys full_case parallel_case
257
 
258
        `REQ_IDLE : begin
259
           r2x_idle = ~req;
260
           req_idle = 1'b1;
261
           req_ack = req & b2r_arb_ok;
262
           req_ld = 1'b0;
263
           r2b_req = 1'b0;
264
           next_req_st = (req & b2r_arb_ok) ? `REQ_ACTIVE : `REQ_IDLE;
265
        end // case: `REQ_IDLE
266
 
267
        `REQ_ACTIVE : begin
268
           r2x_idle = 1'b0;
269
           req_idle = 1'b0;
270
           req_ack = 1'b0;
271
           req_ld = b2r_ack;
272
           r2b_req = 1'b1;                       // req_gen to bank_req
273
           next_req_st = (b2r_ack & r2b_last) ? `REQ_IDLE : `REQ_ACTIVE;
274
        end // case: `REQ_ACTIVE
275
 
276
      endcase // case(req_st)
277
 
278
   end // always @ (req_st or ....)
279
 
280
   always @ (posedge clk)
281
      if (~reset_n) begin
282
         req_st <= `REQ_IDLE;
283
      end // if (~reset_n)
284
      else begin
285
         req_st <= next_req_st;
286
      end // else: !if(~reset_n)
287
//
288
// addrs bits for the bank, row and column
289
//
290 47 dinesha
// Register row/column/bank to improve fpga timing issue
291
wire [APP_AW-1:0]        map_address ;
292 3 dinesha
 
293 47 dinesha
assign      map_address  = (req_ack) ? req_addr_int :
294
                           (req_ld)  ? next_sdr_addr : curr_sdr_addr;
295
 
296
always @ (posedge clk) begin
297 13 dinesha
// Bank Bits are always - 2 Bits
298 47 dinesha
    r2b_ba <= (cfg_colbits == 2'b00) ? {map_address[9:8]}   :
299 50 dinesha
              (cfg_colbits == 2'b01) ? {map_address[10:9]}  :
300
              (cfg_colbits == 2'b10) ? {map_address[11:10]} : map_address[12:11];
301 3 dinesha
 
302 46 dinesha
/********************
303
*  Colbits Mapping:
304
*           2'b00 - 8 Bit
305
*           2'b01 - 16 Bit
306
*           2'b10 - 10 Bit
307
*           2'b11 - 11 Bits
308
************************/
309 47 dinesha
    r2b_caddr <= (cfg_colbits == 2'b00) ? {4'b0, map_address[7:0]} :
310 50 dinesha
                 (cfg_colbits == 2'b01) ? {3'b0, map_address[8:0]} :
311
                 (cfg_colbits == 2'b10) ? {2'b0, map_address[9:0]} : {1'b0, map_address[10:0]};
312 3 dinesha
 
313 47 dinesha
    r2b_raddr <= (cfg_colbits == 2'b00)  ? map_address[21:10] :
314 50 dinesha
                 (cfg_colbits == 2'b01)  ? map_address[22:11] :
315
                 (cfg_colbits == 2'b10)  ? map_address[23:12] : map_address[24:13];
316 47 dinesha
end
317 3 dinesha
 
318
endmodule // sdr_req_gen

powered by: WebSVN 2.1.0

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