你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

使用 stm32f7x单片机对sdram 读写 ?

[复制链接]
hpdell 提问时间:2016-10-23 12:34 /
悬赏4ST金币未解决
大虾们好,最近在使用 stm32f7x单片机对sdram 读写 ?? 出现如下情况:

图片1,读写正常,单个字节读写,见图片描述

1.png

一写一读正常,这说明硬件木有什么问题吧 ??

下面的连续写或者连续读都不行,图片如下:
大神们看看是哪里不对,SDRAM 我是使用两片 16位组合成32位的
a、 不行-1.png

b、 不行-2.png

c、上述a或者b操作后,如果不使用 static void MPU_Config(void) 这个函数,那么再单独进行单个字节的读写也不正常,这又是为何啊 ???







软件设置如下:


/**
  * @brief  Configure the MPU attributes as Write Back for SDRAM.
  * @note   The Base Address is 0xC0000000.
  *         The Region Size is 32MB, it is related to SDRAM memory size.
  * @param  None
  * @retval None
  */
static void MPU_Config(void)
{
  MPU_Region_InitTypeDef MPU_InitStruct;

  /* Disable the MPU */
  HAL_MPU_Disable();

  /* Configure the MPU attributes as WB for SDRAM */
  MPU_InitStruct.Enable = MPU_REGION_ENABLE;
  MPU_InitStruct.BaseAddress = SDRAM_BASE_ADDR;   // 0xC0000000;
  MPU_InitStruct.Size = MPU_REGION_SIZE_32MB;
  MPU_InitStruct.AccessPermission = MPU_REGION_FULL_ACCESS;
  MPU_InitStruct.IsBufferable = MPU_ACCESS_BUFFERABLE;
  MPU_InitStruct.IsCacheable = MPU_ACCESS_CACHEABLE;
  MPU_InitStruct.IsShareable = MPU_ACCESS_NOT_SHAREABLE;
  MPU_InitStruct.Number = MPU_REGION_NUMBER0;
  MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL0;
  MPU_InitStruct.SubRegionDisable = 0x00;
  MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_ENABLE;

  HAL_MPU_ConfigRegion(&MPU_InitStruct);

  /* Enable the MPU */
  HAL_MPU_Enable(MPU_PRIVILEGED_DEFAULT);
}



// 执行外部存储器SDRAM的初始化序列
/**
  * @brief  Perform the SDRAM external memory initialization sequence
  * @param  hsdram: SDRAM handle
  * @param  Command: Pointer to SDRAM command structure
  * @retval None
  */
void BSP_SDRAM_Initialization_Sequence(SDRAM_HandleTypeDef *hsdram, FMC_SDRAM_CommandTypeDef *Command)
{
  __IO uint32_t tmpmrd =0;
  /* Step 1:  Configure a clock configuration enable command */
  Command->CommandMode = FMC_SDRAM_CMD_CLK_ENABLE;
  Command->CommandTarget = FMC_SDRAM_CMD_TARGET_BANK1;
  Command->AutoRefreshNumber = 1;
  Command->ModeRegisterDefinition = 0;

  /* Send the command */
  HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

  /* Step 2: Insert 100 us minimum delay */
  /* Inserted delay is equal to 1 ms due to systick time base unit (ms) */
  HAL_Delay(1);

  /* Step 3: Configure a PALL (precharge all) command */
  Command->CommandMode = FMC_SDRAM_CMD_PALL;
  Command->CommandTarget = FMC_SDRAM_CMD_TARGET_BANK1;
  Command->AutoRefreshNumber = 1;
  Command->ModeRegisterDefinition = 0;

  /* Send the command */
  HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

  /* Step 4 : Configure a Auto-Refresh command */
  Command->CommandMode = FMC_SDRAM_CMD_AUTOREFRESH_MODE;
  Command->CommandTarget = FMC_SDRAM_CMD_TARGET_BANK1;
  Command->AutoRefreshNumber = 8;
  Command->ModeRegisterDefinition = 0;

  /* Send the command */
  HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

  /* Step 5: Program the external memory mode register */
  tmpmrd = (uint32_t)SDRAM_MODEREG_BURST_LENGTH_1          |
                     SDRAM_MODEREG_BURST_TYPE_SEQUENTIAL   |
                     SDRAM_MODEREG_CAS_LATENCY_2           |
                     SDRAM_MODEREG_OPERATING_MODE_STANDARD |
                     SDRAM_MODEREG_WRITEBURST_MODE_SINGLE;

  Command->CommandMode = FMC_SDRAM_CMD_LOAD_MODE;
  Command->CommandTarget = FMC_SDRAM_CMD_TARGET_BANK1;
  Command->AutoRefreshNumber = 1;
  Command->ModeRegisterDefinition = tmpmrd;

  /* Send the command */
  HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);


  /* Step 6: Set the refresh rate counter */
  /* (15.62 us x Freq) - 20 */
  /* Set the device refresh counter */
  hsdram->Instance->SDRTR |= ((uint32_t)((1292)<< 1));      // 1292


}


