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

Subversion Repositories sdram_ctrl

[/] [sdram_ctrl/] [trunk/] [test_bench/] [mt48lc4m32b2.vhd] - Blame information for rev 10

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

Line No. Rev Author Line
1 2 ntpqa
-----------------------------------------------------------------------------------------
2
--
3
--     File Name: MT48LC4M32B2.VHD
4
--       Version: 2.0
5
--          Date: January 24th, 2002
6
--         Model: Behavioral
7
--     Simulator: Model Technology
8
--
9
--  Dependencies: None
10
--
11
--         Email: modelsupport@micron.com
12
--       Company: Micron Technology, Inc.
13
--   Part Number: MT48LC4M32A2 (1Mb x 32 x 4 Banks)
14
--
15
--   Description: Micron 128Mb SDRAM
16
--
17
--    Limitation: - Doesn't check for 4096-cycle refresh
18
--
19
--          Note: - Set simulator resolution to "ps" accuracy
20
--
21
--    Disclaimer: THESE DESIGNS ARE PROVIDED "AS IS" WITH NO WARRANTY 
22
--                WHATSOEVER AND MICRON SPECIFICALLY DISCLAIMS ANY 
23
--                IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR
24
--                A PARTICULAR PURPOSE, OR AGAINST INFRINGEMENT.
25
--
26
--                Copyright (c) 1998 Micron Semiconductor Products, Inc.
27
--                All rights researved
28
--
29
--  Rev  Author          Date        Changes
30
--  ---  --------------------------  -------------------------------------
31
--  2.0  SH              01/24/2002  - Second Release
32
--       Micron Technology Inc.
33
--
34
--------------------------------------------------------------------------
35
 
36
LIBRARY IEEE;
37
    USE IEEE.STD_LOGIC_1164.ALL;
38
    USE IEEE.STD_LOGIC_UNSIGNED.ALL;
39
    USE IEEE.STD_LOGIC_ARITH.ALL;
40
 
41
ENTITY mt48lc4m32b2 IS
42
    GENERIC (
43
        -- Timing Parameters for -75 (PC133) and CL = 3
44
        tAC       : TIME    :=  5.4 ns;
45
        tHZ       : TIME    :=  5.4 ns;
46
        tOH       : TIME    :=  2.7 ns;
47
        tMRD      : INTEGER :=  2;          -- 2 Clk Cycles
48
        tRAS      : TIME    := 44.0 ns;
49
        tRC       : TIME    := 66.0 ns;
50
        tRCD      : TIME    := 20.0 ns;
51
        tRFC      : TIME    := 66.0 ns;
52
        tRP       : TIME    := 20.0 ns;
53
        tRRD      : TIME    := 15.0 ns;
54
        tWRa      : TIME    :=  7.5 ns;     -- Auto precharge
55
        tWRm      : TIME    := 15.0 ns;     -- Manual Precharge
56
 
57
        tAH       : TIME    :=  0.8 ns;
58
        tAS       : TIME    :=  1.5 ns;
59
        tCH       : TIME    :=  2.5 ns;
60
        tCL       : TIME    :=  2.5 ns;
61
        tCK       : TIME    :=  7.5 ns;
62
        tDH       : TIME    :=  0.8 ns;
63
        tDS       : TIME    :=  1.5 ns;
64
        tCKH      : TIME    :=  0.8 ns;
65
        tCKS      : TIME    :=  1.5 ns;
66
        tCMH      : TIME    :=  0.8 ns;
67
        tCMS      : TIME    :=  1.5 ns;
68
 
69
        addr_bits : INTEGER := 12;
70
        data_bits : INTEGER := 32;
71
        col_bits  : INTEGER :=  8
72
    );
73
    PORT (
74
        Dq    : INOUT STD_LOGIC_VECTOR (data_bits - 1 DOWNTO 0) := (OTHERS => 'Z');
75
        Addr  : IN    STD_LOGIC_VECTOR (addr_bits - 1 DOWNTO 0) := (OTHERS => '0');
76
        Ba    : IN    STD_LOGIC_VECTOR (1 DOWNTO 0) := "00";
77
        Clk   : IN    STD_LOGIC := '0';
78
        Cke   : IN    STD_LOGIC := '1';
79
        Cs_n  : IN    STD_LOGIC := '1';
80
        Ras_n : IN    STD_LOGIC := '1';
81
        Cas_n : IN    STD_LOGIC := '1';
82
        We_n  : IN    STD_LOGIC := '1';
83
        Dqm   : IN    STD_LOGIC_VECTOR (3 DOWNTO 0) := "0000"
84
    );
85
END mt48lc4m32b2;
86
 
87
ARCHITECTURE behave OF mt48lc4m32b2 IS
88
    TYPE   State       IS (BST, NOP, PRECH, READ, WRITE);
89
    TYPE   Array4xI    IS ARRAY (3 DOWNTO 0) OF INTEGER;
90
    TYPE   Array4xT    IS ARRAY (3 DOWNTO 0) OF TIME;
91
    TYPE   Array4xB    IS ARRAY (3 DOWNTO 0) OF STD_LOGIC;
92
    TYPE   Array4x2BV  IS ARRAY (3 DOWNTO 0) OF STD_LOGIC_VECTOR (1 DOWNTO 0);
93
    TYPE   Array4xCBV  IS ARRAY (4 DOWNTO 0) OF STD_LOGIC_VECTOR (Col_bits - 1 DOWNTO 0);
94
    TYPE   Array_state IS ARRAY (4 DOWNTO 0) OF State;
95
    SIGNAL Mode_reg : STD_LOGIC_VECTOR (addr_bits - 1 DOWNTO 0) := (OTHERS => '0');
96
    SIGNAL Active_enable, Aref_enable, Burst_term : STD_LOGIC := '0';
97
    SIGNAL Mode_reg_enable, Prech_enable, Read_enable, Write_enable : STD_LOGIC := '0';
98
    SIGNAL Burst_length_1, Burst_length_2, Burst_length_4, Burst_length_8 : STD_LOGIC := '0';
99
    SIGNAL Cas_latency_1, Cas_latency_2, Cas_latency_3 : STD_LOGIC := '0';
100
    SIGNAL Cs_in, Ras_in, Cas_in, We_in : STD_LOGIC := '0';
101
    SIGNAL Write_burst_mode : STD_LOGIC := '0';
102
    SIGNAL Sys_clk, CkeZ : STD_LOGIC := '0';
103
 
104
BEGIN
105
    -- Strip the strength
106
    Cs_in  <= To_X01 (Cs_n);
107
    Ras_in <= To_X01 (Ras_n);
108
    Cas_in <= To_X01 (Cas_n);
109
    We_in  <= To_X01 (We_n);
110
 
111
    -- Commands Decode
112
    Active_enable   <= NOT(Cs_in) AND NOT(Ras_in) AND     Cas_in  AND     We_in;
113
    Aref_enable     <= NOT(Cs_in) AND NOT(Ras_in) AND NOT(Cas_in) AND     We_in;
114
    Burst_term      <= NOT(Cs_in) AND     Ras_in  AND     Cas_in  AND NOT(We_in);
115
    Mode_reg_enable <= NOT(Cs_in) AND NOT(Ras_in) AND NOT(Cas_in) AND NOT(We_in);
116
    Prech_enable    <= NOT(Cs_in) AND NOT(Ras_in) AND     Cas_in  AND NOT(We_in);
117
    Read_enable     <= NOT(Cs_in) AND     Ras_in  AND NOT(Cas_in) AND     We_in;
118
    Write_enable    <= NOT(Cs_in) AND     Ras_in  AND NOT(Cas_in) AND NOT(We_in);
