📄 sdram.v
字号:
end // 3'b000
3'b001: begin
i_state <= 3'b011;
i_cmd <= {{1{1'b0}},3'h2};
i_count <= 0;
i_next <= 3'b010;
end // 3'b001
3'b010: begin
i_cmd <= {{1{1'b0}},3'h1};
i_refs <= i_refs + 1'b1;
i_state <= 3'b011;
i_count <= 3;
// Count up init_refresh_commands
if (i_refs == 3'h1)
i_next <= 3'b111;
else
i_next <= 3'b010;
end // 3'b010
3'b011: begin
i_cmd <= {{1{1'b0}},3'h7};
//WAIT til safe to Proceed...
if (i_count > 1)
i_count <= i_count - 1'b1;
else
i_state <= i_next;
end // 3'b011
3'b101: begin
i_state <= 3'b101;
end // 3'b101
3'b111: begin
i_state <= 3'b011;
i_cmd <= {{1{1'b0}},3'h0};
i_addr <= {{2{1'b0}},1'b0,2'b00,3'h3,4'h0};
i_count <= 4;
i_next <= 3'b101;
end // 3'b111
default: begin
i_state <= 3'b000;
end // default
endcase // i_state
end
end
assign active_bank = {active_addr[21],active_addr[8]};
assign csn_match = active_cs_n == f_cs_n;
assign rnw_match = active_rnw == f_rnw;
assign bank_match = active_bank == f_bank;
assign row_match = {active_addr[20 : 9]} == {f_addr[20 : 9]};
assign pending = csn_match && rnw_match && bank_match && row_match && !f_empty;
assign cas_addr = f_select ? { {4{1'b0}},f_addr[7 : 0] } : { {4{1'b0}},active_addr[7 : 0] };
// **** Main FSM ****
always @(posedge clk or negedge reset_n)
begin
if (reset_n == 0)
begin
m_state <= 9'b000000001;
m_next <= 9'b000000001;
m_cmd <= 4'b1111;
m_bank <= 2'b00;
m_addr <= 12'b000000000000;
m_data <= 32'b00000000000000000000000000000000;
m_dqm <= 4'b0000;
m_count <= 3'b000;
ack_refresh_request <= 1'b0;
f_pop <= 1'b0;
oe <= 1'b0;
end
else
begin
f_pop <= 1'b0;
oe <= 1'b0;
case (m_state) // synthesis parallel_case full_case
9'b000000001: begin
//Wait for init-fsm to be done...
if (init_done)
begin
//Hold bus if another cycle ended to arf.
if (refresh_request)
m_cmd <= {{1{1'b0}},3'h7};
else
m_cmd <= 4'b1111;
ack_refresh_request <= 1'b0;
//Wait for a read/write request.
if (refresh_request)
begin
m_state <= 9'b001000000;
m_next <= 9'b010000000;
m_count <= 0;
active_cs_n <= 1'b1;
end
else if (!f_empty)
begin
f_pop <= 1'b1;
active_cs_n <= f_cs_n;
active_rnw <= f_rnw;
active_addr <= f_addr;
active_data <= f_data;
active_dqm <= f_dqm;
m_state <= 9'b000000010;
end
end
else
begin
m_addr <= i_addr;
m_state <= 9'b000000001;
m_next <= 9'b000000001;
m_cmd <= i_cmd;
end
end // 9'b000000001
9'b000000010: begin
m_state <= 9'b000000100;
m_cmd <= {csn_decode,3'h3};
m_bank <= active_bank;
m_addr <= active_addr[20 : 9];
m_data <= active_data;
m_dqm <= active_dqm;
m_count <= 1;
m_next <= active_rnw ? 9'b000001000 : 9'b000010000;
end // 9'b000000010
9'b000000100: begin
// precharge all if arf, else precharge csn_decode
if (m_next == 9'b010000000)
m_cmd <= {{1{1'b0}},3'h7};
else
m_cmd <= {csn_decode,3'h7};
//Count down til safe to Proceed...
if (m_count > 1)
m_count <= m_count - 1'b1;
else
m_state <= m_next;
end // 9'b000000100
9'b000001000: begin
m_cmd <= {csn_decode,3'h5};
m_bank <= f_select ? f_bank : active_bank;
m_dqm <= f_select ? f_dqm : active_dqm;
m_addr <= cas_addr;
//Do we have a transaction pending?
if (pending)
begin
//if we need to ARF, bail, else spin
if (refresh_request)
begin
m_state <= 9'b000000100;
m_next <= 9'b000000001;
m_count <= 2;
end
else
begin
f_pop <= 1'b1;
active_cs_n <= f_cs_n;
active_rnw <= f_rnw;
active_addr <= f_addr;
active_data <= f_data;
active_dqm <= f_dqm;
end
end
else
begin
//correctly end RD spin cycle if fifo mt
if (~pending & f_pop)
m_cmd <= {csn_decode,3'h7};
m_state <= 9'b100000000;
end
end // 9'b000001000
9'b000010000: begin
m_cmd <= {csn_decode,3'h4};
oe <= 1'b1;
m_data <= f_select ? f_data : active_data;
m_dqm <= f_select ? f_dqm : active_dqm;
m_bank <= f_select ? f_bank : active_bank;
m_addr <= cas_addr;
//Do we have a transaction pending?
if (pending)
begin
//if we need to ARF, bail, else spin
if (refresh_request)
begin
m_state <= 9'b000000100;
m_next <= 9'b000000001;
m_count <= 1;
end
else
begin
f_pop <= 1'b1;
active_cs_n <= f_cs_n;
active_rnw <= f_rnw;
active_addr <= f_addr;
active_data <= f_data;
active_dqm <= f_dqm;
end
end
else
begin
//correctly end WR spin cycle if fifo empty
if (~pending & f_pop)
begin
m_cmd <= {csn_decode,3'h7};
oe <= 1'b0;
end
m_state <= 9'b100000000;
end
end // 9'b000010000
9'b000100000: begin
m_cmd <= {csn_decode,3'h7};
//Count down til safe to Proceed...
if (m_count > 1)
m_count <= m_count - 1'b1;
else
begin
m_state <= 9'b001000000;
m_count <= 0;
end
end // 9'b000100000
9'b001000000: begin
m_state <= 9'b000000100;
m_addr <= {12{1'b1}};
// precharge all if arf, else precharge csn_decode
if (refresh_request)
m_cmd <= {{1{1'b0}},3'h2};
else
m_cmd <= {csn_decode,3'h2};
end // 9'b001000000
9'b010000000: begin
ack_refresh_request <= 1'b1;
m_state <= 9'b000000100;
m_cmd <= {{1{1'b0}},3'h1};
m_count <= 3;
m_next <= 9'b000000001;
end // 9'b010000000
9'b100000000: begin
m_cmd <= {csn_decode,3'h7};
//if we need to ARF, bail, else spin
if (refresh_request)
begin
m_state <= 9'b000000100;
m_next <= 9'b000000001;
m_count <= 1;
end
else //wait for fifo to have contents
if (!f_empty)
//Are we 'pending' yet?
if (csn_match && rnw_match && bank_match && row_match)
begin
m_state <= f_rnw ? 9'b000001000 : 9'b000010000;
f_pop <= 1'b1;
active_cs_n <= f_cs_n;
active_rnw <= f_rnw;
active_addr <= f_addr;
active_data <= f_data;
active_dqm <= f_dqm;
end
else
begin
m_state <= 9'b000100000;
m_next <= 9'b000000001;
m_count <= 1;
end
end // 9'b100000000
// synthesis translate_off
default: begin
m_state <= m_state;
m_cmd <= 4'b1111;
f_pop <= 1'b0;
oe <= 1'b0;
end // default
// synthesis translate_on
endcase // m_state
end
end
assign rd_strobe = m_cmd[2 : 0] == 3'h5;
//Track RD Req's based on cas_latency w/shift reg
always @(posedge clk or negedge reset_n)
begin
if (reset_n == 0)
rd_valid <= {3{1'b0}};
else
rd_valid <= (rd_valid << 1) | { {2{1'b0}}, rd_strobe };
end
// Register dq data.
always @(posedge clk or negedge reset_n)
begin
if (reset_n == 0)
za_data <= 0;
else if (1)
za_data <= zs_dq;
end
// Delay za_valid to match registered data.
always @(posedge clk or negedge reset_n)
begin
if (reset_n == 0)
za_valid <= 0;
else if (1)
za_valid <= rd_valid[2];
end
assign cmd_code = m_cmd[2 : 0];
assign cmd_all = m_cmd;
//synthesis translate_off
//////////////// SIMULATION-ONLY CONTENTS
assign txt_code = (cmd_code == 3'h0)? 24'h4c4d52 :
(cmd_code == 3'h1)? 24'h415246 :
(cmd_code == 3'h2)? 24'h505245 :
(cmd_code == 3'h3)? 24'h414354 :
(cmd_code == 3'h4)? 24'h205752 :
(cmd_code == 3'h5)? 24'h205244 :
(cmd_code == 3'h6)? 24'h425354 :
(cmd_code == 3'h7)? 24'h4e4f50 :
24'h424144;
assign CODE = &(cmd_all|4'h7) ? 24'h494e48 : txt_code;
//////////////// END SIMULATION-ONLY CONTENTS
//synthesis translate_on
endmodule
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -