本文不包含任何代码,所有注意事项都是我在学习使用SPI对SD卡进行读写过程中遇到的一些问题及解决方法。
- 供电电压!!!!
供电电压是首先要注意的。我在最开始使用的时候,出现SD卡初始化正常(CMD0、CMD8等命令都正常回复)但无法进行读写、4G的SD卡可以识别但16G、32G无法识别,最后检查就是供电不足引起的。 - 命令全都是10进制
比如CMD55的55是十进制的55,开始我老是写成0x55。 - CMD0需要加0x95作为校验
- CMD8需要加0x1aa作为参数,需要加0x87作为校验
- ACMD前要先发送CMD55,等待CMD55响应且需要发送8个填充时钟,否则会出现异常
- 初始化过程中的ACMD44需要循环发送直到不处于空闲状态(R1=0),否则发送CMD58出现R1=0x05
- 擦除块时,使用CMD32设置擦除起始地址,使用CDM33设置擦除结束地址,CMD38开始擦除。
- ACMD41的参数中需要将HCS位置1
这一点我也不明白为什么,反正置1就对了,置0就不行。有知道的欢迎告诉我。 - SPI和SDIO模式的响应完全不同
别看错了,如果你看的是官方SD卡协议,直接从第7章SPI Mode开始看吧。 - 发送命令后SD卡有时很久才回复
有时就是要等很久才回复,while(1)慢慢等吧。 - 进行读或写后不能马上进行下一步操作
我采用的方式是读写后不断发送CMD58,直到返回正常值,才进行下一步操作。但有时可以观察到发送第一个CMD58就返回正常值了,有时又需要很多次才可以。 - 对于SDSC卡,读写地址为块编号*512;对于SDHC和SDXC读写地址为块编号
最开始使用的是ST提供的SD卡驱动文件(stm32_eval_spi_sd.c),到最后文件系统都移植上去了,但单片机创建文件后把SD卡插上电脑,电脑就是找不到文件。原来是ST提供的驱动文件中,块地址乘了512,但对于现在常见的SDHC,不需要这么做,读写命令中直接使用块编号就可以了。
反正初始化过程看懂这张图就可以了。
|