119
 
120
    -- Burst Length Decode
121
    Burst_length_1  <= NOT(Mode_reg(2)) AND NOT(Mode_reg(1)) AND NOT(Mode_reg(0));
122
    Burst_length_2  <= NOT(Mode_reg(2)) AND NOT(Mode_reg(1)) AND     Mode_reg(0);
123
    Burst_length_4  <= NOT(Mode_reg(2)) AND     Mode_reg(1)  AND NOT(Mode_reg(0));
124
    Burst_length_8  <= NOT(Mode_reg(2)) AND     Mode_reg(1)  AND     Mode_reg(0);
125
 
126
    -- CAS Latency Decode
127
    Cas_latency_1   <= NOT(Mode_reg(6)) AND NOT(Mode_reg(5)) AND     Mode_reg(4);
128
    Cas_latency_2   <= NOT(Mode_reg(6)) AND     Mode_reg(5)  AND NOT(Mode_reg(4));
129
    Cas_latency_3   <= NOT(Mode_reg(6)) AND     Mode_reg(5)  AND     Mode_reg(4);
130
 
131
    -- Write Burst Mode
132
    Write_burst_mode <= Mode_reg(9);
133
 
134
    -- System Clock
135
    int_clk : PROCESS (Clk)
136
    BEGIN
137
        IF Clk'LAST_VALUE = '0' AND Clk = '1' THEN
138
            CkeZ <= Cke;
139
        END IF;
140
        Sys_clk <= CkeZ AND Clk;
141
    END PROCESS;
142
 
143
    state_register : PROCESS
144
        TYPE ram_type IS ARRAY (2**col_bits - 1 DOWNTO 0) OF STD_LOGIC_VECTOR (data_bits - 1 DOWNTO 0);
145
        TYPE ram_pntr IS ACCESS ram_type;
146
        TYPE ram_stor IS ARRAY (2**addr_bits - 1 DOWNTO 0) OF ram_pntr;
147
        VARIABLE Bank0 : ram_stor;
148
        VARIABLE Bank1 : ram_stor;
149
        VARIABLE Bank2 : ram_stor;
150
        VARIABLE Bank3 : ram_stor;
151
        VARIABLE Row_index, Col_index : INTEGER := 0;
152
        VARIABLE Dq_temp : STD_LOGIC_VECTOR (data_bits - 1 DOWNTO 0) := (OTHERS => '0');
153
 
154
        VARIABLE Col_addr : Array4xCBV;
155
        VARIABLE Bank_addr : Array4x2BV;
156
        VARIABLE Dqm_reg0, Dqm_reg1 : STD_LOGIC_VECTOR (3 DOWNTO 0) := "0000";
157
 
158
        VARIABLE Bank, Prev_bank : STD_LOGIC_VECTOR (1 DOWNTO 0) := "00";
159
        VARIABLE B0_row_addr, B1_row_addr, B2_row_addr, B3_row_addr : STD_LOGIC_VECTOR (addr_bits - 1 DOWNTO 0) := (OTHERS => '0');
160
        VARIABLE Col_brst : STD_LOGIC_VECTOR (col_bits - 1 DOWNTO 0) := (OTHERS => '0');
161
        VARIABLE Row : STD_LOGIC_VECTOR (addr_bits - 1 DOWNTO 0) := (OTHERS => '0');
162
        VARIABLE Col : STD_LOGIC_VECTOR (col_bits - 1 DOWNTO 0) := (OTHERS => '0');
163
        VARIABLE Burst_counter : INTEGER := 0;
164
 
165
        VARIABLE Command : Array_state;
166
        VARIABLE Bank_precharge : Array4x2BV;
167
        VARIABLE A10_precharge : Array4xB := ('0' & '0' & '0' & '0');
168
        VARIABLE Auto_precharge : Array4xB := ('0' & '0' & '0' & '0');
169
        VARIABLE Read_precharge : Array4xB := ('0' & '0' & '0' & '0');
170
        VARIABLE Write_precharge : Array4xB := ('0' & '0' & '0' & '0');
171
        VARIABLE RW_interrupt_read : Array4xB := ('0' & '0' & '0' & '0');
172
        VARIABLE RW_interrupt_write : Array4xB := ('0' & '0' & '0' & '0');
173
        VARIABLE RW_interrupt_bank : STD_LOGIC_VECTOR (1 DOWNTO 0) := "00";
174
        VARIABLE RW_interrupt_counter : Array4xI := (0 & 0 & 0 & 0);
175
        VARIABLE Count_precharge : Array4xI := (0 & 0 & 0 & 0);
176
 
177
        VARIABLE Data_in_enable, Data_out_enable : STD_LOGIC := '0';
178
        VARIABLE Pc_b0, Pc_b1, Pc_b2, Pc_b3 : STD_LOGIC := '0';
179
        VARIABLE Act_b0, Act_b1, Act_b2, Act_b3 : STD_LOGIC := '1';
180
 
181
        -- Timing Check
182
        VARIABLE MRD_chk : INTEGER := 0;
183
        VARIABLE RFC_chk : TIME := 0 ns;
184
        VARIABLE RRD_chk : TIME := 0 ns;
185
        VARIABLE WR_chkm : Array4xT := (0 ns & 0 ns & 0 ns & 0 ns);
186
        VARIABLE RAS_chk0, RAS_chk1, RAS_chk2, RAS_chk3 : TIME := 0 ns;
187
        VARIABLE RC_chk0, RC_chk1, RC_chk2, RC_chk3 : TIME := 0 ns;
188
        VARIABLE RCD_chk0, RCD_chk1, RCD_chk2, RCD_chk3 : TIME := 0 ns;
189
        VARIABLE RP_chk0, RP_chk1, RP_chk2, RP_chk3 : TIME := 0 ns;
190
 
191
        -- Initialize empty rows
192
        PROCEDURE Init_mem (Bank : STD_LOGIC_VECTOR (1 DOWNTO 0); Row_index : INTEGER) IS
193
            VARIABLE i, j : INTEGER := 0;
194
        BEGIN
195
            IF Bank = "00" THEN
196
                IF Bank0 (Row_index) = NULL THEN                        -- Check to see if row empty
197
                    Bank0 (Row_index) := NEW ram_type;                  -- Open new row for access
198
                    FOR i IN (2**col_bits - 1) DOWNTO 0 LOOP            -- Filled row with zeros
199
                        FOR j IN (data_bits - 1) DOWNTO 0 LOOP
200
                            Bank0 (Row_index) (i) (j) := '0';
201
                        END LOOP;
202
                    END LOOP;
203
                END IF;
204
            ELSIF Bank = "01" THEN
205
                IF Bank1 (Row_index) = NULL THEN
206
                    Bank1 (Row_index) := NEW ram_type;
207
                    FOR i IN (2**col_bits - 1) DOWNTO 0 LOOP
208
                        FOR j IN (data_bits - 1) DOWNTO 0 LOOP
209
                            Bank1 (Row_index) (i) (j) := '0';
210
                        END LOOP;
211
                    END LOOP;
212
                END IF;
213
            ELSIF Bank = "10" THEN
214
                IF Bank2 (Row_index) = NULL THEN
215
                    Bank2 (Row_index) := NEW ram_type;
216
                    FOR i IN (2**col_bits - 1) DOWNTO 0 LOOP
217
                        FOR j IN (data_bits - 1) DOWNTO 0 LOOP
218
                            Bank2 (Row_index) (i) (j) := '0';
219
                        END LOOP;
220
                    END LOOP;
221
                END IF;
