【发布时间】:2022-08-03 18:34:21
【问题描述】:
最近买了一块用于STM32F746的Nucleo-144开发板。对于我正在进行的项目,我需要获得一致的 >3 MB/s 写入 SD 卡的速度。使用 STM32CubeIDE,我已经能够让 SD 1 位模式与 FatFS 在轮询和 DMA 模式下全速工作。但是,切换到 SD 4 位模式后,我开始在读取时收到很多与错误数据 CRC 相关的 IO 错误。
细节
在 SD 4 位轮询模式下,我什至无法正确处理单个块读取。调用 f_mount 返回一个 IO 错误,调试它进一步显示第一次调用 HAL_SD_ReadBlocks,读取扇区 0,失败,错误代码为 SDMMC_ERROR_DATA_CRC_FAIL:
检查从卡中读取的 512 字节数据缓冲区显示数据至少部分完整,其中包含您希望在第一个扇区中看到的一些字符串:
重要的,此缓冲区以完全相同的方式损坏在每次运行软件之间。如果是某种电气干扰问题,我希望看到不同的字节被损坏,但我没有。运行之间的缓冲区是相同的。切换回 1 位模式并检查数据缓冲区,显然它的状态要好得多。 4 位缓冲区显然有很多损坏的位和完全丢失的位,抵消了一切。 4 位模式主要读取垃圾,但始终是相同的垃圾。
我尝试过的
- 轮询和 DMA 模式。
- 两者都以类似的方式失败,尽管调试 DMA 更加困难。
- 将 SDMMCCLK 时钟分频器一直降低到 255,它会达到最高分频器(和最低时钟速度)。
- 在我较旧的、更便宜的 Lexar SD 卡上,这种模式下的读/写工作完美无缺(尽管速度很慢)。
- 在我更新、更昂贵的三星 SD 卡读/写仍然失败,并出现
SDMMC_ERROR_DATA_CRC_FAIL错误。数据缓冲区看起来更加完整,但它显然仍然是垃圾数据。
- 传输将 GPIO 上拉应用于所有 SD 引脚(时钟除外)以及不带上拉。
- 没有变化,至少据我所知。
- 使用多个不同的 SD 卡。
- 具体来说,是 Lexar “300x” 32 GB 卡和三星 “EVO Plus” 128 GB 卡。
- 如前所述,降低时钟速度可以让我的两张卡中的一张工作。
- 但是,即使在最低速度下,我的更高质量卡在第一次读取时仍然失败。
接线
不确定这有多相关,但我想我会为了完成而将它包括在内。这就是我在原型设计时连接 SD 卡的方式。所有电缆的长度都相同,但即使在如此短的距离内,它们可能也会相互干扰?我还使用 Adafruit SD 卡分线适配器进行测试。
SD Card GPIO Pin CLK PC12 D0 PC8 CMD PD2 D3 PC11 D1 PC9 D2 PC10 概括
似乎对于某些卡,即使在较低的时钟速度下,IO 错误仅在 SD 4 位模式下非常常见。在更高的时钟速度下,我能够测试的所有卡都开始在 4 位模式下出现 IO 错误。然而,在 SD 1 位模式下,即使在最大时钟速度下,我也能够正常读写。
我想利用 4 位模式来获得更快的速度。我究竟做错了什么?它是电气的吗,例如需要更强的上拉电阻或更短的电线?谢谢,我真的很感激!
-
我只是在这里吐口水,但也许你的别针处于错误的模式? (QSPI 要求引脚从驱动切换到读取)。另一个想法是您没有为 SSD 卡提供足够的电源以在 QSPI 模式下将其信号驱动给您?
-
我有几个建议给你: - 尝试将数据模式写入 SD 卡(例如 0xAAAAAAAA 0xCCCCCCCC 0x55555555 0x33333333)然后使用 4 位模式回读。 - 检查命令部分和数据部分是否全部使用 4 位。如果是这样,请尝试将数据部分仅设为 4 位
标签: embedded storage stm32 hardware