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

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [orpsocv2/] [boards/] [xilinx/] [ml501/] [rtl/] [verilog/] [xilinx_ddr2/] [ddr2_usr_rd.v] - Blame information for rev 412

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 412 julius
//*****************************************************************************
2
// DISCLAIMER OF LIABILITY
3
//
4
// This file contains proprietary and confidential information of
5
// Xilinx, Inc. ("Xilinx"), that is distributed under a license
6
// from Xilinx, and may be used, copied and/or disclosed only
7
// pursuant to the terms of a valid license agreement with Xilinx.
8
//
9
// XILINX IS PROVIDING THIS DESIGN, CODE, OR INFORMATION
10
// ("MATERIALS") "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER
11
// EXPRESSED, IMPLIED, OR STATUTORY, INCLUDING WITHOUT
12
// LIMITATION, ANY WARRANTY WITH RESPECT TO NONINFRINGEMENT,
13
// MERCHANTABILITY OR FITNESS FOR ANY PARTICULAR PURPOSE. Xilinx
14
// does not warrant that functions included in the Materials will
15
// meet the requirements of Licensee, or that the operation of the
16
// Materials will be uninterrupted or error-free, or that defects
17
// in the Materials will be corrected. Furthermore, Xilinx does
18
// not warrant or make any representations regarding use, or the
19
// results of the use, of the Materials in terms of correctness,
20
// accuracy, reliability or otherwise.
21
//
22
// Xilinx products are not designed or intended to be fail-safe,
23
// or for use in any application requiring fail-safe performance,
24
// such as life-support or safety devices or systems, Class III
25
// medical devices, nuclear facilities, applications related to
26
// the deployment of airbags, or any other applications that could
27
// lead to death, personal injury or severe property or
28
// environmental damage (individually and collectively, "critical
29
// applications"). Customer assumes the sole risk and liability
30
// of any use of Xilinx products in critical applications,
31
// subject only to applicable laws and regulations governing
32
// limitations on product liability.
33
//
34
// Copyright 2006, 2007, 2008 Xilinx, Inc.
35
// All rights reserved.
36
//
37
// This disclaimer and copyright notice must be retained as part
38
// of this file at all times.
39
//*****************************************************************************
40
//   ____  ____
41
//  /   /\/   /
42
// /___/  \  /    Vendor: Xilinx
43
// \   \   \/     Version: 3.0
44
//  \   \         Application: MIG
45
//  /   /         Filename: ddr2_usr_rd.v
46
// /___/   /\     Date Last Modified: $Date: 2008/12/23 14:26:01 $
47
// \   \  /  \    Date Created: Tue Aug 29 2006
48
//  \___\/\___\
49
//
50
//Device: Virtex-5
51
//Design Name: DDR2
52
//Purpose:
53
//   The delay between the read data with respect to the command issued is
54
//   calculted in terms of no. of clocks. This data is then stored into the
55
//   FIFOs and then read back and given as the ouput for comparison.
56
//Reference:
57
//Revision History:
58
//*****************************************************************************
59
 