222
            ELSIF Bank = "11" THEN
223
                IF Bank3 (Row_index) = NULL THEN
224
                    Bank3 (Row_index) := NEW ram_type;
225
                    FOR i IN (2**col_bits - 1) DOWNTO 0 LOOP
226
                        FOR j IN (data_bits - 1) DOWNTO 0 LOOP
227
                            Bank3 (Row_index) (i) (j) := '0';
228
                        END LOOP;
229
                    END LOOP;
230
                END IF;
231
            END IF;
232
        END;
233
 
234
        -- Burst Counter
235
        PROCEDURE Burst_decode IS
236
            VARIABLE Col_int : INTEGER := 0;
237
            VARIABLE Col_vec, Col_temp : STD_LOGIC_VECTOR (col_bits - 1 DOWNTO 0) := (OTHERS => '0');
238
        BEGIN
239
            -- Advance Burst Counter
240
            Burst_counter := Burst_counter + 1;
241
 
242
            -- Burst Type
243
            IF Mode_reg (3) = '0' THEN
244
                Col_int := conv_integer(Col) + 1;
245
                Col_temp := CONV_STD_LOGIC_VECTOR(Col_int, col_bits);
246
            ELSIF Mode_reg (3) = '1' THEN
247
                Col_vec := CONV_STD_LOGIC_VECTOR(Burst_counter, col_bits);
248
                Col_temp (2) := Col_vec (2) XOR Col_brst (2);
249
                Col_temp (1) := Col_vec (1) XOR Col_brst (1);
250
                Col_temp (0) := Col_vec (0) XOR Col_brst (0);
251
            END IF;
252
 
253
            -- Burst Length
254
            IF Burst_length_2 = '1' THEN
255
                Col (0) := Col_temp (0);
256
            ELSIF Burst_length_4 = '1' THEN
257
                Col (1 DOWNTO 0) := Col_temp (1 DOWNTO 0);
258
            ELSIF Burst_length_8 = '1' THEN
259
                Col (2 DOWNTO 0) := Col_temp (2 DOWNTO 0);
260
            ELSE
261
                Col := Col_temp;
262
            END IF;
263
 
264
            -- Burst Read Single Write
265
            IF Write_burst_mode = '1' AND Data_in_enable = '1' THEN
266
                Data_in_enable := '0';
267
            END IF;
268
 
269
            -- Data counter
270
            IF Burst_length_1 = '1' THEN
271
                IF Burst_counter >= 1 THEN
272
                    IF Data_in_enable = '1' THEN
273
                        Data_in_enable := '0';
274
                    ELSIF Data_out_enable = '1' THEN
275
                        Data_out_enable := '0';
276
                    END IF;
277
                END IF;
278
            ELSIF Burst_length_2 = '1' THEN
279
                IF Burst_counter >= 2 THEN
280
                    IF Data_in_enable = '1' THEN
281
                        Data_in_enable := '0';
282
                    ELSIF Data_out_enable = '1' THEN
283
                        Data_out_enable := '0';
284
                    END IF;
285
                END IF;
286
            ELSIF Burst_length_4 = '1' THEN
287
                IF Burst_counter >= 4 THEN
288
                    IF Data_in_enable = '1' THEN
289
                        Data_in_enable := '0';
290
                    ELSIF Data_out_enable = '1' THEN
291
                        Data_out_enable := '0';
292
                    END IF;
293
                END IF;
294
            ELSIF Burst_length_8 = '1' THEN
295
                IF Burst_counter >= 8 THEN
296
                    IF Data_in_enable = '1' THEN
297
                        Data_in_enable := '0';
298
                    ELSIF Data_out_enable = '1' THEN
299
                        Data_out_enable := '0';
300
                    END IF;
301
                END IF;
302
            END IF;
303
        END;
304
 
305
    BEGIN
306
        WAIT ON Sys_clk;
307
        IF Sys_clk'event AND Sys_clk = '1' THEN
308
            -- Internal Pipeline
309
            Command(0) := Command(1);
310
            Command(1) := Command(2);
311
            Command(2) := Command(3);
312
            Command(3) := NOP;
313
 
314
            Col_addr(0) := Col_addr(1);
315
            Col_addr(1) := Col_addr(2);
316
            Col_addr(2) := Col_addr(3);
317
            Col_addr(3) := (OTHERS => '0');
318
 
319
            Bank_addr(0) := Bank_addr(1);
320
            Bank_addr(1) := Bank_addr(2);
321
            Bank_addr(2) := Bank_addr(3);
322
            Bank_addr(3) := "00";
323
 
324
            Bank_precharge(0) := Bank_precharge(1);
325
            Bank_precharge(1) := Bank_precharge(2);
326
            Bank_precharge(2) := Bank_precharge(3);
327
            Bank_precharge(3) := "00";
328
 
329
            A10_precharge(0) := A10_precharge(1);
330
            A10_precharge(1) := A10_precharge(2);
331
            A10_precharge(2) := A10_precharge(3);
332
            A10_precharge(3) := '0';
333
 
334
            -- Dqm pipeline for Read
335
            Dqm_reg0 := Dqm_reg1;
336
            Dqm_reg1 := Dqm;
337
 
338
            -- Read or Write with Auto Precharge Counter
339
            IF Auto_precharge (0) = '1' THEN
340
                Count_precharge (0) := Count_precharge (0) + 1;
341
            END IF;
342
            IF Auto_precharge (1) = '1' THEN
343
                Count_precharge (1) := Count_precharge (1) + 1;
344
            END IF;
345
            IF Auto_precharge (2) = '1' THEN
346
                Count_precharge (2) := Count_precharge (2) + 1;
347
            END IF;
348
            IF Auto_precharge (3) = '1' THEN
349
                Count_precharge (3) := Count_precharge (3) + 1;
350
            END IF;
351
 
352
            -- Read or Write Interrupt Counter
353
            IF RW_interrupt_write (0) = '1' THEN
354
               RW_interrupt_counter  (0) := RW_interrupt_counter (0) + 1;
355
            END IF;
356
            IF RW_interrupt_write (1) = '1' THEN
357
                RW_interrupt_counter (1) := RW_interrupt_counter (1) + 1;
358
            END IF;
359
            IF RW_interrupt_write (2) = '1' THEN
360
                RW_interrupt_counter (2) := RW_interrupt_counter (2) + 1;
361
            END IF;
362
            IF RW_interrupt_write (3) = '1' THEN
363
                RW_interrupt_counter (3) := RW_interrupt_counter (3) + 1;
364
            END IF;
365
 
366
            -- tMRD Counter
367
            MRD_chk := MRD_chk + 1;
368
 
369
            -- Auto Refresh
370
            IF Aref_enable = '1' THEN
371
                -- Auto Refresh to Auto Refresh
372
                ASSERT (NOW - RFC_chk >= tRFC)
373
                    REPORT "tRFC violation during Auto Refresh"
374
                    SEVERITY WARNING;
375
 
376
                -- Precharge to Auto Refresh
377
                ASSERT ((NOW - RP_chk0 >= tRP) OR (NOW - RP_chk1 >= tRP) OR
378
                        (NOW - RP_chk2 >= tRP) OR (NOW - RP_chk3 >= tRP))
379
                    REPORT "tRP violation during Auto Refresh"
380
                    SEVERITY WARNING;
381
 
382
                -- Precharge to Auto Refresh
383
                ASSERT (Pc_b0 ='1' AND Pc_b1 = '1' AND Pc_b2 ='1' AND Pc_b3 = '1')
384
                    REPORT "All banks must be Precharge before Auto Refresh"
385
                    SEVERITY WARNING;
