EDK软件的memory and memory controller中有一个xps multi-channel external memory controller(sram/flash)的IP,用来外接sram/flash存储器,它和51单片机的外部总线时序一样,有单独的数据总线,地址总线和读写片选控制线;这样,连接基于并行总线的外设IC也很方便了。
下面我们做一个sram读写的范例,来介绍如何配制和使用xps_mch_emc IP核。
以下是基于EDK 12.2版本,SRAM为IS61LV6416(64K×16bit异步sram)。
先建一个EDK工程,添加串口外设,将串口作为print的输出接口,添加xps_mch_emc IP,弹出ip配制窗口
红圈处设置如上图,其它设置黙认。
连接IP,引出端口,分配地址,如下图
打开UCF文件,分配管脚
注意:当数据宽度为8位时,SRAM的A0对应于IP的A0,SRAM的A1对应于IP的A1……;
当数据宽度为16位时,SRAM的A0对应于IP的A1,SRAM的A1对应于IP的A2……;(SRAM_A0不接)
当数据宽度为32位时,SRAM的A0对应于IP的A2,SRAM的A1对应于IP的A3……(SRAM_A0、SRAM_A1不接);
但由于EDK的数据位是倒序的,因此
当数据宽度为16位时,SRAM的A0对应于IP的A30,SRAM的A2对应于IP的A28……;
UCF文件如下:
#addr a0~a15
#Net xps_mch_emc_0_Mem_A_pin<31> LOC=; 16位宽度的总线,A0不接
Net xps_mch_emc_0_Mem_A_pin<30> LOC=J7; #SRAM_A0
Net xps_mch_emc_0_Mem_A_pin<29> LOC=L3;
Net xps_mch_emc_0_Mem_A_pin<28> LOC=L4;
Net xps_mch_emc_0_Mem_A_pin<27> LOC=F3;
Net xps_mch_emc_0_Mem_A_pin<26> LOC=F4;
Net xps_mch_emc_0_Mem_A_pin<25> LOC=E3;
Net xps_mch_emc_0_Mem_A_pin<24> LOC=U2;
Net xps_mch_emc_0_Mem_A_pin<23> LOC=E1;
Net xps_mch_emc_0_Mem_A_pin<22> LOC=F2;
Net xps_mch_emc_0_Mem_A_pin<21> LOC=F1;
Net xps_mch_emc_0_Mem_A_pin<20> LOC=H2;
Net xps_mch_emc_0_Mem_A_pin<19> LOC=R1;
Net xps_mch_emc_0_Mem_A_pin<18> LOC=R2;
Net xps_mch_emc_0_Mem_A_pin<17> LOC=T1;
Net xps_mch_emc_0_Mem_A_pin<16> LOC=T2;
Net xps_mch_emc_0_Mem_A_pin<15> LOC=U1; #SRAM_A15
#data d0~d15
Net xps_mch_emc_0_Mem_DQ_pin<15> LOC=N2;
Net xps_mch_emc_0_Mem_DQ_pin<14> LOC=N1;
Net xps_mch_emc_0_Mem_DQ_pin<13> LOC=M2;
Net xps_mch_emc_0_Mem_DQ_pin<12> LOC=L2;
Net xps_mch_emc_0_Mem_DQ_pin<11> LOC=L1;
Net xps_mch_emc_0_Mem_DQ_pin<10> LOC=K2;
Net xps_mch_emc_0_Mem_DQ_pin<9> LOC=J1;
Net xps_mch_emc_0_Mem_DQ_pin<8> LOC=J2;
Net xps_mch_emc_0_Mem_DQ_pin<7> LOC=F5;
Net xps_mch_emc_0_Mem_DQ_pin<6> LOC=G4;
Net xps_mch_emc_0_Mem_DQ_pin<5> LOC=G5;
Net xps_mch_emc_0_Mem_DQ_pin<4> LOC=H3;
Net xps_mch_emc_0_Mem_DQ_pin<3> LOC=J4;
Net xps_mch_emc_0_Mem_DQ_pin<2> LOC=J3;
Net xps_mch_emc_0_Mem_DQ_pin<1> LOC=J6;
Net xps_mch_emc_0_Mem_DQ_pin<0> LOC=K3;
###############################
Net xps_mch_emc_0_Mem_BEN_pin<1> LOC=N18; #SRAM的UB
Net xps_mch_emc_0_Mem_BEN_pin<0> LOC=N17; #SRAM的LB
Net xps_mch_emc_0_Mem_CEN_pin<0> LOC=P1;
Net xps_mch_emc_0_Mem_OEN_pin<0> LOC=K5;
Net xps_mch_emc_0_Mem_WEN_pin LOC=H1;
保存UCF文件,点击updatebitstream生成bit和xparameters.h文件
在test_memory文件中输入如下代码
#define RAM XPAR_EMC_0_MEM0_BASEADDR // XPAR_EMC_0_MEM0_BASEADDR是xparameters.h中生成的宏,定义的SRAM 基地址
//====================================================
int main (void) {
Xuint32 addr;
Xuint16 i,dat;
Xuint8 status=0;
print("-- Entering main() --\r\n");
// print("字节读写测试\r\n");
//
// //write
// addr=0;
// for(i=0;i<0xfffe;i++)
// {
// *(volatile Xuint8 *)(RAM+addr) = i;
// addr += 1;
// }
//
// //read
// addr=0;
// for(i=0;i<0xfffe;i++)
// {
// dat = *(volatile Xuint8 *)(RAM+addr);
// addr += 1;
// if(dat != i)
// {
// xil_printf("addr =0x%x,dat=0x%x,i=0x%x \r\n",addr,dat,i);
// status |= 0x1;
// break;
// }
// }
print("字读写测试\r\n");
//write
addr=0;
for(i=0;i<0xfffe;i++)
{
*(volatile Xuint16 *)(RAM+addr) = i;
addr += 2; //16位的地址要加2
}
//read
addr=0;
for(i=0;i<0xfffe;i++)
{
dat = *(volatile Xuint16 *)(RAM+addr);
addr += 2; //16位的地址要加2
if(dat != i)
{
xil_printf("addr =0x%x,dat=0x%x,i=0x%x \r\n",addr,dat,i);
status |= 0x2;
break;
}
}
if(status == 1)
print("字节读写测试失败!\r\n");
else if(status == 2)
print("字读写测试失败!\r\n");
else if (status == 3)
print("字节和字读写测试失败!\r\n");
else if (status == 0)
print("字节和字读写测试成功!\r\n");
print("-- Exiting main() --\r\n");
return 0;
}
再点击updatebitstream,并将生成的bit down到FPGA,查看串口终端输出信息如下:
附:
SRAM IP时序配制说明
用户3829303 2016-6-7 21:23
用户1501897 2013-4-29 12:34
用户417961 2012-3-30 20:53
用户251222 2011-1-6 11:25