/* FMC initialization function */
void MX_FMC_Init(void)
  /** Perform the SDRAM1 memory initialization sequence
  */
  hsdram1.Instance = FMC_SDRAM_DEVICE;                        //SDRAM在BANK5,6
  /* hsdram1.Init */
  /* 两片 MT48LC32M16(数据宽度16位) 组合成为 一片 MT48LC32M32(即把两片16位的组合成32位宽的)*/

  hsdram1.Init.SDBank = FMC_SDRAM_BANK1;                          //SDRAM接在BANK5上
  hsdram1.Init.ColumnBitsNumber = FMC_SDRAM_COLUMN_BITS_NUM_10;  // 列地址线数目
  hsdram1.Init.RowBitsNumber = FMC_SDRAM_ROW_BITS_NUM_13;       // 行地址线数目
  hsdram1.Init.MemoryDataWidth = FMC_SDRAM_MEM_BUS_WIDTH_32;
  hsdram1.Init.InternalBankNumber = FMC_SDRAM_INTERN_BANKS_NUM_4;       //一共4个BANK
  hsdram1.Init.CASLatency = FMC_SDRAM_CAS_LATENCY_2;    //CAS为3
  hsdram1.Init.WriteProtection = FMC_SDRAM_WRITE_PROTECTION_DISABLE;
  hsdram1.Init.SDClockPeriod = FMC_SDRAM_CLOCK_PERIOD_2;  
  hsdram1.Init.ReadBurst = FMC_SDRAM_RBURST_ENABLE;       // 使能突发读
  hsdram1.Init.ReadPipeDelay = FMC_SDRAM_RPIPE_DELAY_0; // 定义在CAS个延时后在等待多少个HCLK时钟才读取数据

  /* SdramTiming */

#if  1
  SdramTiming.LoadToActiveDelay = 2;      // TMDR 加载模式寄存器到激活时间的延迟为2个时钟周期
  SdramTiming.ExitSelfRefreshDelay = 6;   // TXSR 退出自刷新延迟为x个时钟周期
  SdramTiming.SelfRefreshTime = 4;        // TRAS 自刷新时间为x个时钟周期
  SdramTiming.RowCycleDelay = 6;          // TRC  行循环延迟为x个时钟周期
  SdramTiming.WriteRecoveryTime = 2;      // TWR  恢复延迟为x个时钟周期
  SdramTiming.RPDelay = 2;                // TRP  行预充电延迟为x个时钟周期
  SdramTiming.RCDDelay = 2;               // TRCD 行到列延迟为x个时钟周期

#else
  SdramTiming.LoadToActiveDelay = 3;      // TMDR 加载模式寄存器到激活时间的延迟为2个时钟周期
  SdramTiming.ExitSelfRefreshDelay = 7;   // TXSR 退出自刷新延迟为x个时钟周期
  SdramTiming.SelfRefreshTime = 5;        // TRAS 自刷新时间为x个时钟周期
  SdramTiming.RowCycleDelay = 7;          // TRC  行循环延迟为x个时钟周期
  SdramTiming.WriteRecoveryTime = 3;      // TWR  恢复延迟为x个时钟周期
  SdramTiming.RPDelay = 3;                // TRP  行预充电延迟为x个时钟周期
  SdramTiming.RCDDelay = 3;               // TRCD 行到列延迟为x个时钟周期

#endif  

  if (HAL_SDRAM_Init(&hsdram1, &SdramTiming) != HAL_OK)
  {
    Error_Handler();
  }

  /* Program the SDRAM external device */
  BSP_SDRAM_Initialization_Sequence(&hsdram1, &SDRAMcommand);   // 执行外部存储器SDRAM的初始化序列

}


MT48LC32M16 芯片截图
2.png

详细的 MT48LC32M16资料如下: MT48LC32M16 datasheet.pdf (1.78 MB, 下载次数: 5)

收藏 1 评论20 发布时间:2016-10-23 12:34

举报

20个回答
hpdell 最优答案 回答时间:2016-10-29 22:21:50
已经搞定了,吧两个芯片更换为一模一样的就可以了

评分

参与人数 1ST金币 +2 收起 理由
zero99 + 2

查看全部评分

anywill 回答时间:2016-10-26 07:20:13
sdram 太高深,暂时还没接触,支持一下
无薪税绵 回答时间:2016-10-26 08:19:15
这个真的不会,只能帮楼主加人气了。
zhoupxa 回答时间:2016-10-26 08:50:22
遇到这种问题,建议用如此测试:

1.原厂例程+评估板
2.原厂例程+自制板
3.自写程序+评估板
4.自写程序+自制板

并对照原厂和自己的软件、硬件设计,以找出问题所在
当然不必全部测试
z258121131 回答时间:2016-10-26 09:16:14
顶楼主,学习啦。
haifeng-388081 回答时间:2016-10-26 09:49:28

顶楼主,学习啦。
wofei1314 回答时间:2016-10-26 11:06:42
2片SDRAM么?
五哥1 回答时间:2016-10-26 12:34:57
帮楼主顶一下
wudianjun2001 回答时间:2016-10-26 15:25:22
不会,帮顶
STM32LEARN 回答时间:2016-10-26 15:57:01
帮顶   
hpdell 回答时间:2016-10-26 16:39:27

是的

两片 MT48LC32M16(两片16bit)组合成 MT48LC32M32(32bit)
zbber 回答时间:2016-10-26 17:07:53
顶楼主,学习啦
高二毛 回答时间:2016-10-26 17:32:20
学习了。。。。
高二毛 回答时间:2016-10-26 17:34:14
刚看了看代码,你吧printf放到你连续的外面试试?printf毕竟速度最慢,操作内存是很快的。
wofei1314 回答时间:2016-10-26 19:42:24
hpdell 发表于 2016-10-26 16:39
是的

两片 MT48LC32M16(两片16bit)组合成 MT48LC32M32(32bit)

这个确实比较麻烦,我还没试过
12下一页

所属标签

相似问题

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版