386
 
387
                -- Load Mode Register to Auto Refresh
388
                ASSERT (MRD_chk >= tMRD)
389
                    REPORT "tMRD violation during Auto Refresh"
390
                    SEVERITY WARNING;
391
 
392
                -- Record current tRFC time
393
                RFC_chk := NOW;
394
            END IF;
395
 
396
            -- Load Mode Register
397
            IF Mode_reg_enable = '1' THEN
398
                -- Register Mode
399
                Mode_reg <= Addr;
400
 
401
                -- Precharge to Load Mode Register
402
                ASSERT (Pc_b0 ='1' AND Pc_b1 = '1' AND Pc_b2 ='1' AND Pc_b3 = '1')
403
                    REPORT "All banks must be Precharge before Load Mode Register"
404
                    SEVERITY WARNING;
405
 
406
                -- Precharge to Load Mode Register
407
                ASSERT ((NOW - RP_chk0 >= tRP) OR (NOW - RP_chk1 >= tRP) OR
408
                        (NOW - RP_chk2 >= tRP) OR (NOW - RP_chk3 >= tRP))
409
                    REPORT "tRP violation during Load Mode Register"
410
                    SEVERITY WARNING;
411
 
412
                -- Auto Refresh to Load Mode Register
413
                ASSERT (NOW - RFC_chk >= tRFC)
414
                    REPORT "tRFC violation during Load Mode Register"
415
                    SEVERITY WARNING;
416
 
417
                -- Load Mode Register to Load Mode Register
418
                ASSERT (MRD_chk >= tMRD)
419
                    REPORT "tMRD violation during Load Mode Register"
420
                    SEVERITY WARNING;
421
 
422
                -- Record current tMRD time
423
                MRD_chk := 0;
424
            END IF;
425
 
426
            -- Active Block (Latch Bank and Row Address)
427
            IF Active_enable = '1' THEN
428
                -- Activate an OPEN bank can corrupt data
429
                ASSERT ((Ba = "00" AND Act_b0 = '0') OR (Ba = "01" AND Act_b1 = '0') OR
430
                        (Ba = "10" AND Act_b2 = '0') OR (Ba = "11" AND Act_b3 = '0'))
431
                    REPORT "Bank is already activated - data can be corrupted"
432
                    SEVERITY WARNING;
433
 
434
                -- Activate Bank 0
435
                IF Ba = "00" AND Pc_b0 = '1' THEN
436
                    -- Activate to Activate (same bank)
437
                    ASSERT (NOW - RC_chk0 >= tRC)
438
                        REPORT "tRC violation during Activate Bank 0"
439
                        SEVERITY WARNING;
440
 
441
                    -- Precharge to Activate
442
                    ASSERT (NOW - RP_chk0 >= tRP)
443
                        REPORT "tRP violation during Activate Bank 0"
444
                        SEVERITY WARNING;
445
 
446
                    -- Record variables for checking violation
447
                    Act_b0 := '1';
448
                    Pc_b0 := '0';
449
                    B0_row_addr := Addr;
450
                    RAS_chk0 := NOW;
451
                    RC_chk0 := NOW;
452
                    RCD_chk0 := NOW;
453
                END IF;
454
 
455
                -- Activate Bank 1
456
                IF Ba = "01" AND Pc_b1 = '1' THEN
457
                    -- Activate to Activate (same bank)
458
                    ASSERT (NOW - RC_chk1 >= tRC)
459
                        REPORT "tRC violation during Activate Bank 1"
460
                        SEVERITY WARNING;
461
 
462
                    -- Precharge to Activate
463
                    ASSERT (NOW - RP_chk1 >= tRP)
464
                        REPORT "tRP violation during Activate Bank 1"
465
                        SEVERITY WARNING;
466
 
467
                    -- Record variables for checking violation
468
                    Act_b1 := '1';
469
                    Pc_b1 := '0';
470
                    B1_row_addr := Addr;
471
                    RAS_chk1 := NOW;
472
                    RC_chk1 := NOW;
473
                    RCD_chk1 := NOW;
474
                END IF;
475
 
476
                -- Activate Bank 2
477
                IF Ba = "10" AND Pc_b2 = '1' THEN
478
                    -- Activate to Activate (same bank)
479
                    ASSERT (NOW - RC_chk2 >= tRC)
480
                        REPORT "tRC violation during Activate Bank 2"
481
                        SEVERITY WARNING;
482
 
483
                    -- Precharge to Activate
484
                    ASSERT (NOW - RP_chk2 >= tRP)
485
                        REPORT "tRP violation during Activate Bank 2"
486
                        SEVERITY WARNING;
487
 
488
                    -- Record variables for checking violation
489
                    Act_b2 := '1';
490
                    Pc_b2 := '0';
491
                    B2_row_addr := Addr;
492
                    RAS_chk2 := NOW;
493
                    RC_chk2 := NOW;
494
                    RCD_chk2 := NOW;
495
                END IF;
496
 
497
                -- Activate Bank 3
498
                IF Ba = "11" AND Pc_b3 = '1' THEN
499
                    -- Activate to Activate (same bank)
500
                    ASSERT (NOW - RC_chk3 >= tRC)
501
                        REPORT "tRC violation during Activate Bank 3"
502
                        SEVERITY WARNING;
503
 
504
                    -- Precharge to Activate
505
                    ASSERT (NOW - RP_chk3 >= tRP)
506
                        REPORT "tRP violation during Activate Bank 3"
507
                        SEVERITY WARNING;
508
 
509
                    -- Record variables for checking violation
510
                    Act_b3 := '1';
511
                    Pc_b3 := '0';
512
                    B3_row_addr := Addr;
513
                    RAS_chk3 := NOW;
514
                    RC_chk3 := NOW;
515
                    RCD_chk3 := NOW;
516
                END IF;
517
 
518
                -- Activate to Activate (different bank)
519
                IF (Prev_bank /= Ba) THEN
520
                    ASSERT (NOW - RRD_chk >= tRRD)
521
                        REPORT "tRRD violation during Activate"
522
                        SEVERITY WARNING;
523
                END IF;
524
 
525
                -- Auto Refresh to Activate
526
                ASSERT (NOW - RFC_chk >= tRFC)
527
                    REPORT "tRFC violation during Activate"
528
                    SEVERITY WARNING;
529
 
530
                -- Load Mode Register to Activate
531
                ASSERT (MRD_chk >= tMRD)
532
                    REPORT "tMRD violation during Activate"
533
                    SEVERITY WARNING;
534
 
535
                -- Record variable for checking violation
536
                RRD_chk := NOW;
537
                Prev_Bank := Ba;
538
            END IF;
539
 
540
            -- Precharge Block
541
            IF Prech_enable = '1' THEN
542
                -- Load Mode Register to Precharge
543
                ASSERT (MRD_chk >= tMRD)
544
                    REPORT "tMRD violation during Precharge"
545
                    SEVERITY WARNING;
546
 
547
                -- Precharge Bank 0
548
                IF ((Addr (10) = '1' OR (Addr (10) = '0' AND Ba = "00")) AND Act_b0 = '1') THEN
549
                    Act_b0 := '0';
550
                    Pc_b0 := '1';
551
                    RP_chk0 := NOW;
552
 
553
                    -- Activate to Precharge
554
                    ASSERT (NOW - RAS_chk0 >= tRAS)
555
                        REPORT "tRAS violation during Precharge"
556
                        SEVERITY WARNING;
557
 
558
                    -- tWR violation check for Write
559
                    ASSERT (NOW - WR_chkm(0) >= tWRm)
