sdram简易控制器设计

article/2025/10/26 11:59:26

耗时一周,终于完成sdram简易控制器的所有代码设计,其中感谢开源骚客 – 邓堪文老师在b站发布的相关视频学习教材;其中仿真模块及所使用到的sdram仿真文件来源于开源骚客;

因为时间较为紧迫,其中就不做代码的一些注释;

在设计中,总结一哈要主要的几个问题:

1. 仲裁模块中if/else语句中的先后顺序很重要,其中根据仿真的时序图经过多次修改;

2. 仲裁模块决定刷新/写/读操作的重要部分,要重点理清楚各模块产生请求信号后产生使能信号的先后顺序;

3. 读/写状态结束后应及时赋予PRE命令,否则导致读数据有误(具体可查看芯片手册相关介绍);

本设计中采用写3行数据后进行数据的读取,代码如下:

 初始化init模块:

module sdram_init(
sys_clk,
sys_rst_n,
init_cmd,
init_addr,
init_end
);input 					   	sys_clk,sys_rst_n;
output reg  [3:0] 	init_cmd;
output wire [12:0]  init_addr;
output wire 				init_end;reg [13:0] cnt_200us;
wire       flag_200us;
reg [3:0]  cnt_cmd;localparam delay_200us = 10000; //200us
//SDRAM init_cmd//
localparam NOP  = 4'b0111; 
localparam PRE  = 4'b0010; 
localparam AREF = 4'b0001; 
localparam MSET = 4'b0000; always@(posedge sys_clk or negedge sys_rst_n)
begin if(!sys_rst_n)cnt_200us <= 0;else if (flag_200us == 0)cnt_200us <= cnt_200us+1;
endassign flag_200us = (cnt_200us >= delay_200us) ? 1'b1:1'b0;always@(posedge sys_clk or negedge sys_rst_n)
begin if(!sys_rst_n)cnt_cmd <= 0;else if ((flag_200us == 1) && (init_end == 0))cnt_cmd <= cnt_cmd+1;
endalways@(posedge sys_clk or negedge sys_rst_n)
begin if(!sys_rst_n)init_cmd <= NOP ;else if (flag_200us == 1)case (cnt_cmd)0: init_cmd <= PRE;1: init_cmd <= AREF;5: init_cmd <= AREF;9: init_cmd <= MSET;default:init_cmd <= NOP;endcase
end//sdram addr//
//always@(posedge sys_clk or negedge sys_rst_n)
//begin 
//	if(!sys_rst_n)
//	init_addr <= 0;
//	else if (flag_200us == 1)
//	case (cnt_init_cmd)assign init_addr = (init_cmd == MSET) ? 13'b0_0000_0011_0010:12'b0_0100_0000_0010;
assign init_end = (cnt_cmd >= 'd10) ? 1'b1:1'b0;endmodule

刷新模块代码:

module sdram_aref(
sys_clk,
sys_rst_n,
init_end,
ref_en,
ref_req,
ref_end,
ref_cmd,
ref_addr
);input 		      sys_clk,sys_rst_n,ref_en,init_end;
output  reg     ref_req;
output  wire    ref_end;
output  reg [3:0]   ref_cmd;
output     [12:0]  ref_addr;  //4M*4banks*16bit//localparam Delay_15us  = 399;
localparam NOP  = 4'b0111; 
localparam PRE  = 4'b0010; 
localparam AREF = 4'b0001; reg     [3:0] 	cnt_cmd;
reg     [9:0] 	cnt_ref;
reg             ref_flag;always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)cnt_ref <= 1'b0;else if (cnt_ref == Delay_15us)cnt_ref <= 1'b0;else if (init_end == 1'b1)cnt_ref <= cnt_ref + 1'b1;
endalways@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)ref_req <= 0;else if (ref_en == 1 && ref_req == 1)ref_req <= 0;else if (cnt_ref >= Delay_15us)ref_req <= 1;
end
//assign ref_req = (cnt_ref == Delay_15us) ? 1'b1:1'b0;always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)ref_flag <= 0;else if (ref_en == 1)ref_flag <= 1;else if (ref_end == 1)ref_flag <= 0;
endalways@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)cnt_cmd <= 0;else if (ref_flag == 1)cnt_cmd <= cnt_cmd+1;elsecnt_cmd <= 0;
endalways@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)ref_cmd <= NOP;else case (cnt_cmd)1:ref_cmd <= PRE;2:ref_cmd <= AREF;default:ref_cmd <= NOP;endcase
endassign ref_end = (cnt_cmd >= 5)? 1'b1:1'b0;
assign ref_addr = 13'b0_0100_0000_0000;endmodule

