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

Subversion Repositories vg_z80_sbc

[/] [vg_z80_sbc/] [trunk/] [rtl/] [ddr_wpath.v] - Blame information for rev 36

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

Line No. Rev Author Line
1 3 hharte
//----------------------------------------------------------------------------
2
// Wishbone DDR Controller -- fast write data-path
3
// 
4
// (c) Joerg Bornschein (<jb@capsec.org>)
5
//----------------------------------------------------------------------------
6
`include "ddr_include.v"
7
 
8
module ddr_wpath (
9
        input                  clk,
10
        input                  clk90,
11
        input                  reset,
12
        // CBA async fifo
13
        input                  cba_clk,
14
        input [`CBA_RNG]       cba_din,
15
        input                  cba_wr,
16
        output                 cba_full,
17
        // WDATA async fifo
18
        input                  wdata_clk,
19
        input [`WFIFO_RNG]     wdata_din,
20
        input                  wdata_wr,
21
        output                 wdata_full,
22
        // sample to rdata
23
        output                 sample,
24
        // DDR 
25 20 hharte
        output           [2:0] ddr_clk,
26
        output           [2:0] ddr_clk_n,
27 3 hharte
        output                 ddr_ras_n,
28
        output                 ddr_cas_n,
29
        output                 ddr_we_n,
30 20 hharte
        output      [  `A_RNG] ddr_a,
31
        output      [ `BA_RNG] ddr_ba,
32
        output      [ `DM_RNG] ddr_dm,
33
        output      [ `DQ_RNG] ddr_dq,
34
        output      [`DQS_RNG] ddr_dqs,
35 3 hharte
        output                 ddr_dqs_oe
36
);
37
 
38
wire gnd = 1'b0;
39
wire vcc = 1'b1;
40
 
41
//----------------------------------------------------------------------------
42
// CBA async. fifo
43
//----------------------------------------------------------------------------
44
wire [`CBA_RNG]        cba_data;
45
wire                   cba_empty;
46
wire                   cba_ack;
47
 
48
wire                   cba_avail = ~cba_empty;
49
 
50
async_fifo #(
51
        .DATA_WIDTH( `CBA_WIDTH ),
52 20 hharte
        .ADDRESS_WIDTH( 4 )
53 3 hharte
) cba_fifo (
54
        .Data_out(   cba_data  ),
55
        .Empty_out(  cba_empty ),
56
        .ReadEn_in(  cba_ack   ),
57
        .RClk(       clk       ),
58
        //
59
        .Data_in(    cba_din   ),
60
        .WriteEn_in( cba_wr    ),
61
        .Full_out(   cba_full  ),
62
        .WClk(       cba_clk   ),
63
        .Clear_in(   reset     )
64
);
65
 
66
//----------------------------------------------------------------------------
67
// WDATA async. fifo
68
//----------------------------------------------------------------------------
69
wire [`WFIFO_RNG]      wdata_data;
70
wire                   wdata_empty;
71
wire                   wdata_ack;
72
 
73
wire                   wdata_avail = ~wdata_empty;
74
 
75
async_fifo #(
76
        .DATA_WIDTH( `WFIFO_WIDTH ),
77 20 hharte
        .ADDRESS_WIDTH( 4 )
78 3 hharte
) wdata_fifo (
79
        .Data_out(   wdata_data  ),
80
        .Empty_out(  wdata_empty ),
81
        .ReadEn_in(  wdata_ack   ),
82
        .RClk(      ~clk90       ),
83
        //
84
        .Data_in(    wdata_din   ),
85
        .WriteEn_in( wdata_wr    ),
86
        .Full_out(   wdata_full  ),
87
        .WClk(       wdata_clk   ),
88
        .Clear_in(   reset       )
89
);
90
 
91
 
92
//----------------------------------------------------------------------------
93
// Handle CBA 
94
//----------------------------------------------------------------------------
95
reg  [3:0]      delay_count;
96
 
97
reg [`CBA_RNG]  ddr_cba;
98
wire [`CBA_RNG] CBA_NOP = { `DDR_CMD_NOP, 15'b0 };
99
 
100
assign cba_ack = cba_avail & (delay_count == 0);
101
 
102
wire [`CMD_RNG] cba_cmd = cba_data[(`CBA_WIDTH-1):(`CBA_WIDTH-3)];
103
 
104
always @(posedge clk)
105
begin
106
        if (reset) begin
107
                delay_count <= 0;
108
                ddr_cba     <= CBA_NOP;
109
        end else begin
110
                if (delay_count != 0) begin
111
                        delay_count <= delay_count - 1;
112
                        ddr_cba     <= CBA_NOP;
113
        end
114
 
115
                if (!cba_ack) begin
116
                        ddr_cba  <= CBA_NOP;
117
                end else begin
118
                        ddr_cba <= cba_data;
119
 
120
                        case (cba_cmd)
121
                                `DDR_CMD_MRS   : delay_count <= 2;
122
                                `DDR_CMD_AR    : delay_count <= 14;
123
                                `DDR_CMD_ACT   : delay_count <= 4;
124
                                `DDR_CMD_PRE   : delay_count <= 2;
125
                                `DDR_CMD_READ  : delay_count <= 6;   // XXX
126
                                `DDR_CMD_WRITE : delay_count <= 8;   // XXX
127
                        endcase
128
                end
129
        end
130
end
131
 
132
 