560
                        REPORT "tWR violation during Precharge"
561
                        SEVERITY WARNING;
562
                END IF;
563
 
564
                -- Precharge Bank 1
565
                IF ((Addr (10) = '1' OR (Addr (10) = '0' AND Ba = "01")) AND Act_b1 = '1') THEN
566
                    Act_b1 := '0';
567
                    Pc_b1 := '1';
568
                    RP_chk1 := NOW;
569
 
570
                    -- Activate to Precharge
571
                    ASSERT (NOW - RAS_chk1 >= tRAS)
572
                        REPORT "tRAS violation during Precharge"
573
                        SEVERITY WARNING;
574
 
575
                    -- tWR violation check for Write
576
                    ASSERT (NOW - WR_chkm(1) >= tWRm)
577
                        REPORT "tWR violation during Precharge"
578
                        SEVERITY WARNING;
579
                END IF;
580
 
581
                -- Precharge Bank 2
582
                IF ((Addr (10) = '1' OR (Addr (10) = '0' AND Ba = "10")) AND Act_b2 = '1') THEN
583
                    Act_b2 := '0';
584
                    Pc_b2 := '1';
585
                    RP_chk2 := NOW;
586
 
587
                    -- Activate to Precharge
588
                    ASSERT (NOW - RAS_chk2 >= tRAS)
589
                        REPORT "tRAS violation during Precharge"
590
                        SEVERITY WARNING;
591
 
592
                    -- tWR violation check for Write
593
                    ASSERT (NOW - WR_chkm(2) >= tWRm)
594
                        REPORT "tWR violation during Precharge"
595
                        SEVERITY WARNING;
596
                END IF;
597
 
598
                -- Precharge Bank 3
599
                IF ((Addr (10) = '1' OR (Addr (10) = '0' AND Ba = "11")) AND Act_b3 = '1') THEN
600
                    Act_b3 := '0';
601
                    Pc_b3 := '1';
602
                    RP_chk3 := NOW;
603
 
604
                    -- Activate to Precharge
605
                    ASSERT (NOW - RAS_chk3 >= tRAS)
606
                        REPORT "tRAS violation during Precharge"
607
                        SEVERITY WARNING;
608
 
609
                    -- tWR violation check for Write
610
                    ASSERT (NOW - WR_chkm(3) >= tWRm)
611
                        REPORT "tWR violation during Precharge"
612
                        SEVERITY WARNING;
613
                END IF;
614
 
615
                -- Terminate a Write Immediately (if same bank or all banks)
616
                IF (Data_in_enable = '1' AND (Bank = Ba OR Addr(10) = '1')) THEN
617
                    Data_in_enable := '0';
618
                END IF;
619
 
620
                -- Precharge Command Pipeline for READ
621
                IF CAS_latency_3 = '1' THEN
622
                    Command(2) := PRECH;
623
                    Bank_precharge(2) := Ba;
624
                    A10_precharge(2) := Addr(10);
625
                ELSIF CAS_latency_2 = '1' THEN
626
                    Command(1) := PRECH;
627
                    Bank_precharge(1) := Ba;
628
                    A10_precharge(1) := Addr(10);
629
                END IF;
630
            END IF;
631
 
632
            -- Burst Terminate
633
            IF Burst_term = '1' THEN
634
                -- Terminate a Write immediately
635
                IF Data_in_enable = '1' THEN
636
                    Data_in_enable := '0';
637
                END IF;
638
 
639
                -- Terminate a Read depend on CAS Latency
640
                IF CAS_latency_3 = '1' THEN
641
                    Command(2) := BST;
642
                ELSIF CAS_latency_2 = '1' THEN
643
                    Command(1) := BST;
644
                END IF;
645
            END IF;
646
 
647
            -- Read Command
648
            IF Read_enable = '1' THEN
649
                -- Activate to Read
650
                ASSERT ((Ba="00" AND Act_b0='1') OR (Ba="01" AND Act_b1='1') OR
651
                        (Ba="10" AND Act_b2='1') OR (Ba="11" AND Act_b3='1'))
652
                    REPORT "Bank is not Activated for Read"
653
                    SEVERITY WARNING;
654
 
655
                -- Activate to Read
656
                ASSERT ((Ba = "00" AND NOW - RCD_chk0 >= tRCD) OR
657
                        (Ba = "01" AND NOW - RCD_chk1 >= tRCD) OR
658
                        (Ba = "10" AND NOW - RCD_chk2 >= tRCD) OR
659
                        (Ba = "11" AND NOW - RCD_chk3 >= tRCD))
660
                    REPORT "tRCD violation during Read"
661
                    SEVERITY WARNING;
662
 
663
                -- CAS Latency Pipeline
664
                IF Cas_latency_3 = '1' THEN
665
                    Command(2) := READ;
666
                    Col_addr (2) := Addr(col_bits - 1 DOWNTO 0);
667
                    Bank_addr (2) := Ba;
668
                ELSIF Cas_latency_2 = '1' THEN
669
                    Command(1) := READ;
670
                    Col_addr (1) := Addr(col_bits - 1 DOWNTO 0);
671
                    Bank_addr (1) := Ba;
672
                ELSIF Cas_latency_1 = '1' THEN
673
                    Command(0) := READ;
674
                    Col_addr (0) := Addr(col_bits - 1 DOWNTO 0);
675
                    Bank_addr (0) := Ba;
676
                END IF;
677
 
678
                -- Read Terminate Write Immediately
679
                IF Data_in_enable = '1' THEN
680
                    Data_in_enable := '0';
681
                    -- Interrupt a Write with Auto Precharge
682
                    IF Auto_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' AND Write_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' THEN
683
                        RW_interrupt_write(CONV_INTEGER(RW_Interrupt_Bank)) := '1';
684
                        RW_interrupt_counter (CONV_INTEGER(RW_Interrupt_Bank)) := 0;
685
                        ASSERT FALSE REPORT "Read interrupt a Write with Auto Precharge." SEVERITY NOTE;
686
                    END IF;
687
                END IF;
688
 
689
                -- Read Terminate Read after CL - 1
690
                IF (Data_out_enable = '1' AND ((Cas_latency_2 = '1' AND ((Burst_length_2 = '1' AND Burst_counter < 1) OR
691
                                                                         (Burst_length_4 = '1' AND Burst_counter < 3) OR
692
                                                                         (Burst_length_8 = '1' AND Burst_counter < 7))) OR
693
                                               (Cas_latency_3 = '1' AND ((Burst_length_4 = '1' AND Burst_counter < 2) OR
694
                                                                         (Burst_length_8 = '1' AND Burst_counter < 6))))) THEN
695
                    -- Interrupt a Read with Auto Precharge
696
                    IF Auto_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' AND Read_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' THEN
697
                        RW_interrupt_read(CONV_INTEGER(RW_Interrupt_Bank)) := '1';
698
                        ASSERT FALSE REPORT "Read interrupt a Read with Auto Precharge." SEVERITY NOTE;
699
                    END IF;
700
                END IF;
701
 
702
                -- Auto Precharge
703
                IF Addr(10) = '1' THEN
704
                    Auto_precharge (CONV_INTEGER(Ba)) := '1';
705
                    Count_precharge (CONV_INTEGER(Ba)) := 0;
706
                    RW_Interrupt_Bank := Ba;
707
                    Read_precharge (CONV_INTEGER(Ba)) := '1';
708
                END IF;
709
            END IF;
710
 
711
            -- Write Command
712
            IF Write_enable = '1' THEN
713
                -- Activate to Write
