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

Subversion Repositories wbddr3

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /wbddr3
    from Rev 8 to Rev 9
    Reverse comparison

Rev 8 → Rev 9

/trunk/bench/cpp/ddrsdram_tb.cpp
122,13 → 122,11
(m_core->i_ddr_data),
(m_core->o_ddr_data));
 
printf(" FIFO[%x,%x](%d,%d,%08x-%08x-%08x)",
printf(" FIFO[%x,%x](%s,%d,%08x)",
m_core->v__DOT__bus_fifo_head,
m_core->v__DOT__bus_fifo_tail,
m_core->v__DOT__bus_fifo_new[m_core->v__DOT__bus_fifo_tail],
(m_core->v__DOT__bus_fifo_new[m_core->v__DOT__bus_fifo_tail])?"N":"o",
m_core->v__DOT__bus_fifo_sub[m_core->v__DOT__bus_fifo_tail],
m_core->v__DOT__r_data,
m_core->v__DOT__bus_fifo_data[(m_core->v__DOT__bus_fifo_head-1)&15],
m_core->v__DOT__bus_fifo_data[m_core->v__DOT__bus_fifo_tail]);
 
printf(" BUS[%03x/%03x/%03x/%d]",
147,12 → 145,30
(m_core->v__DOT__reset_cmd));
*/
 
printf(" %s%03x[%d]%04x:%d",
(m_core->v__DOT__r_pending)?"R":" ",
printf(" R_%s%03x[%d]%04x:%d/%08x",
(!m_core->v__DOT__r_pending)?"_"
:(m_core->v__DOT__r_we)?"W":"R",
(m_core->v__DOT__r_row),
(m_core->v__DOT__r_bank),
(m_core->v__DOT__r_col),0);
// (m_core->v__DOT__r_sub));
(m_core->v__DOT__r_col),
(m_core->v__DOT__r_sub),
(m_core->v__DOT__r_data));
 
printf(" S_%s%03x[%d]%04x:%d/%08x%s%s%s",
(!m_core->v__DOT__s_pending)?"_"
:(m_core->v__DOT__s_we)?"W":"R",
(m_core->v__DOT__s_row),
(m_core->v__DOT__s_bank),
(m_core->v__DOT__s_col),
(m_core->v__DOT__s_sub),
(m_core->v__DOT__s_data),
(m_core->v__DOT__s_match)?"M":" ",
(m_core->v__DOT__pipe_stall)?"P":" ",
"-"
//(m_core->v__DOT__s_stall)?"S":" "
);
 
 
printf(" %s%s%s",
"B",
// (m_core->v__DOT__all_banks_closed)?"b":"B",
172,7 → 188,7
extern int gbl_state, gbl_counts;
printf(" %2d:%08x ", gbl_state, gbl_counts);
 
printf(" %s%s%s%s%s%s%s:%08x:%08x",
printf(" %s%s%s%s%s%s:%08x:%08x",
(m_core->v__DOT__reset_override)?"R":" ",
(m_core->v__DOT__need_refresh)?"N":" ",
(m_core->v__DOT__need_close_bank)?"C":" ",
179,7 → 195,6
(m_core->v__DOT__need_open_bank)?"O":" ",
(m_core->v__DOT__valid_bank)?"V":" ",
(m_core->v__DOT__r_move)?"R":" ",
(m_core->v__DOT__m_move)?"M":" ",
m_core->v__DOT__activate_bank_cmd,
m_core->v__DOT__cmd);
 
251,8 → 266,7
if (m_core->o_wb_stall) {
while((errcount++ < BOMBCOUNT)&&(m_core->o_wb_stall))
tick();
} else
tick();
} tick();
 
m_core->i_wb_stb = 0;
 
423,7 → 437,6
Verilated::commandArgs(argc, argv);
DDRSDRAM_TB *tb = new DDRSDRAM_TB;
unsigned *rdbuf, *mbuf;
int nw = 3, nr = 13;
unsigned mlen = (1<<(LGMEMSIZE-2));
 
printf("Giving the core 140k cycles to start up\n");
443,6 → 456,16
printf("Charging my memory with random values\n");
uload(mlen, rdbuf);
 
#define SINGULAR_WRITE
#define SINGULAR_READ
#define BIGPIPELINE_WRITE
#define BIGPIPELINE_READ
#define PRIMEVEC_WRITE
#define PRIMEVEC_READ
#define SKIP_WRITE
#define SKIP_READ
 
#ifdef SINGULAR_WRITE
// First test: singular reads through the memory, followed by
// singular writes
printf("Starting the single-read test\n");
456,7 → 479,17
} if (tb->bombed())
goto test_failure;
 
} for(int i=0; i<(int)mlen; i++) {
}
#else
#ifdef SINGULAR_READ
// If we aren't doing the write test, we still need to charge
// the memory for the read test. Here we do it manually.
for(int i=0; i<(int)mlen; i++)
(*tb)[i] = rdbuf[i];
#endif // !SINGULAR_WRITE && SINGULAR_READ
#endif // SINGULAR_WRITE
#ifdef SINGULAR_READ
for(int i=0; i<(int)mlen; i++) {
unsigned v;
if (rdbuf[i] != (v=tb->wb_read(i))) {
printf("READ[%06x] = %08x (Expecting %08x)\n",
466,7 → 499,9
goto test_failure;
tb->wb_tick();
}
#endif
 
#ifdef BIGPIPELINE_WRITE
// Second test: Vector writes going through all memory, followed a
// massive vector read
uload(mlen, rdbuf); // Get some new values
481,7 → 516,16
goto test_failure;
}
}
 