133
//----------------------------------------------------------------------------
134
// READ-SHIFT-REGISTER
135
//----------------------------------------------------------------------------
136 20 hharte
reg [7:0] read_shr;
137 3 hharte
wire      read_cmd = (cba_cmd == `DDR_CMD_READ) & cba_ack;
138 20 hharte
assign    sample   = read_shr[6];
139 3 hharte
 
140
always @(posedge clk)
141
begin
142
        if (reset)
143
                read_shr <= 'b0;
144
        else begin
145
                if (read_cmd)
146 20 hharte
                        read_shr <= { 8'b00011000 };
147 3 hharte
                else
148 20 hharte
                        read_shr <= { read_shr[6:0], 1'b0 };
149 3 hharte
        end
150
end
151
 
152
//----------------------------------------------------------------------------
153
// WRITE-SHIFT-REGISTER
154
//----------------------------------------------------------------------------
155
 
156
reg [0:4] write_shr;
157
wire      write_cmd = (cba_cmd == `DDR_CMD_WRITE) & cba_ack;
158
 
159
always @(posedge clk)
160
begin
161
        if (reset)
162
                write_shr <= 'b0;
163
        else begin
164
                if (write_cmd)
165
                        write_shr <= { 5'b11111 };
166
                else
167
                        write_shr <= { write_shr[1:4], 1'b0 };
168
        end
169
end
170
 
171
//----------------------------------------------------------------------------
172
// DDR_DQS, DDR_DQS_OE
173
//----------------------------------------------------------------------------
174
genvar i;
175
 
176
reg ddr_dqs_oe_reg;
177
assign ddr_dqs_oe = ddr_dqs_oe_reg;
178
 
179
always @(negedge clk)
180
begin
181
  ddr_dqs_oe_reg <= write_shr[0];
182
end
183
 
184 20 hharte
generate
185
for (i=0; i<3; i=i+1) begin : CLK
186
        FDDRRSE ddr_clk_reg (
187
                .Q(   ddr_clk[i]   ),
188
                .C0(  clk90        ),
189
                .C1( ~clk90        ),
190
                .CE(  vcc          ),
191
                .D0(  vcc          ),
192
                .D1(  gnd          ),
193
                .R(   gnd          ),
194
                .S(   gnd          )
195
        );
196 3 hharte
 
197 20 hharte
        FDDRRSE ddr_clk_n_reg (
198
                .Q(   ddr_clk_n[i] ),
199
                .C0(  clk90        ),
200
                .C1( ~clk90        ),
201
                .CE(  vcc          ),
202
                .D0(  gnd          ),
203
                .D1(  vcc          ),
204
                .R(   gnd          ),
205
                .S(   gnd          )
206
        );
207
end
208
endgenerate
209 3 hharte
 
210
generate
211
for (i=0; i<`DQS_WIDTH; i=i+1) begin : DQS
212
        FDDRRSE ddr_dqs_reg (
213
                .Q(   ddr_dqs[i]   ),
214
                .C0(  clk          ),
215
                .C1( ~clk          ),
216
                .CE(  vcc          ),
217
                .D0(  write_shr[1] ),
218
                .D1(  gnd          ),
219
                .R(   gnd          ),
220
                .S(   gnd          )
221
        );
222
end
223
endgenerate
224
 
225
 
226
//----------------------------------------------------------------------------
227
// DQ data output
228
//----------------------------------------------------------------------------
229
wire [`DQ_RNG] buf_d0;
230
wire [`DM_RNG] buf_m0;
231
reg  [`DQ_RNG] buf_d1;       // pipleine high word data
232
reg  [`DM_RNG] buf_m1;       // pipleine high word mask
233
 
234
assign buf_d0 = wdata_data[`WFIFO_D0_RNG];
235
assign buf_m0 = wdata_data[`WFIFO_M0_RNG];
236
 
237
always @(negedge clk90)
238
begin
239
        buf_d1 <= wdata_data[`WFIFO_D1_RNG];
240
        buf_m1 <= wdata_data[`WFIFO_M1_RNG];
241
end
242
 
243
assign wdata_ack = write_shr[1];
244
 
245
// generate DDR_DQ register
246
generate
247
for (i=0; i<`DQ_WIDTH; i=i+1) begin : DQ_REG
248
        FDDRRSE ddr_dq_reg (
249
                .Q(   ddr_dq[i]    ),
250
                .C0( ~clk90        ),
251
                .C1(  clk90        ),
252
                .CE(  vcc          ),
253
                .D0(  buf_d0[i]    ),
254
                .D1(  buf_d1[i]    ),
255
                .R(   gnd          ),
256
                .S(   gnd          )
257
        );
258
end
259
endgenerate
260
 
261
// generate DDR_DM register
262
generate
263
for (i=0; i<`DM_WIDTH; i=i+1) begin : DM_REG
264
        FDDRRSE ddr_dm_reg (
265
                .Q(   ddr_dm[i]    ),
266
                .C0( ~clk90        ),
267
                .C1(  clk90        ),
268
                .CE(  vcc          ),
269
                .D0(  buf_m0[i]    ),
270
                .D1(  buf_m1[i]    ),
271
                .R(   gnd          ),
272
                .S(   gnd          )
273
        );
274
end
275
endgenerate
276
 
277
//----------------------------------------------------------------------------
278
// Connect ddr_cba to actual DDR pins
279
//----------------------------------------------------------------------------
280
assign ddr_a     = ddr_cba[(`A_WIDTH-1):0];
281
assign ddr_ba    = ddr_cba[(`A_WIDTH+`BA_WIDTH-1):(`A_WIDTH)];
282
assign ddr_ras_n = ddr_cba[(`CBA_WIDTH-1)];
283
assign ddr_cas_n = ddr_cba[(`CBA_WIDTH-2)];
284
assign ddr_we_n  = ddr_cba[(`CBA_WIDTH-3)];
285
 
286
endmodule

powered by: WebSVN 2.1.0

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