714
                ASSERT ((Ba="00" AND Act_b0='1') OR (Ba="01" AND Act_b1='1') OR
715
                        (Ba="10" AND Act_b2='1') OR (Ba="11" AND Act_b3='1'))
716
                    REPORT "Bank is not Activated for Write"
717
                    SEVERITY WARNING;
718
 
719
                -- Activate to Write
720
                ASSERT ((Ba = "00" AND NOW - RCD_chk0 >= tRCD) OR
721
                        (Ba = "01" AND NOW - RCD_chk1 >= tRCD) OR
722
                        (Ba = "10" AND NOW - RCD_chk2 >= tRCD) OR
723
                        (Ba = "11" AND NOW - RCD_chk3 >= tRCD))
724
                    REPORT "tRCD violation during Write"
725
                    SEVERITY WARNING;
726
 
727
                -- Latch write command, bank, column
728
                Command(0) := WRITE;
729
                Col_addr (0) := Addr(col_bits - 1 DOWNTO 0);
730
                Bank_addr (0) := Ba;
731
 
732
                -- Write Terminate Write Immediately
733
                IF Data_in_enable = '1' THEN
734
                    Data_in_enable := '0';
735
 
736
                    -- Interrupt a Write with Auto Precharge
737
                    IF Auto_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' AND Write_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' THEN
738
                        RW_interrupt_write(CONV_INTEGER(RW_Interrupt_Bank)) := '1';
739
                        RW_interrupt_counter (CONV_INTEGER(RW_Interrupt_Bank)) := 0;
740
                        ASSERT FALSE REPORT "Write interrupt a Write with Auto Precharge." SEVERITY NOTE;
741
                    END IF;
742
                END IF;
743
 
744
                -- Write Terminate Read Immediately
745
                IF Data_out_enable = '1' THEN
746
                    Data_out_enable := '0';
747
 
748
                    -- Interrupt a Read with Auto Precharge
749
                    IF Auto_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' AND Read_precharge(CONV_INTEGER(RW_Interrupt_Bank)) = '1' THEN
750
                        RW_interrupt_read(CONV_INTEGER(RW_Interrupt_Bank)) := '1';
751
                        ASSERT FALSE REPORT "Write interrupt a Read with Auto Precharge." SEVERITY NOTE;
752
                    END IF;
753
                END IF;
754
 
755
                -- Auto Precharge
756
                IF Addr(10) = '1' THEN
757
                    Auto_precharge (CONV_INTEGER(Ba)) := '1';
758
                    Count_precharge (CONV_INTEGER(Ba)) := 0;
759
                    RW_Interrupt_Bank := Ba;
760
                    Write_precharge (CONV_INTEGER(Ba)) := '1';
761
                END IF;
762
            END IF;
763
 
764
            -- Write with AutoPrecharge Calculation
765
            --      The device start internal precharge when:
766
            --          1.  Meet tRAS requirement
767
            --      and 2.  tWR cycle(s) after last valid data
768
            --       or 3.  Interrupt by a Read or Write (with or without Auto Precharge)
769
            --
770
            -- Note: Model is starting the internal precharge 1 cycle after they meet all the 
771
            --       requirement but tRP will be compensate for the time after the 1 cycle.
772
            IF ((Auto_precharge(0) = '1') AND (Write_precharge(0) = '1')) THEN
773
                IF (((NOW - RAS_chk0 >= tRAS) AND
774
                   (((Burst_length_1 = '1' OR Write_burst_mode = '1' ) AND Count_precharge(0) >= 1)  OR
775
                     (Burst_length_2 = '1'                             AND Count_precharge(0) >= 2)  OR
776
                     (Burst_length_4 = '1'                             AND Count_precharge(0) >= 4)  OR
777
                     (Burst_length_8 = '1'                             AND Count_precharge(0) >= 8))) OR
778
                     (RW_interrupt_write(0) = '1' AND RW_interrupt_counter(0) >= 1)) THEN
779
                    Auto_precharge(0) := '0';
780
                    Write_precharge(0) := '0';
781
                    RW_interrupt_write(0) := '0';
782
                    Pc_b0 := '1';
783
                    Act_b0 := '0';
784
                    RP_chk0 := NOW + tWRa;
785
                END IF;
786
            END IF;
787
            IF ((Auto_precharge(1) = '1') AND (Write_precharge(1) = '1')) THEN
788
                IF (((NOW - RAS_chk1 >= tRAS) AND
789
                   (((Burst_length_1 = '1' OR Write_burst_mode = '1' ) AND Count_precharge(1) >= 1)  OR
790
                     (Burst_length_2 = '1'                             AND Count_precharge(1) >= 2)  OR
791
                     (Burst_length_4 = '1'                             AND Count_precharge(1) >= 4)  OR
792
                     (Burst_length_8 = '1'                             AND Count_precharge(1) >= 8))) OR
793
                     (RW_interrupt_write(1) = '1' AND RW_interrupt_counter(1) >= 1)) THEN
794
                    Auto_precharge(1) := '0';
795
                    Write_precharge(1) := '0';
796
                    RW_interrupt_write(1) := '0';
797
                    Pc_b1 := '1';
798
                    Act_b1 := '0';
799
                    RP_chk1 := NOW + tWRa;
800
                END IF;
801
            END IF;
802
            IF ((Auto_precharge(2) = '1') AND (Write_precharge(2) = '1')) THEN
803
                IF (((NOW - RAS_chk2 >= tRAS) AND
804
                   (((Burst_length_1 = '1' OR Write_burst_mode = '1' ) AND Count_precharge(2) >= 1)  OR
805
                     (Burst_length_2 = '1'                             AND Count_precharge(2) >= 2)  OR
806
                     (Burst_length_4 = '1'                             AND Count_precharge(2) >= 4)  OR
807
                     (Burst_length_8 = '1'                             AND Count_precharge(2) >= 8))) OR
808
                     (RW_interrupt_write(2) = '1' AND RW_interrupt_counter(2) >= 1)) THEN
809
                    Auto_precharge(2) := '0';
810
                    Write_precharge(2) := '0';
811
                    RW_interrupt_write(2) := '0';
812
                    Pc_b2 := '1';
813
                    Act_b2 := '0';
814
                    RP_chk2 := NOW + tWRa;
815
                END IF;
816
            END IF;
817
            IF ((Auto_precharge(3) = '1') AND (Write_precharge(3) = '1')) THEN
818
                IF (((NOW - RAS_chk3 >= tRAS) AND
819
                   (((Burst_length_1 = '1' OR Write_burst_mode = '1' ) AND Count_precharge(3) >= 1)  OR
820
                     (Burst_length_2 = '1'                             AND Count_precharge(3) >= 2)  OR
821
                     (Burst_length_4 = '1'                             AND Count_precharge(3) >= 4)  OR
822
                     (Burst_length_8 = '1'                             AND Count_precharge(3) >= 8))) OR
823
                     (RW_interrupt_write(0) = '1' AND RW_interrupt_counter(3) >= 1)) THEN
824
                    Auto_precharge(3) := '0';
825
                    Write_precharge(3) := '0';
826
                    RW_interrupt_write(3) := '0';
827
                    Pc_b3 := '1';
828
                    Act_b3 := '0';
829
                    RP_chk3 := NOW + tWRa;
830
                END IF;
831
            END IF;
832
 
833
            -- Read with AutoPrecharge Calculation
834
            --      The device start internal precharge when:
835
            --          1.  Meet minimum tRAS requirement
836
            --      and 2.  CL - 1 cycle(s) before last valid data
837
            --       or 3.  Interrupt by a Read or Write (with or without Auto Precharge)
838
            IF ((Auto_precharge(0) = '1') AND (Read_precharge(0) = '1')) THEN