#else
#ifdef BIGPIPELINE_READ
uload(mlen, rdbuf); // Get some new values
// If we aren't doing the write test, we still need to charge
// the memory for the read test. Here we do it manually.
for(int i=0; i<(int)mlen; i++)
(*tb)[i] = rdbuf[i];
#endif // BIGPIPELINE_WRITE && BIGPIPELINE_READ
#endif
#ifdef BIGPIPELINE_READ
tb->wb_read( 0, mlen, mbuf);
if (tb->bombed())
goto test_failure;
492,40 → 536,61
goto test_failure;
}
}
#endif
 
#ifdef PRIMEVEC_WRITE
// Third test: Vector writes going through all memory, in prime numbers
// of values at a time, followed by reads via a different prime number
uload(mlen, rdbuf); // Get some new values
for(int i=0; i<(int)mlen; i+=nw) {
int ln = ((int)mlen-i>nw)?nw:mlen-i;
tb->wb_write(i, nw, &rdbuf[i]);
for(int j=0; j<ln; j++) {
if ((*tb)[i+j] != rdbuf[i+j]) {
printf("P-WRITE[%06x] = %08x (Expecting %08x) FAILED\n",
i, (*tb)[i], rdbuf[i]);
{
int nw = 3;
for(int i=0; i<(int)mlen; i+=nw) {
int ln = ((int)mlen-i>nw)?nw:mlen-i;
tb->wb_write(i, nw, &rdbuf[i]);
for(int j=0; j<ln; j++) {
if ((*tb)[i+j] != rdbuf[i+j]) {
printf("P-WRITE[%06x] = %08x (Expecting %08x) FAILED\n",
i, (*tb)[i], rdbuf[i]);
goto test_failure;
}
} if (tb->bombed())
goto test_failure;
}
} if (tb->bombed())
goto test_failure;
} for(int i=0; i<(int)mlen; i+=nr) {
int ln = ((int)mlen-i>nr)?nr:mlen-i;
tb->wb_read(i, nr, &mbuf[i]);
for(int j=0; j<ln; j++) {
if (mbuf[i+j] != rdbuf[i+j]) {
printf("P-READ[%06x] = %08x (Expecting %08x) FAILED\n",
i, mbuf[i], rdbuf[i]);
}
}
#else
#ifdef PRIMEVEC_READ
uload(mlen, rdbuf); // Get some new values
// If we aren't doing the write test, we still need to charge
// the memory for the read test. Here we do it manually.
for(int i=0; i<(int)mlen; i++)
(*tb)[i] = rdbuf[i];
#endif
#endif
#ifdef PRIMEVEC_READ
{
int nr = 13;
for(int i=0; i<(int)mlen; i+=nr) {
int ln = ((int)mlen-i>nr)?nr:mlen-i;
tb->wb_read(i, nr, &mbuf[i]);
for(int j=0; j<ln; j++) {
if (mbuf[i+j] != rdbuf[i+j]) {
printf("P-READ[%06x] = %08x (Expecting %08x) FAILED\n",
i, mbuf[i], rdbuf[i]);
goto test_failure;
}
} if (tb->bombed())
goto test_failure;
}
} if (tb->bombed())
goto test_failure;
}
}
#endif
 
#ifdef SKIP_WRITE
// Fourth test: Singular writes though all of memory, skipping by some
// prime address increment each time, followed by reads via a different
// prime numbered increment.
uload(mlen, rdbuf); // Get some new values
for(int i=0; i<(int)mlen; i++) {
int loc = (i*13)&0x3ffffff;
int loc = (i*3889)&(mlen-1);
tb->wb_write(loc, rdbuf[loc]);
if ((*tb)[loc] != rdbuf[loc]) {
printf("R-WRITE[%06x] = %08x (Expecting %08x) FAILED\n",
533,8 → 598,17
goto test_failure;
} if (tb->bombed())
goto test_failure;
} for(int i=0; i<(int)mlen; i++) {
int loc = (i*19)&0x3ffffff;
}
#else
#ifdef SKIP_READ
uload(mlen, rdbuf); // Get some new values
for(int i=0; i<(int)mlen; i++)
(*tb)[i] = rdbuf[i];
#endif // !SKIP_WRITE && SKIP_READ
#endif
#ifdef SKIP_READ
for(int i=0; i<(int)mlen; i++) {
int loc = (i*7477)&(mlen-1);
mbuf[loc] = tb->wb_read(loc);
if (mbuf[loc] != rdbuf[loc]) {
printf("R-READ[%06x] = %08x (Expecting %08x) FAILED\n",
543,6 → 617,7
} if (tb->bombed())
goto test_failure;
}
#endif
 
 
printf("SUCCESS!!\n");
/trunk/bench/cpp/ddrsdramsim.cpp
38,6 → 38,7
#include <stdio.h>
#include <assert.h>
 
#define PREFIX "DDR3-SDRAM"
const unsigned ckCL = 5,
ckRC = 3,
ckRFC = 320, // Clocks from refresh to activate
142,7 → 143,7
m_reset_counts++;
assert(cke);
if (cmd != DDR_NOOP) {
printf("DDR3-SDRAM::RESET-CMD[4]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
printf(PREFIX "::RESET-CMD[4]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
assert(m_reset_counts > 3);
m_reset_counts = 0;
m_reset_state = 5;
154,7 → 155,7
m_reset_counts++;
assert(cke);
if (cmd != DDR_NOOP) {
printf("DDR3-SDRAM::RESET-CMD[5]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
printf(PREFIX "::RESET-CMD[5]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
assert(m_reset_counts > 11);
m_reset_counts = 0;
m_reset_state = 6;
165,7 → 166,7
m_reset_counts++;
assert(cke);
if (cmd != DDR_NOOP) {
printf("DDR3-SDRAM::RESET-CMD[6]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
printf(PREFIX "::RESET-CMD[6]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
assert(m_reset_counts > 512);
m_reset_counts = 0;
m_reset_state = 7;
176,7 → 177,7
m_reset_counts++;
assert(cke);
if (cmd != DDR_NOOP) {
printf("DDR3-SDRAM::RESET-CMD[7]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
printf(PREFIX "::RESET-CMD[7]: %d:%08x[%d]@0x%04x\n", cmd, m_reset_counts, ba, addr);
assert(m_reset_counts > 3);
m_reset_counts = 0;
m_reset_state = 8;
189,7 → 190,7
assert(cmd == DDR_NOOP);
if (m_reset_counts > 140) {
m_reset_state = 16;
printf("DDR3-SDRAM: Leaving reset state\n");
printf(PREFIX ": Leaving reset state\n");
}
break;
default:
217,7 → 218,7
m_bank[i].tick(DDR_REFRESH,0);
 
if (m_nrefresh_issued == nREF)
printf("DDRSDRAM::Refresh cycle complete\n");
printf(PREFIX "::Refresh cycle complete\n");
} else {
// In operational mode!!
 
248,7 → 249,6
}
break;
case DDR_ACTIVATE:
printf("DDRSIM::ACTIVE, clocks_since_refresh = %d >= %d\n", m_clocks_since_refresh, ckRFC);
assert(m_clocks_since_refresh >= (int)ckRFC);
m_bank[ba].tick(DDR_ACTIVATE,addr);
for(int i=0; i<NBANKS; i++)
269,14 → 269,11
caddr &= ~7;
caddr >>= 1;
 
printf("DDRSDRAM::WRITE ADDR = %04x|%d|%04x|%d -> %06x\n",
m_bank[ba].m_row, ba, addr, 0, caddr);
 
BUSTIMESLOT *tp;
int offset = m_busloc+ckCL+1;
 
tp = &m_bus[(offset+0)&(NTIMESLOTS-1)];
printf("Setting bus timeslots from (now=%d)+%d=%d to now+%d+3\n", m_busloc, ckCL,(m_busloc+ckCL)&(NTIMESLOTS-1), ckCL);
// printf("Setting bus timeslots from (now=%d)+%d=%d to now+%d+3\n", m_busloc, ckCL,(m_busloc+ckCL)&(NTIMESLOTS-1), ckCL);
tp->m_addr = caddr ;
tp->m_used = 1;
tp->m_read = 0;
355,12 → 352,6
m_busloc = (m_busloc+1)&(NTIMESLOTS-1);
 
BUSTIMESLOT *ts = &m_bus[m_busloc];
if (ts->m_used) {
printf("Current timeslot = %2d, used", m_busloc);
if (ts->m_read)
printf(", read");
printf("\n");
}
unsigned vl = ts->m_data;
assert( ((!ts->m_used)||(busoe))
|| ((ts->m_used)&&(ts->m_read)));
367,7 → 358,7
 
assert((!ts->m_used)||(ts->m_addr < (unsigned)m_memlen));
if ((ts->m_used)&&(!ts->m_read)&&(!dm)) {
printf("Setting MEM[%08x] = %08x\n", ts->m_addr, data);
printf(PREFIX "::Setting MEM[%08x] = %08x\n", ts->m_addr, data);
m_mem[ts->m_addr] = data;
}
ts->m_used = 0;
/trunk/rtl/wbddrsdram.v
6,6 → 6,24
//
// Purpose:
//
/*
Stall logic:
1. First clock sets r_* variables.
2. Second clock sets need_* variables. If need_open, need_close, or
need_refresh are true, that should also set the o_wb_stall
variable. Well also move r_* info to s_* (think s=stall)
3. If stalled, the next command comes from s_*. Otherwise, from r_*.
4. Bus FIFO fills from s_*
//
//
For every transaction, one of 4 possibilities:
1. Wait for refresh to complete
2. Wait for precharge and activate to complete
3. Wait for activate to complete
4. Issue RW cmd
5. Wait for bus transaction to complete
6. ACK
*/
// Creator: Dan Gisselquist, Ph.D.
// Gisselquist Technology, LLC
//
124,9 → 142,20
reg [1:0] r_sub;
reg r_move; // It was accepted, and can move to next stage
 
// The pending transaction, one further into the pipeline. This is
// the stage where the read/write command is actually given to the
// interface if we haven't stalled.
reg [31:0] s_data;
reg s_pending, s_we, s_match;
reg [25:0] s_addr;
reg [13:0] s_row, s_nxt_row;
reg [2:0] s_bank, s_nxt_bank;
reg [9:0] s_col;
reg [1:0] s_sub;
 
// Can the pending transaction be satisfied with the current (ongoing)
// transaction?
reg m_move, m_match, m_continue, m_pending, m_we;
reg m_move, m_match, m_pending, m_we;
reg [25:0] m_addr;
reg [13:0] m_row;
reg [2:0] m_bank;
145,10 → 174,12
valid_bank, last_valid_bank;
reg [(`DDR_CMDLEN-1):0] close_bank_cmd, activate_bank_cmd,
maybe_close_cmd, maybe_open_cmd, rw_cmd;
reg [1:0] rw_sub;
reg rw_we;
 
wire w_this_closing_bank, w_this_opening_bank,
w_this_maybe_close, w_this_maybe_open,
w_this_rw_move, w_this_refresh;
w_this_rw_move;
reg last_closing_bank, last_opening_bank;
//
// tWTR = 7.5
188,9 → 219,10
// the DDR3 SDRAM, or a timer to wait until the next command. Further, the
// timer commands indicate whether or not the command during the timer is to
// be set to idle, or whether the command is instead left as it was.
reg reset_override, reset_ztimer;
reg reset_override, reset_ztimer, maintenance_override;
reg [4:0] reset_address;
reg [(`DDR_CMDLEN-1):0] reset_cmd, cmd, refresh_cmd;
reg [(`DDR_CMDLEN-1):0] reset_cmd, cmd, refresh_cmd,
maintenance_cmd;
reg [24:0] reset_instruction;
reg [16:0] reset_timer;
initial reset_override = 1'b1;
512,7 → 544,8
begin
bus_active[`BUSNOW:0] <= { bus_active[(`BUSNOW-1):0], 1'b0 };
bus_read[`BUSNOW:0] <= { bus_read[(`BUSNOW-1):0], 1'b0 }; // Drive the d-bus?
bus_new[`BUSNOW:0] <= { bus_new[(`BUSNOW-1):0], 1'b0 }; // Drive the d-bus?
// Is this a new command? i.e., the start of a transaction?
bus_new[`BUSNOW:0] <= { bus_new[(`BUSNOW-1):0], 1'b0 };
//bus_mask[8:0] <= { bus_mask[7:0], 1'b1 }; // Write this value?
bus_subaddr[8] <= bus_subaddr[7];
bus_subaddr[7] <= bus_subaddr[6];
530,9 → 563,9
bus_subaddr[3] <= 2'h0;
bus_subaddr[2] <= 2'h1;
bus_subaddr[1] <= 2'h2;
bus_new[{ 2'b0, (2'h3-r_sub) }] <= 1'b1;
bus_new[{ 2'b0, rw_sub }] <= 1'b1;
 
bus_read[3:0] <= (r_we)? 4'h0:4'hf;
bus_read[3:0] <= (rw_we)? 4'h0:4'hf;
end
end
 
544,19 → 577,30
// Now, let's see, can we issue a read command?
//
//
wire w_s_match;
assign w_s_match = (s_pending)&&(r_pending)&&(r_we == s_we)
&&(r_row == s_row)&&(r_bank == s_bank)
&&(r_col == s_col)
&&(r_sub > s_sub);
reg pipe_stall;
always @(posedge i_clk)
begin
if ((i_wb_stb)&&(~o_wb_stall))
r_pending <= (i_wb_stb)&&(~o_wb_stall)
||(r_pending)&&(pipe_stall);
if (~pipe_stall)
s_pending <= r_pending;
if (~pipe_stall)
begin
r_pending <= 1'b1;
pipe_stall <= (r_pending)&&(((!w_r_valid)||(valid_bank))&&(!w_s_match));
o_wb_stall <= (r_pending)&&(((!w_r_valid)||(valid_bank))&&(!w_s_match));
end else begin // if (pipe_stall)
pipe_stall <= (s_pending)&&((!w_s_valid)||(valid_bank)||(r_move)||(last_valid_bank));
o_wb_stall <= (s_pending)&&((!w_s_valid)||(valid_bank)||(r_move)||(last_valid_bank));
end
if (need_refresh)
o_wb_stall <= 1'b1;
end else if ((m_move)||(w_this_rw_move))
begin
r_pending <= 1'b0;
o_wb_stall <= 1'b0;
end
 
if (~o_wb_stall)
if (~pipe_stall)
begin
r_we <= i_wb_we;
r_addr <= i_wb_addr;
570,12 → 614,42
r_nxt_row <= (i_wb_addr[11:9]==3'h7)?i_wb_addr[25:12]+14'h1:i_wb_addr[25:12];
r_nxt_bank <= i_wb_addr[11:9]+3'h1;
end
 
if (~pipe_stall)
begin
// Moving one down the pipeline
s_we <= r_we;
s_addr <= r_addr;
s_data <= r_data;
s_row <= r_row;
s_bank <= r_bank;
s_col <= r_col;
s_sub <= r_sub;
 
// pre-emptive work
s_nxt_row <= r_nxt_row;
s_nxt_bank <= r_nxt_bank;
 
s_match <= w_s_match;
end
end
 
wire w_need_close_this_bank, w_need_open_bank;
wire w_need_close_this_bank, w_need_open_bank,
w_r_valid, w_s_valid;
assign w_need_close_this_bank = (r_pending)&&(bank_status[r_bank][0])
&&(r_row != bank_address[r_bank]);
assign w_need_open_bank = (r_pending)&&(bank_status[r_bank][1:0]==2'b00);
&&(r_row != bank_address[r_bank])
||(pipe_stall)&&(s_pending)&&(bank_status[s_bank][0])
&&(s_row != bank_address[s_bank]);
assign w_need_open_bank = (r_pending)&&(bank_status[r_bank][1:0]==2'b00)
||(pipe_stall)&&(s_pending)&&(bank_status[s_bank][1:0]==2'b00);
assign w_r_valid = (!need_refresh)&&(r_pending)
&&(bank_status[r_bank][3])
&&(bank_address[r_bank]==r_row)
&&(!bus_active[0]);
assign w_s_valid = (!need_refresh)&&(s_pending)
&&(bank_status[s_bank][3])
&&(bank_address[s_bank]==s_row)
&&(!bus_active[0]);
 
always @(posedge i_clk)
begin
606,52 → 680,31
 
 
 
valid_bank <= (r_pending)&&(bank_status[r_bank][3])
&&(bank_address[r_bank]==r_row)
&&(!last_valid_bank)&&(!r_move)
&&(!bus_active[0]);
valid_bank <= ((w_r_valid)||(pipe_stall)&&(w_s_valid))
&&(!last_valid_bank)&&(!r_move);
last_valid_bank <= r_move;
 
rw_cmd[`DDR_CSBIT:`DDR_WEBIT] <= (~r_pending)?`DDR_NOOP:((r_we)?`DDR_WRITE:`DDR_READ);
rw_cmd[`DDR_WEBIT-1:0] <= { r_bank, 3'h0, 1'b0, r_col };
if ((s_pending)&&(pipe_stall))
rw_cmd[`DDR_CSBIT:`DDR_WEBIT] <= (s_we)?`DDR_WRITE:`DDR_READ;
else if (r_pending)
rw_cmd[`DDR_CSBIT:`DDR_WEBIT] <= (r_we)?`DDR_WRITE:`DDR_READ;
else
rw_cmd[`DDR_CSBIT:`DDR_WEBIT] <= `DDR_NOOP;
if ((s_pending)&&(pipe_stall))
rw_cmd[`DDR_WEBIT-1:0] <= { s_bank, 3'h0, 1'b0, s_col };
else
rw_cmd[`DDR_WEBIT-1:0] <= { r_bank, 3'h0, 1'b0, r_col };
if ((s_pending)&&(pipe_stall))
rw_sub <= 2'b11 - s_sub;
else
rw_sub <= 2'b11 - r_sub;
if ((s_pending)&&(pipe_stall))
rw_we <= s_we;
else
rw_we <= r_we;
end
 
 
// Match registers, to see if we can move forward without sending a
// new command
reg [2:0] m_clock;
reg m_timeout;
always @(posedge i_clk)
begin
if (|m_clock)
m_clock <= m_clock - 3'h1;
if (!m_timeout)
m_timeout <= (m_clock[2:1] == 2'b00);
if (w_this_rw_move)
begin
m_pending <= r_pending;
m_we <= r_we;
m_addr <= r_addr;
m_row <= r_row;
m_bank <= r_bank;
m_col <= r_col;
m_sub <= r_sub;
m_clock<= 3'h7;
m_timeout <= 1'b0;
end else if ((m_match)&&(!m_timeout))
m_sub <= r_sub;
 
m_match <= (m_pending)&&(r_pending)&&(r_we == m_we)
&&(r_row == m_row)&&(r_bank == m_bank)
&&(r_col == m_col)
&&(r_sub > m_sub);
m_continue <= (m_pending)&&(r_pending)&&(r_we == m_we)
&&(r_row == m_row)&&(r_bank == m_bank)
&&(r_col == m_col+10'h1);
// m_nextbank <= (m_pending)&&(r_pending)&&(r_we == m_we)
// &&(r_row == m_row)&&(r_bank == m_bank);
end
 
//
//
// Okay, let's look at the last assignment in our chain. It should look
667,21 → 720,31
else if (reset_ztimer)
o_ddr_cke <= reset_instruction[`DDR_CKEBIT];
 
assign w_this_refresh = (!reset_override)&&(need_refresh)
&&(refresh_cmd[`DDR_CSBIT:`DDR_WEBIT] == `DDR_REFRESH);
always @(posedge i_clk)
if (i_reset)
maintenance_override <= 1'b1;
else
maintenance_override <= (reset_override)||(need_refresh);
 
assign w_this_closing_bank = (!reset_override)&&(!need_refresh)
initial maintenance_cmd = { `DDR_NOOP, 17'h00 };
always @(posedge i_clk)
if (i_reset)
maintenance_cmd <= { `DDR_NOOP, 17'h00 };
else
maintenance_cmd <= (reset_override)?reset_cmd:refresh_cmd;
 
assign w_this_closing_bank = (!maintenance_override)
&&(need_close_bank);
assign w_this_opening_bank = (!reset_override)&&(!need_refresh)
assign w_this_opening_bank = (!maintenance_override)
&&(!need_close_bank)&&(need_open_bank);
assign w_this_rw_move = (!reset_override)&&(!need_refresh)
assign w_this_rw_move = (!maintenance_override)
&&(!need_close_bank)&&(!need_open_bank)
&&(valid_bank)&&(!r_move);
assign w_this_maybe_close = (!reset_override)&&(!need_refresh)
assign w_this_maybe_close = (!maintenance_override)
&&(!need_close_bank)&&(!need_open_bank)
&&((!valid_bank)||(r_move))
&&(maybe_close_next_bank);
assign w_this_maybe_open = (!reset_override)&&(!need_refresh)
assign w_this_maybe_open = (!maintenance_override)
&&(!need_close_bank)&&(!need_open_bank)
&&((!valid_bank)||(r_move))
&&(!maybe_close_next_bank)
693,13 → 756,10
last_maybe_open <= 1'b0;
last_maybe_close <= 1'b0;
r_move <= 1'b0;
if (reset_override)
cmd <= reset_cmd[`DDR_CSBIT:0];
else if (need_refresh)
if (maintenance_override) // Command from either reset or
cmd <= maintenance_cmd; // refresh logic
else if (need_close_bank)
begin
cmd <= refresh_cmd; // The command from the refresh logc
end else if (need_close_bank)
begin
cmd <= close_bank_cmd;
last_closing_bank <= 1'b1;
end else if (need_open_bank)
732,7 → 792,11
 
// The bus R/W FIFO
wire w_bus_fifo_read_next_transaction;
assign w_bus_fifo_read_next_transaction = (bus_fifo_sub[bus_fifo_tail]==bus_subaddr[`BUSREG])&&(bus_active[`BUSREG])&&(bus_new[`BUSREG] == bus_fifo_new[bus_fifo_tail]);
assign w_bus_fifo_read_next_transaction =
(bus_fifo_sub[bus_fifo_tail]==bus_subaddr[`BUSREG])
&&(bus_fifo_tail != bus_fifo_head)
&&(bus_active[`BUSREG])
&&(bus_new[`BUSREG] == bus_fifo_new[bus_fifo_tail]);
always @(posedge i_clk)
begin
pre_ack <= 1'b0;
743,7 → 807,7
bus_fifo_tail <= 4'h0;
o_ddr_dm <= 1'b0;
end else begin
if ((w_this_rw_move)||(m_move))
if ((w_this_rw_move)||((s_pending)&&(s_match)&&(!pipe_stall)))
bus_fifo_head <= bus_fifo_head + 4'h1;
 
o_ddr_dm <= (bus_active[`BUSREG])&&(!bus_read[`BUSREG]);
754,8 → 818,8
o_ddr_dm <= 1'b0;
end
end
bus_fifo_data[bus_fifo_head] <= r_data;
bus_fifo_sub[bus_fifo_head] <= r_sub;
bus_fifo_data[bus_fifo_head] <= s_data;
bus_fifo_sub[bus_fifo_head] <= s_sub;
bus_fifo_new[bus_fifo_head] <= w_this_rw_move;
end
 

powered by: WebSVN 2.1.0

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