60
`timescale 1ns/1ps
61
 
62
module ddr2_usr_rd #
63
  (
64
   // Following parameters are for 72-bit RDIMM design (for ML561 Reference 
65
   // board design). Actual values may be different. Actual parameters values 
66
   // are passed from design top module ddr2_mig module. Please refer to
67
   // the ddr2_mig module for actual values.
68
   parameter DQ_PER_DQS    = 8,
69
   parameter DQS_WIDTH     = 9,
70
   parameter APPDATA_WIDTH = 144,
71
   parameter ECC_WIDTH     = 72,
72
   parameter ECC_ENABLE    = 0
73
   )
74
  (
75
   input                                    clk0,
76
   input                                    rst0,
77
   input [(DQS_WIDTH*DQ_PER_DQS)-1:0]       rd_data_in_rise,
78
   input [(DQS_WIDTH*DQ_PER_DQS)-1:0]       rd_data_in_fall,
79
   input [DQS_WIDTH-1:0]                    ctrl_rden,
80
   input [DQS_WIDTH-1:0]                    ctrl_rden_sel,
81
   output reg [1:0]                         rd_ecc_error,
82
   output                                   rd_data_valid,
83
   output reg [(APPDATA_WIDTH/2)-1:0]       rd_data_out_rise,
84
   output reg [(APPDATA_WIDTH/2)-1:0]       rd_data_out_fall
85
   );
86
 
87
  // determine number of FIFO72's to use based on data width
88
  localparam RDF_FIFO_NUM = ((APPDATA_WIDTH/2)+63)/64;
89
 
90
  reg [DQS_WIDTH-1:0]               ctrl_rden_r;
91
  wire [(DQS_WIDTH*DQ_PER_DQS)-1:0] fall_data;
92
  reg [(DQS_WIDTH*DQ_PER_DQS)-1:0]  rd_data_in_fall_r;
93
  reg [(DQS_WIDTH*DQ_PER_DQS)-1:0]  rd_data_in_rise_r;
94
  wire                              rden;
95
  reg [DQS_WIDTH-1:0]               rden_sel_r
96
                                    /* synthesis syn_preserve=1 */;
97
  wire [DQS_WIDTH-1:0]              rden_sel_mux;
98
  wire [(DQS_WIDTH*DQ_PER_DQS)-1:0] rise_data;
99
 
100
  // ECC specific signals
101
  wire [((RDF_FIFO_NUM -1) *2)+1:0] db_ecc_error;
102
  reg [(DQS_WIDTH*DQ_PER_DQS)-1:0]  fall_data_r;
103
  reg                               fifo_rden_r0;
104
  reg                               fifo_rden_r1;
105
  reg                               fifo_rden_r2;
106
  reg                               fifo_rden_r3;
107
  reg                               fifo_rden_r4;
108
  reg                               fifo_rden_r5;
109
  reg                               fifo_rden_r6;
110
  wire [(APPDATA_WIDTH/2)-1:0]      rd_data_out_fall_temp;
111
  wire [(APPDATA_WIDTH/2)-1:0]      rd_data_out_rise_temp;
112
  reg                               rst_r;
113
  reg [(DQS_WIDTH*DQ_PER_DQS)-1:0]  rise_data_r;
114
  wire [((RDF_FIFO_NUM -1) *2)+1:0] sb_ecc_error;
115
 
116
 
117
  //***************************************************************************
118
 
119
  always @(posedge clk0) begin
120
    rden_sel_r        <= ctrl_rden_sel;
121
    ctrl_rden_r       <= ctrl_rden;
122
    rd_data_in_rise_r <= rd_data_in_rise;
123
    rd_data_in_fall_r <= rd_data_in_fall;
124
  end
125
 
126
  // Instantiate primitive to allow this flop to be attached to multicycle
127
  // path constraint in UCF. Multicycle path allowed for data from read FIFO.
128
  // This is the same signal as RDEN_SEL_R, but is only used to select data
129
  // (does not affect control signals)
130
  genvar rd_i;
131
  generate
132
    for (rd_i = 0; rd_i < DQS_WIDTH; rd_i = rd_i+1) begin: gen_rden_sel_mux
133
      FDRSE u_ff_rden_sel_mux
134
        (
135
         .Q   (rden_sel_mux[rd_i]),
136
         .C   (clk0),
137
         .CE  (1'b1),
138
         .D   (ctrl_rden_sel[rd_i]),
139
         .R   (1'b0),
140
         .S   (1'b0)
141
         ) /* synthesis syn_preserve=1 */;
142
    end
143
  endgenerate
144
 
145
  // determine correct read data valid signal timing
146
  assign rden = (rden_sel_r[0]) ? ctrl_rden[0] : ctrl_rden_r[0];
147
 
148
  // assign data based on the skew
149
  genvar data_i;
150
  generate
151
    for(data_i = 0; data_i < DQS_WIDTH; data_i = data_i+1) begin: gen_data
152
      assign rise_data[(data_i*DQ_PER_DQS)+(DQ_PER_DQS-1):
153
                       (data_i*DQ_PER_DQS)]
154
               = (rden_sel_mux[data_i]) ?
155
                 rd_data_in_rise[(data_i*DQ_PER_DQS)+(DQ_PER_DQS-1) :
156
                                 (data_i*DQ_PER_DQS)] :
157
                 rd_data_in_rise_r[(data_i*DQ_PER_DQS)+(DQ_PER_DQS-1):
158
                                   (data_i*DQ_PER_DQS)];
159
       assign fall_data[(data_i*DQ_PER_DQS)+(DQ_PER_DQS-1):
160
                        (data_i*DQ_PER_DQS)]
161
                = (rden_sel_mux[data_i]) ?
162
                  rd_data_in_fall[(data_i*DQ_PER_DQS)+(DQ_PER_DQS-1):
163
                                  (data_i*DQ_PER_DQS)] :
164
                  rd_data_in_fall_r[(data_i*DQ_PER_DQS)+(DQ_PER_DQS-1):
165
                                    (data_i*DQ_PER_DQS)];
166
    end
167
  endgenerate
168
 
169
  // Generate RST for FIFO reset AND for read/write enable:
170
  // ECC FIFO always being read from and written to
171
  always @(posedge clk0)
172
    rst_r <= rst0;
173
 
174
  genvar rdf_i;
175
  generate
176
    if (ECC_ENABLE) begin
177
      always @(posedge clk0) begin
178
        rd_ecc_error[0]   <= (|sb_ecc_error) & fifo_rden_r5;
179
        rd_ecc_error[1]   <= (|db_ecc_error) & fifo_rden_r5;
180
        rd_data_out_rise  <= rd_data_out_rise_temp;
181
        rd_data_out_fall  <= rd_data_out_fall_temp;
182
        rise_data_r       <= rise_data;
183
        fall_data_r       <= fall_data;
184
      end
185
 
186
      // can use any of the read valids, they're all delayed by same amount
187
      assign rd_data_valid = fifo_rden_r6;
188
 
189
      // delay read valid to take into account max delay difference btw
190
      // the read enable coming from the different DQS groups
191
      always @(posedge clk0) begin
192
        if (rst0) begin
193
          fifo_rden_r0 <= 1'b0;
194
          fifo_rden_r1 <= 1'b0;
195
          fifo_rden_r2 <= 1'b0;
196
          fifo_rden_r3 <= 1'b0;
197
          fifo_rden_r4 <= 1'b0;
198
          fifo_rden_r5 <= 1'b0;
199
          fifo_rden_r6 <= 1'b0;
200
        end else begin
201
          fifo_rden_r0 <= rden;
202
          fifo_rden_r1 <= fifo_rden_r0;
203
          fifo_rden_r2 <= fifo_rden_r1;
204
          fifo_rden_r3 <= fifo_rden_r2;
205
          fifo_rden_r4 <= fifo_rden_r3;
206
          fifo_rden_r5 <= fifo_rden_r4;
207
          fifo_rden_r6 <= fifo_rden_r5;
208
        end
209
      end
210
 
211
      for (rdf_i = 0; rdf_i < RDF_FIFO_NUM; rdf_i = rdf_i + 1) begin: gen_rdf
212
 
213
        FIFO36_72  # // rise fifo
214
          (
215
           .ALMOST_EMPTY_OFFSET     (9'h007),
216
           .ALMOST_FULL_OFFSET      (9'h00F),
217
           .DO_REG                  (1),          // extra CC output delay
218
           .EN_ECC_WRITE            ("FALSE"),
219
           .EN_ECC_READ             ("TRUE"),
220
           .EN_SYN                  ("FALSE"),
221
           .FIRST_WORD_FALL_THROUGH ("FALSE")
222
           )
223
          u_rdf
224
            (
225
             .ALMOSTEMPTY (),
226
             .ALMOSTFULL  (),
227
             .DBITERR     (db_ecc_error[rdf_i + rdf_i]),
228
             .DO          (rd_data_out_rise_temp[(64*(rdf_i+1))-1:
229
                                                 (64 *rdf_i)]),
230
             .DOP         (),
231
             .ECCPARITY   (),
232
             .EMPTY       (),
233
             .FULL        (),
234
             .RDCOUNT     (),
235
             .RDERR       (),
236
             .SBITERR     (sb_ecc_error[rdf_i + rdf_i]),
237
             .WRCOUNT     (),
238
             .WRERR       (),
239
             .DI          (rise_data_r[((64*(rdf_i+1)) + (rdf_i*8))-1:
240
                                       (64 *rdf_i)+(rdf_i*8)]),
241
             .DIP         (rise_data_r[(72*(rdf_i+1))-1:
242
                                       (64*(rdf_i+1))+ (8*rdf_i)]),
243
             .RDCLK       (clk0),
244
             .RDEN        (~rst_r),
245
             .RST         (rst_r),
246
             .WRCLK       (clk0),
247
             .WREN        (~rst_r)
248
             );
249
 
250
        FIFO36_72  # // fall_fifo
251
          (
252
           .ALMOST_EMPTY_OFFSET     (9'h007),
253
           .ALMOST_FULL_OFFSET      (9'h00F),
254
           .DO_REG                  (1),          // extra CC output delay
255
           .EN_ECC_WRITE            ("FALSE"),
256
           .EN_ECC_READ             ("TRUE"),
257
           .EN_SYN                  ("FALSE"),
258
           .FIRST_WORD_FALL_THROUGH ("FALSE")
259
           )
260
          u_rdf1
261
            (
262
             .ALMOSTEMPTY (),
263
             .ALMOSTFULL  (),
264
             .DBITERR     (db_ecc_error[(rdf_i+1) + rdf_i]),
265
             .DO          (rd_data_out_fall_temp[(64*(rdf_i+1))-1:
266
                                                 (64 *rdf_i)]),
267
             .DOP         (),
268
             .ECCPARITY   (),
269
             .EMPTY       (),
270
             .FULL        (),
271
             .RDCOUNT     (),
272
             .RDERR       (),
273
             .SBITERR     (sb_ecc_error[(rdf_i+1) + rdf_i]),
274
             .WRCOUNT     (),
275
             .WRERR       (),
276
             .DI          (fall_data_r[((64*(rdf_i+1)) + (rdf_i*8))-1:
277
                                       (64*rdf_i)+(rdf_i*8)]),
278
             .DIP         (fall_data_r[(72*(rdf_i+1))-1:
279
                                       (64*(rdf_i+1))+ (8*rdf_i)]),
280
             .RDCLK       (clk0),
281
             .RDEN        (~rst_r),
282
             .RST         (rst_r),          // or can use rst0
283
             .WRCLK       (clk0),
284
             .WREN        (~rst_r)
285
             );
286
      end
287
    end // if (ECC_ENABLE)
288
 
289
    else begin
290
       assign rd_data_valid = fifo_rden_r0;
291
       always @(posedge clk0) begin
292
          rd_data_out_rise <= rise_data;
293
          rd_data_out_fall <= fall_data;
294
          fifo_rden_r0 <= rden;
295
       end
296
    end
297
  endgenerate
298
 
299
endmodule

powered by: WebSVN 2.1.0

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