写模块代码:

module sdram_write(
sys_clk,
sys_rst_n,
//ref_end,
ref_req,
wr_en,
wr_trig,wr_data,
wr_addr,
wr_cmd,
bank_addr,
wr_end,
wr_req
);input 		sys_clk;
input 		sys_rst_n;
//input 		ref_end;
input 		ref_req;
input 		wr_en;
input 		wr_trig;output reg  [5:0] 	wr_data;
output reg  [12:0]	wr_addr;
output reg  [3:0]    wr_cmd;
output      [1:0]    bank_addr;
output reg			   wr_end;
output reg	       wr_req;
//state//
localparam s_idle  = 5'b00001;
localparam s_req   = 5'b00010;
localparam s_act   = 5'b00100;
localparam s_wr    = 5'b01000;
localparam s_pre   = 5'b10000;
//cmd//
localparam PRE  = 4'b0010;
localparam AREF = 4'b0001;
localparam ACT  = 4'b0011;
localparam NOP  = 4'b0111;
localparam MSET = 4'b0000;
localparam WR   = 4'b0100;
localparam RD   = 4'b0101;reg cnt_act;
reg [1:0] burst_cnt;
reg [4:0] state;
reg [8:0] col_cnt;
reg col_full;
reg [13:0] row_addr; //change//
reg wr_data_end;
reg wr_flag;assign bank_addr = 2'b00;
//wr_req//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)wr_req <= 0;else if (wr_en == 1 && wr_req == 1)wr_req <= 0;else if (wr_trig == 1 || wr_end ==1 && wr_flag ==1)wr_req <= 1;
end
//wr_flag//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)wr_flag <= 0;else if (wr_en ==1 && wr_flag ==0)wr_flag <= 1;else if (wr_data_end == 1)wr_flag <= 0;
end
//state//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)state <= s_idle;else case (state)s_idle:beginif (wr_req == 1 )state <= s_req;elsestate <= s_idle;ends_req:beginif (wr_en == 1 )state <= s_act;elsestate <= s_req;ends_act:beginif (cnt_act ==1 )state <= s_wr;else if ((wr_data_end == 1))  //change//state <= s_idle;elsestate <= s_act;ends_wr:begin //change//if ((burst_cnt == 3 && ref_req ==1) || (wr_data_end == 1))state <= s_idle;else if (burst_cnt == 3 || col_full == 1)state <= s_pre;elsestate <= s_wr;ends_pre:beginif(wr_data_end == 1)state <= s_idle;elsestate<=s_act;enddefault: state <= s_idle;endcase
end
//cnt_act//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)cnt_act <= 0;else if (state == s_act)cnt_act <= cnt_act +1;
end
//burst_cnt//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)burst_cnt <= 0;else if (state == s_wr)burst_cnt <= burst_cnt +1;
end
//wr_cmd//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)wr_cmd <= NOP;else if (wr_en == 1)wr_cmd <= ACT;else if (cnt_act == 1)wr_cmd <= WR;else if ((burst_cnt == 3 || col_full == 1))wr_cmd <= PRE;elsewr_cmd <= NOP;
end
//wr_end//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)wr_end <= 0;else if ((burst_cnt == 3 && ref_req ==1) || (wr_data_end == 1))wr_end <= 1;else wr_end <= 0;  //change//
end
//col_cnt//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)col_cnt <= 0;else if (state == s_wr)col_cnt <= col_cnt +1;
end
//col_full//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)col_full <=0;else if (col_cnt == 511)col_full <=1;else  //change//col_full <= 0;
end
//wr_data//
always@(*)
begincase (burst_cnt)0 : wr_data <= 3;1 : wr_data <= 5;2 : wr_data <= 7;3 : wr_data <= 9;endcase
end
//wr_addr//
always@(*)
begincase (state)s_act : wr_addr <= row_addr;s_wr  : wr_addr <= {4'b000,col_cnt};s_pre  : wr_addr <= 13'b0_0100_0000_0000;endcase
end
//row_addr//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)row_addr <= 0;else if (col_full == 1)row_addr <= row_addr +1;
end
//wr_data_end//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)wr_data_end <= 0;else if (row_addr == 'd3 && col_cnt == 'd511)wr_data_end <= 1;else wr_data_end <= 0;
endendmodule

读模块代码:

module sdram_read(
sys_clk,
sys_rst_n,
ref_req,
rd_en,
rd_trig,//rd_data,
rd_addr,
rd_cmd,
bank_addr,
rd_end,
rd_req
);input 		sys_clk;
input 		sys_rst_n;
//input 		ref_end;
input 		ref_req;
input 		rd_trig;
input 		rd_en;//output reg  [5:0] 	rd_data;
output reg  [12:0]	rd_addr;
output reg  [3:0]    rd_cmd;
output      [1:0]    bank_addr;
output reg			    rd_end;
output reg		      rd_req;
//state//
localparam s_idle  = 5'b00001;
localparam s_req   = 5'b00010;
localparam s_act   = 5'b00100;
localparam s_rd    = 5'b01000;
localparam s_pre   = 5'b10000;
//cmd//
localparam PRE  = 4'b0010;
localparam AREF = 4'b0001;
localparam ACT  = 4'b0011;
localparam NOP  = 4'b0111;
localparam MSET = 4'b0000;
localparam WR   = 4'b0100;
localparam RD   = 4'b0101;reg cnt_act;
reg [1:0] burst_cnt;
reg [4:0] state;
reg [8:0] col_cnt;
reg col_full;
reg [13:0] row_addr;
reg rd_data_end;
reg rd_flag;assign bank_addr = 2'b00;//rd_req//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)rd_req <= 0;else if (rd_en == 1 && rd_req == 1)rd_req <= 0;else if (rd_trig == 1 || rd_end ==1 && rd_flag ==1)rd_req <= 1;
end//rd_flag//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)rd_flag <= 0;else if (rd_en ==1 && rd_flag ==0)rd_flag <= 1;else if (rd_data_end == 1)rd_flag <= 0;
end
//state//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)state <= s_idle;else case (state)s_idle:beginif (rd_req == 1 )state <= s_req;elsestate <= s_idle;ends_req:beginif (rd_en == 1 )state <= s_act;elsestate <= s_req;ends_act:beginif (cnt_act ==1 )state <= s_rd;else if ((rd_data_end == 1))state <= s_idle;elsestate <= s_act;ends_rd:beginif ((burst_cnt == 3 && ref_req ==1) || (rd_data_end == 1))state <= s_idle;else if (burst_cnt == 3 || col_full == 1)state <= s_pre;elsestate <= s_rd;ends_pre:beginif(rd_data_end == 1)state <= s_idle;elsestate<=s_act;enddefault: state <= s_idle;endcase
end
//cnt_act//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)cnt_act <= 0;else if (state == s_act)cnt_act <= cnt_act +1;
end
//burst_cnt//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)burst_cnt <= 0;else if (state == s_rd)burst_cnt <= burst_cnt +1;
end
//rd_cmd//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)rd_cmd <= NOP;else if (rd_en == 1)rd_cmd <= ACT;else if (cnt_act == 1)rd_cmd <= RD;else if ((burst_cnt == 3 || col_full == 1))rd_cmd <= PRE;elserd_cmd <= NOP;
end
//rd_end//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)rd_end <= 0;else if ((burst_cnt == 3 && ref_req ==1) || (rd_data_end == 1))rd_end <= 1;elserd_end <= 0;
end
//col_cnt//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)col_cnt <= 0;else if (state == s_rd)col_cnt <= col_cnt +1;
end
//col_full//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)col_full <=0;else if (col_cnt == 511)col_full <=1;elsecol_full <= 0;
end
rd_data//
//always@(*)
//begin
//	case (burst_cnt)
//		0 : rd_data <= 3;
//		1 : rd_data <= 5;
//		2 : rd_data <= 7;
//		3 : rd_data <= 9;
//	endcase
//end
//rd_addr//
always@(*)
begincase (state)s_act : rd_addr <= row_addr;s_rd  : rd_addr <= {4'b000,col_cnt};s_pre  : rd_addr <= 13'b0_0100_0000_0000;endcase
end
//row_addr//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)row_addr <= 0;else if (col_full == 1)row_addr <= row_addr +1;
end
//rd_data_end//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)rd_data_end <= 0;else if (row_addr == 'd3 && col_cnt == 'd511)rd_data_end <= 1;else rd_data_end <= 0;
endendmodule

顶层模块:

module sdram_top(
sys_clk,
sys_rst_n,
wr_trig,
rd_trig,sdram_clk,
sdram_cke,
sdram_cs_n,
sdram_ras_n,
sdram_cas_n,
sdram_we_n,
sdram_bank,
sdram_addr,
sdram_dqm,
sdram_dq
);input					sys_clk;
input					sys_rst_n;
input					wr_trig;
input					rd_trig;output				sdram_clk;
output				sdram_cke;
output				sdram_cs_n;
output				sdram_ras_n;
output				sdram_cas_n;
output				sdram_we_n;
output	reg [1:0]	sdram_bank;
output reg [12:0]	sdram_addr;
output	[1:0]	sdram_dqm;
inout  [15:0]	sdram_dq;reg [3:0] sdram_cmd;
assign {sdram_cs_n,sdram_ras_n,sdram_cas_n,sdram_we_n} = sdram_cmd;
assign sdram_dqm = 2'b00;
assign sdram_cke = 1'b1;
assign sdram_clk = ~sys_clk;//define//
wire [3:0] 	init_cmd;
wire [12:0] init_addr;
wire 			 	init_end;reg					ref_en;
wire				ref_req;
wire				ref_end;
wire	[3:0]	ref_cmd;
wire [12:0] ref_addr;reg					wr_en;
wire	[5:0]	wr_data;
wire [12:0]	wr_addr;
wire	[3:0]	wr_cmd;
wire	[1:0]	wr_bank_addr;
wire				wr_end;
wire				wr_req;reg					rd_en;
wire	[5:0]	rd_data;
wire [12:0]	rd_addr;
wire	[3:0]	rd_cmd;
wire	[1:0]	rd_bank_addr;
wire				rd_end;
wire				rd_req;//ARBIT_STATE//
localparam s_IDLE  = 5'b00001;
localparam s_ARBIT = 5'b00010;
localparam s_AREF  = 5'b00100;
localparam s_WR    = 5'b01000;
localparam s_READ  = 5'b10000;
reg [4:0] state;always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)state <= s_IDLE;else case (state)s_IDLE:beginif (init_end == 1)state <= s_ARBIT;elsestate <= s_IDLE;ends_ARBIT:beginif (ref_req == 1)state <= s_AREF;else if (wr_req == 1)state <= s_WR;else if (rd_req == 1)state <= s_READ;ends_AREF:beginif (ref_end == 1)state <= s_ARBIT;elsestate <= s_AREF;ends_WR:beginif (wr_end == 1)state <= s_ARBIT;elsestate <= s_WR;ends_READ:beginif (rd_end == 1)state <= s_ARBIT;elsestate <= s_READ;enddefault:state <= s_IDLE;endcase
end
//cmd//
localparam NOP   = 4'b0111; 
always@(*)begincase (state)s_IDLE:beginsdram_cmd <= init_cmd;sdram_addr <= init_addr;sdram_bank <= 2'b00;ends_AREF:beginsdram_cmd <= ref_cmd;sdram_addr <= ref_addr;sdram_bank <= 2'b00;ends_WR:beginsdram_cmd <= wr_cmd;sdram_addr <= wr_addr;sdram_bank <= wr_bank_addr;ends_READ:beginsdram_cmd <= rd_cmd;sdram_addr <= rd_addr;sdram_bank <= rd_bank_addr;enddefault:beginsdram_cmd <= NOP;sdram_addr <= 0;sdram_bank <= 2'b00;endendcase
end
assign sdram_dq = (state == s_WR)?wr_data:{16{1'bz}};
//ref_en//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)ref_en <= 0;else if (ref_en == 1 && ref_req == 1)ref_en <= 0;else if (state == s_AREF && ref_req == 1)ref_en <= 1;
end
//wr_en//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)wr_en <= 0;else if (wr_en == 1 && wr_req == 1)  //change//wr_en <= 0;else if (state == s_WR && wr_req == 1)wr_en <= 1;
end
//rd_en//
always@(posedge sys_clk or negedge sys_rst_n)
beginif (!sys_rst_n)rd_en <= 0;else if (rd_en == 1 && rd_req == 1)rd_en <= 0;else if (state == s_READ && rd_req == 1)rd_en <= 1;
endsdram_init init(.sys_clk(sys_clk),.sys_rst_n(sys_rst_n),.init_cmd(init_cmd),.init_addr(init_addr),.init_end(init_end)
);sdram_aref aref(.sys_clk(sys_clk),.sys_rst_n(sys_rst_n),.init_end(init_end),.ref_en(ref_en),.ref_req(ref_req),.ref_end(ref_end),.ref_cmd(ref_cmd),.ref_addr(ref_addr)
);sdram_write write(.sys_clk(sys_clk),.sys_rst_n(sys_rst_n),
//ref_end,.ref_req(ref_req),.wr_en(wr_en),.wr_trig(wr_trig),.wr_data(wr_data),.wr_addr(wr_addr),.wr_cmd(wr_cmd),.bank_addr(wr_bank_addr),.wr_end(wr_end),.wr_req(wr_req)
);sdram_read read(.sys_clk(sys_clk),.sys_rst_n(sys_rst_n),.ref_req(ref_req),.rd_en(rd_en),.rd_trig(rd_trig),//rd_data,.rd_addr(rd_addr),.rd_cmd(rd_cmd),.bank_addr(rd_bank_addr),.rd_end(rd_end),.rd_req(rd_req)
);endmodule

时序图仿真如下:

 

欢迎指出问题,一起讨论。


http://chatgpt.dhexx.cn/article/k3we5Brj.shtml

相关文章

基于FPGA的SDRAM控制器设计(一)

基于FPGA的SDRAM控制器设计&#xff08;一&#xff09; 1. SDRAM控制器整体框架2.UART_RX模块3.UART_TX模块4. RX与TX模块的整合5.需要注意的问题6.代码7.参考资料 1. SDRAM控制器整体框架 图1.1整体框架 PC端通过串口模块UART_RX发送读写命令以及数据到Cmd_encode模块&#xf…

基于FPGA的SDRAM控制器设计(1)

基于FPGA的SDRAM初始化配置 SDRAM简述SDRAM的引脚及作用SDRAM初始化时序控制SDRAM上电时序代码SDRAM测试模块的代码仿真测试结果参考文献总结 SDRAM简述 SDRAM&#xff08; Synchronous Dynamic Random Access Memory&#xff09;&#xff0c;同步动态随机存储器。同步是指 Me…

FPGA进阶(3):SDRAM读写控制器的设计与验证

文章目录 第50讲&#xff1a;SDRAM读写控制器的设计与验证理论部分设计与实现1. sdram_ctrlsdram_initsdram_a_refsdram_writesdram_readsdram_arbitsdram_ctrl 2. sdram_topfifo_ctrlsdram_top 3. uart_sdramuart_rxuart_txfifo_readuart_sdram 第50讲&#xff1a;SDRAM读写控…

SDRAM

简介、优缺点、历史 1、译为“同步动态随机存取内存”&#xff0c;区别于异步DRAM。SRAM是异步静态存储器。 2、同步(Synchronous)&#xff1a;与通常的异步 DRAM 不同&#xff0c; SDRAM 存在一个同步接口&#xff0c;其工作时钟的时钟频率与对应控制器(CPU/FPGA上的读写控制…

关于SDRAM存储器

一、对SDRAM的初步认识 1.1 什么是SDRAM SDRAM&#xff08;Synchronous Dynamic Random Access Memory&#xff09;&#xff0c;同步动态随机存取存储器。 同步&#xff1a;工作频率与对应控制器的系统时钟频率相同&#xff0c;且内存内部的命令以及数据的传输都以此为基准 …

内存控制器与SDRAM

内存接口概念&#xff1a; 通常ARM芯片内置的内存很少&#xff0c;要运行Linux&#xff0c;需要扩展内存。ARM9扩展内存使用SDRAM内存&#xff0c;ARM11使用 DDR SDRAM。S3C2440通常外接32位64MBytes的SDRAM&#xff0c;采用两片16位32M的SDRAM芯片&#xff0c;SDRAM芯片通过地…

SDRAM驱动篇之简易SDRAM控制器的verilog代码实现

在Kevin写的上一篇博文《SDRAM理论篇之基础知识及操作时序》中&#xff0c;已经把SDRAM工作的基本原理和SDRAM初始化、读、写及自动刷新操作的时序讲清楚了&#xff0c;在这一片博文中&#xff0c;Kevin来根据在上一篇博文中分析的思路来把写一个简单的SDRAM控制器。 我们在上一…

FPGA之SDRAM控制器设计(一)

MT48LC128M4A2 – 32 Meg x 4 x 4 banks是512M SRAM&#xff0c;总体概述如下图 分别从上电初始化&#xff0c;刷新&#xff0c;写&#xff0c;读四个部分进行设计&#xff0c;此外还包含主控状态机&#xff0c;一个顶层。 1&#xff1a;上电初始化 整体架构&#xff1a;从控…

内存控制器与SDRAM【赞】

原文链接&#xff1a;https://blog.csdn.net/qq_31216691/article/details/87115697 内存接口概念&#xff1a; 通常ARM芯片内置的内存很少&#xff0c;要运行Linux&#xff0c;需要扩展内存。ARM9扩展内存使用SDRAM内存&#xff0c;ARM11使用 DDR SDRAM。S3C2440通常外接32位6…

SDRAM 介绍

目录 1、名词解释 2、SDRAM 内部结构 3、SDRAM 外部信号描述 4、SDRAM 命令 4.1、COMMAND INHIBIT 4.2、NO OERATION 4.3、ACTIVE 4.4、LOAD MODE REGISTER (LMR) 4.5、READ 4.6、WRITE 4.7、PRECHARGE 4.8、BURST TERMINATE 4.9、REFRESH 4.9.1、AUTO REFRESH …

SDRAM控制器操作时序

此为学习http://dengkanwen.com/137.html整理的笔记&#xff0c;侵删&#xff01; SDRAM工作原理 内部的状态跳转图 我们所需关注的几个地方&#xff1a; 1&#xff09;粗黑线表示在该状态下会自动跳转到另一个状态&#xff0c;细黑线表示需要给命令才会跳转。 2&#xff09…

SDR SDRAM控制器设计

目录 前言 1、关于刷新 2、关于数据中心对齐 3、SDRAM芯片手册介绍 3.1SDRAM芯片的管脚 3.2 SDRAM指令集 3.3 模式寄存器 3.4 关于SDRAM上电初始化和装载模式寄存器 3.5 SDRAM刷新时序 3.6 关于写访问 3.7 关于突发访问 4、FPGA工程设计 4.1状态机设计 5、仿真测试…

【GD32】从零开始学GD32单片机高级篇——外部存储器控制器EXMC详解+SDRAM读写例程

目录 简介外部设备地址映射NOR和PSRAM的地址映射NAND/PC Card地址映射SDRAM地址映射 NOR/PSRAM控制器接口描述控制时序模式1模式2 NAND Flash或PC Card控制器接口描述控制时序 SDRAM控制器接口描述控制时序突发读操作突发写操作读写FIFO跨边界读写操作低功耗模式自刷新模式掉电…

初识内存控制器和SDRAM【一文了解】

原文链接&#xff1a;https://blog.csdn.net/qq_36243942/article/details/85596249 目录 1.引入内存控制器 2.不同位宽内存设备之间的连接 3.如何确定芯片的访问地址 4.分析读写NOR FLASH的读写时序 5.SDRAM初识 6.编程读/写 SDRAM 附录&#xff1a;源代码 1.引入内存控制器 我…

存储控制器(SDRAM操作)

什么是存储控制器 2440是32位单片机&#xff0c;进行数据访问时通过32位地址访问。 CPU发出32位地址信号给存储控制器&#xff0c;存储控制器根据地址信号设置片选信号及地址总线&#xff0c;将相应数据通过数据总线传回存储控制器&#xff0c;存储控制器将收到的数据以字节为…

数字IC实践项目(2)——高速SDRAM控制器的设计与综合(入门级工程项目)

数字IC实践项目&#xff08;2&#xff09;—高速SDRAM控制器的设计与综合&#xff08;入门级工程项目&#xff09; 写在前面的话项目简介和学习目的SDRAM简介SDRAM控制器简介完整项目框图SDRAM控制器项目框图SDRAM初始化模块SDRAM自动刷新模块SDRAM写模块SDRAM读模块SDRAM仲裁机…

SDRAM控制器——仲裁模块的实现

前面一文中&#xff0c;我们已经对SDRAM的上电初始化、自动刷新以及突发读写进行了学习。 本文跟着大佬学习SDRAM中的仲裁模块。 仲裁机制 仲裁&#xff08;arbit&#xff09;&#xff1a;在FPGA中&#xff0c;当多个source源同时发出请求&#xff0c;容易导致操作冲突&#x…

SDRAM读写控制器

第1节 –作者&#xff1a;小黑同学 本文为明德扬原创及录用文章&#xff0c;转载请注明出处&#xff01; 1.1 总体设计 1.1.1 概述 同步动态随机存取内存&#xff08;synchronous dynamic randon-access menory&#xff0c;简称SDRAM&#xff09;是有一个同步接口的动态随…

FPGA综合项目——SDRAM控制器

FPGA综合项目——SDRAM控制器 目录 1.整体框架2.串口接收模块3.接收模块测试仿真4.串口发送模块5.发送模块测试仿真6.SDRAM基础学习7.SDRAM顶层模块8.SDRAM初始化模块设计与仿真测试9.自动刷新模块设计与测试10.写模块设计与测试11.读模块设计与仿真测试12.通信处理模块13.顶层…

细说SDRAM控制器

SDRAM的基本概念 SDRAM凭借其极高的性价比&#xff0c;广泛应用于高速数据存储、实时图像处理等设计当中&#xff0c;但是相对于SRAM、FIFO等其他存储器件&#xff0c;SDRAM的控制相对复杂。虽说是复杂&#xff0c;但也不代表没办法实现&#xff0c;仔细梳理一下&#xff0c;发…