839
                IF (((NOW - RAS_chk0 >= tRAS) AND
840
                    ((Burst_length_1 = '1' AND Count_precharge(0) >= 1)  OR
841
                     (Burst_length_2 = '1' AND Count_precharge(0) >= 2)  OR
842
                     (Burst_length_4 = '1' AND Count_precharge(0) >= 4)  OR
843
                     (Burst_length_8 = '1' AND Count_precharge(0) >= 8))) OR
844
                     (RW_interrupt_read(0) = '1')) THEN
845
                    Pc_b0 := '1';
846
                    Act_b0 := '0';
847
                    RP_chk0 := NOW;
848
                    Auto_precharge(0) := '0';
849
                    Read_precharge(0) := '0';
850
                    RW_interrupt_read(0) := '0';
851
                END IF;
852
            END IF;
853
            IF ((Auto_precharge(1) = '1') AND (Read_precharge(1) = '1')) THEN
854
                IF (((NOW - RAS_chk1 >= tRAS) AND
855
                    ((Burst_length_1 = '1' AND Count_precharge(1) >= 1)  OR
856
                     (Burst_length_2 = '1' AND Count_precharge(1) >= 2)  OR
857
                     (Burst_length_4 = '1' AND Count_precharge(1) >= 4)  OR
858
                     (Burst_length_8 = '1' AND Count_precharge(1) >= 8))) OR
859
                     (RW_interrupt_read(1) = '1')) THEN
860
                    Pc_b1 := '1';
861
                    Act_b1 := '0';
862
                    RP_chk1 := NOW;
863
                    Auto_precharge(1) := '0';
864
                    Read_precharge(1) := '0';
865
                    RW_interrupt_read(1) := '0';
866
                END IF;
867
            END IF;
868
            IF ((Auto_precharge(2) = '1') AND (Read_precharge(2) = '1')) THEN
869
                IF (((NOW - RAS_chk2 >= tRAS) AND
870
                    ((Burst_length_1 = '1' AND Count_precharge(2) >= 1)  OR
871
                     (Burst_length_2 = '1' AND Count_precharge(2) >= 2)  OR
872
                     (Burst_length_4 = '1' AND Count_precharge(2) >= 4)  OR
873
                     (Burst_length_8 = '1' AND Count_precharge(2) >= 8))) OR
874
                     (RW_interrupt_read(2) = '1')) THEN
875
                    Pc_b2 := '1';
876
                    Act_b2 := '0';
877
                    RP_chk2 := NOW;
878
                    Auto_precharge(2) := '0';
879
                    Read_precharge(2) := '0';
880
                    RW_interrupt_read(2) := '0';
881
                END IF;
882
            END IF;
883
            IF ((Auto_precharge(3) = '1') AND (Read_precharge(3) = '1')) THEN
884
                IF (((NOW - RAS_chk3 >= tRAS) AND
885
                    ((Burst_length_1 = '1' AND Count_precharge(3) >= 1)  OR
886
                     (Burst_length_2 = '1' AND Count_precharge(3) >= 2)  OR
887
                     (Burst_length_4 = '1' AND Count_precharge(3) >= 4)  OR
888
                     (Burst_length_8 = '1' AND Count_precharge(3) >= 8))) OR
889
                     (RW_interrupt_read(3) = '1')) THEN
890
                    Pc_b3 := '1';
891
                    Act_b3 := '0';
892
                    RP_chk3 := NOW;
893
                    Auto_precharge(3) := '0';
894
                    Read_precharge(3) := '0';
895
                    RW_interrupt_read(3) := '0';
896
                END IF;
897
            END IF;
898
 
899
            -- Internal Precharge or Bst
900
            IF Command(0) = PRECH THEN                          -- PRECH terminate a read if same bank or all banks
901
                IF Bank_precharge(0) = Bank OR A10_precharge(0) = '1' THEN
902
                    IF Data_out_enable = '1' THEN
903
                        Data_out_enable := '0';
904
                    END IF;
905
                END IF;
906
            ELSIF Command(0) = BST THEN                         -- BST terminate a read regardless of bank
907
                IF Data_out_enable = '1' THEN
908
                    Data_out_enable := '0';
909
                END IF;
910
            END IF;
911
 
912
            IF Data_out_enable = '0' THEN
913
                Dq <= TRANSPORT (OTHERS => 'Z') AFTER tOH;
914
            END IF;
915
 
916
            -- Detect Read or Write Command
917
            IF Command(0) = READ THEN
918
                Bank := Bank_addr (0);
919
                Col := Col_addr (0);
920
                Col_brst := Col_addr (0);
921
                IF Bank_addr (0) = "00" THEN
922
                    Row := B0_row_addr;
923
                ELSIF Bank_addr (0) = "01" THEN
924
                    Row := B1_row_addr;
925
                ELSIF Bank_addr (0) = "10" THEN
926
                    Row := B2_row_addr;
927
                ELSE
928
                    Row := B3_row_addr;
929
                END IF;
930
                Burst_counter := 0;
931
                Data_in_enable := '0';
932
                Data_out_enable := '1';
933
            ELSIF Command(0) = WRITE THEN
934
                Bank := Bank_addr(0);
935
                Col := Col_addr(0);
936
                Col_brst := Col_addr(0);
937
                IF Bank_addr (0) = "00" THEN
938
                    Row := B0_row_addr;
939
                ELSIF Bank_addr (0) = "01" THEN
940
                    Row := B1_row_addr;
941
                ELSIF Bank_addr (0) = "10" THEN
942
                    Row := B2_row_addr;
943
                ELSE
944
                    Row := B3_row_addr;
945
                END IF;
946
                Burst_counter := 0;
947
                Data_in_enable := '1';
948
                Data_out_enable := '0';
949
            END IF;
950
 
951
            -- DQ (Driver / Receiver)
952
            Row_index := CONV_INTEGER (Row);
953
            Col_index := CONV_INTEGER (Col);
954
 
955
            IF Data_in_enable = '1' THEN
956
                IF Dqm /= "1111" THEN
957
                    -- Initialize Memory
958
                    Init_mem (Bank, Row_index);
959
 
960
                    -- Array Buffer
961
                    CASE Bank IS
962
                        WHEN "00"   => Dq_temp := Bank0 (Row_index) (Col_index);
963
                        WHEN "01"   => Dq_temp := Bank1 (Row_index) (Col_index);
964
                        WHEN "10"   => Dq_temp := Bank2 (Row_index) (Col_index);
965
                        WHEN OTHERS => Dq_temp := Bank3 (Row_index) (Col_index);
966
                    END CASE;
967
 
968
                    -- Dqm Operation
969
                    IF Dqm (0) = '0' THEN
970
                        Dq_temp ( 7 DOWNTO  0) := Dq ( 7 DOWNTO  0);
971
                    END IF;
972
                    IF Dqm (1) = '0' THEN
973
                        Dq_temp (15 DOWNTO  8) := Dq (15 DOWNTO  8);
974
                    END IF;
975
                    IF Dqm (2) = '0' THEN
976
                        Dq_temp (23 DOWNTO 16) := Dq (23 DOWNTO 16);
977
                    END IF;
978
                    IF Dqm (3) = '0' THEN
979
                        Dq_temp (31 DOWNTO 24) := Dq (31 DOWNTO 24);
980
                    END IF;
981
 
982
                    -- Write to Memory
983
                    CASE Bank IS
984
                        WHEN "00"   => Bank0 (Row_index) (Col_index) := Dq_temp;
985
                        WHEN "01"   => Bank1 (Row_index) (Col_index) := Dq_temp;
986
                        WHEN "10"   => Bank2 (Row_index) (Col_index) := Dq_temp;
987
                        WHEN OTHERS => Bank3 (Row_index) (Col_index) := Dq_temp;
988
                    END CASE;
989
 
990
                    -- Record tWR for manual precharge
991
                    WR_chkm(CONV_INTEGER(Bank)) := NOW;
992
                END IF;
993
 
994
                -- Advance Burst Counter
995
                Burst_decode;
996
 
997
            ELSIF Data_out_enable = '1' THEN
998
                IF Dqm_reg0 /= "1111" THEN
999
                    -- Initialize Memory
1000
                    Init_mem (Bank, Row_index);
1001
 
1002
                    -- Array Buffer
1003
                    CASE Bank IS
1004
                        WHEN "00"   => Dq_temp := Bank0 (Row_index) (Col_index);
1005
                        WHEN "01"   => Dq_temp := Bank1 (Row_index) (Col_index);
1006
                        WHEN "10"   => Dq_temp := Bank2 (Row_index) (Col_index);
1007
                        WHEN OTHERS => Dq_temp := Bank3 (Row_index) (Col_index);
1008
                    END CASE;
1009
 
1010
                    -- Dqm Operation
1011
                    IF Dqm_reg0 (0) = '1' THEN
1012
                        Dq_temp ( 7 DOWNTO  0) := (OTHERS => 'Z');
1013
                    END IF;
1014
                    IF Dqm_reg0 (1) = '1' THEN
1015
                        Dq_temp (15 DOWNTO  8) := (OTHERS => 'Z');
1016
                    END IF;
1017
                    IF Dqm_reg0 (2) = '1' THEN
1018
                        Dq_temp (23 DOWNTO 16) := (OTHERS => 'Z');
1019
                    END IF;
1020
                    IF Dqm_reg0 (3) = '1' THEN
1021
                        Dq_temp (31 DOWNTO 24) := (OTHERS => 'Z');
1022
                    END IF;
1023
 
1024
                    -- Output
1025
                    Dq <= TRANSPORT Dq_temp AFTER tAC;
1026
                ELSE
1027
                    Dq <= TRANSPORT (OTHERS => 'Z') AFTER tHZ;
1028
                END IF;
1029
 
1030
                -- Advance Burst Counter
1031
                Burst_decode;
1032
            END IF;
1033
        END IF;
1034
 
1035
    END PROCESS;
1036
 
1037
    -- Clock timing checks
1038
    Clock_check : PROCESS
1039
        VARIABLE Clk_low, Clk_high : TIME := 0 ns;
1040
    BEGIN
1041
        WAIT ON Clk;
1042
        IF (Clk = '1' AND NOW >= 10 ns) THEN
1043
            ASSERT (NOW - Clk_low >= tCL)
1044
                REPORT "tCL violation"
1045
                SEVERITY WARNING;
1046
            ASSERT (NOW - Clk_high >= tCK)
1047
                REPORT "tCK violation"
1048
                SEVERITY WARNING;
1049
            Clk_high := NOW;
1050
        ELSIF (Clk = '0' AND NOW /= 0 ns) THEN
1051
            ASSERT (NOW - Clk_high >= tCH)
1052
                REPORT "tCH violation"
1053
                SEVERITY WARNING;
1054
            Clk_low := NOW;
1055
        END IF;
1056
    END PROCESS;
1057
 
1058
    -- Setup timing checks
1059
    Setup_check : PROCESS
1060
    BEGIN
1061
        WAIT ON Clk;
1062
        IF Clk = '1' THEN
1063
            ASSERT(Cke'LAST_EVENT >= tCKS)
1064
                REPORT "CKE Setup time violation -- tCKS"
1065
                SEVERITY WARNING;
1066
            ASSERT(Cs_n'LAST_EVENT >= tCMS)
1067
                REPORT "CS# Setup time violation -- tCMS"
1068
                SEVERITY WARNING;
1069
            ASSERT(Cas_n'LAST_EVENT >= tCMS)
1070
                REPORT "CAS# Setup time violation -- tCMS"
1071
                SEVERITY WARNING;
1072
            ASSERT(Ras_n'LAST_EVENT >= tCMS)
1073
                REPORT "RAS# Setup time violation -- tCMS"
1074
                SEVERITY WARNING;
1075
            ASSERT(We_n'LAST_EVENT >= tCMS)
1076
                REPORT "WE# Setup time violation -- tCMS"
1077
                SEVERITY WARNING;
1078
            ASSERT(Dqm'LAST_EVENT >= tCMS)
1079
                REPORT "Dqm Setup time violation -- tCMS"
1080
                SEVERITY WARNING;
1081
            ASSERT(Addr'LAST_EVENT >= tAS)
1082
                REPORT "ADDR Setup time violation -- tAS"
1083
                SEVERITY WARNING;
1084
            ASSERT(Ba'LAST_EVENT >= tAS)
1085
                REPORT "BA Setup time violation -- tAS"
1086
                SEVERITY WARNING;
1087
            ASSERT(Dq'LAST_EVENT >= tDS)
1088
                REPORT "Dq Setup time violation -- tDS"
1089
                SEVERITY WARNING;
1090
        END IF;
1091
    END PROCESS;
1092
 
1093
    -- Hold timing checks
1094
    Hold_check : PROCESS
1095
    BEGIN
1096
        WAIT ON Clk'DELAYED (tCKH), Clk'DELAYED (tCMH), Clk'DELAYED (tAH), Clk'DELAYED (tDH);
1097
        IF Clk'DELAYED (tCKH) = '1' THEN
1098
            ASSERT(Cke'LAST_EVENT > tCKH)
1099
                REPORT "CKE Hold time violation -- tCKH"
1100
                SEVERITY WARNING;
1101
        END IF;
1102
        IF Clk'DELAYED (tCMH) = '1' THEN
1103
            ASSERT(Cs_n'LAST_EVENT > tCMH)
1104
                REPORT "CS# Hold time violation -- tCMH"
1105
                SEVERITY WARNING;
1106
            ASSERT(Cas_n'LAST_EVENT > tCMH)
1107
                REPORT "CAS# Hold time violation -- tCMH"
1108
                SEVERITY WARNING;
1109
            ASSERT(Ras_n'LAST_EVENT > tCMH)
1110
                REPORT "RAS# Hold time violation -- tCMH"
1111
                SEVERITY WARNING;
1112
            ASSERT(We_n'LAST_EVENT > tCMH)
1113
                REPORT "WE# Hold time violation -- tCMH"
1114
                SEVERITY WARNING;
1115
            ASSERT(Dqm'LAST_EVENT > tCMH)
1116
                REPORT "Dqm Hold time violation -- tCMH"
1117
                SEVERITY WARNING;
1118
        END IF;
1119
        IF Clk'DELAYED (tAH) = '1' THEN
1120
            ASSERT(Addr'LAST_EVENT > tAH)
1121
                REPORT "ADDR Hold time violation -- tAH"
1122
                SEVERITY WARNING;
1123
            ASSERT(Ba'LAST_EVENT > tAH)
1124
                REPORT "BA Hold time violation -- tAH"
1125
                SEVERITY WARNING;
1126
        END IF;
1127
        IF Clk'DELAYED (tDH) = '1' THEN
1128
            ASSERT(Dq'LAST_EVENT > tDH)
1129
                REPORT "Dq Hold time violation -- tDH"
1130
                SEVERITY WARNING;
1131
        END IF;
1132
    END PROCESS;
1133
 
1134
END behave;

powered by: WebSVN 2.1.0

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