zoukankan      html  css  js  c++  java
  • SPI模式下MCU对SD卡的控制及操作命令(转)

    源:SPI模式下MCU对SD卡的控制及操作命令

    一、前言

            SD 卡有两个可选的通讯协议:SD 模式和 SPI模式 SD 模式是SD 卡标准的读写方式,但是在选用SD 模式时,往往需要选择带有SD 卡控制器接口的 MCU,或者必须加入额外的SD卡控制单元以支持SD 卡的读写 然而,大多数MCU都没有集成SD 卡控制器接口,若选用SD 模式通讯就无形中增加了产品的硬件成本。在SD卡数据读写时间要求不是很严格的情况下, 选用 SPI模式可以说是一种最佳的解决方案 因为在 SPI模式下,通过四条线就可以完成所有的数据交换,并且目前市场上很多MCU都集成 有现成的SPI接口电路,采用 SPI模式对 SD卡进行读写操作可大大简化硬件电路的设计 

    二、硬件电路实现

            以NXP的LPC2210 ARM7MCU为例,下图是周立功开发的实现板电路

    这里,将LPC2210MCU的SPI0用于SD卡的控制和数据读写。对SPI0的两个数据线加了上拉电阻以便于MMC卡兼容。

    卡供电采用了可控方式,通过GPIO口控制MOS管对其进行供电。

    卡检测电路也使用GPIO口实现。通过读GPIO口数据,检查卡是否写保护和完全插入。

    具体内容可以参考周立功的说明书,百度文库里边有

    image

    三、SD卡物理接口

    我们看到的SD卡一包如下所示,包含9个引脚和一个写保护开关:

    image

    其引脚定义如下:

     image

    注:1.  S:电源;I:输入;O:推挽输出;PP:推挽I/O。         2.  扩展的DAT线(DAT1 ~ DAT3)在上电后处于输入状态。它们在执行SET_BUS_WIDTH命令后作为DAT线操作。当不使用DAT1 ~ DAT3 线时,主机应使自己的DAT1~DAT3线处于输入模式。这样定义是为了与MMC卡保持兼容。

          3.  上电后,这条线为带 50KΩ上拉电阻的输入线(可以用于检测卡是否存在或选择 SPI 模式) 。用户可以在正常的数据传输中用 SET_CLR_CARD_DETECT(ACMD42)命令断开上拉电阻的连接。MMC卡的该引脚在SD模式下为保留引脚,在SD模式下无任何作用。  4.  MMC卡在SD模式下为:I/O/PP/OD。  5.  MMC卡在SPI模式下为:I/PP。

          

    四、对SD卡的控制流程

    1、SD卡的SPI工作模式

    SD 卡在上电初期自动进入SD 总线模式,在此模式下向 SD 卡发送复位命令CMD0 。如果SD卡在接收复位命令过程中CS低电平有效,则进入SPI模式,否则工作在SD 总线模式。

    下边是插入SD卡,并初始化为SPI模式的流程图:(至于CMD××究竟是什么样的命令,本文最后会附上

    image

    在复位成功之后可以通过CMD55和ACMD41 判断当前电压是否在工作范围内 主机还可以继续通过CMD10读取SD 卡的CID寄存器,通过CMD16 设置数据 Block长度,通过CMD9 读取卡的 CSD寄存器 从CSD 寄存器中,主机可获知卡容量,支持的命令集等重要参数。

    2、数据块的读写

    完成SD 卡的初始化之后即可进行它的读写操作 SD卡的读写操作都是通过发送 SD 卡命令完成的SPI总线模式支持单块(CMD24)和多块(CMD25)写操作,多块操作是指从指定位置开始写下去,直到SD 卡收到一个停止命令CMD12才停止 单块写操作的数据块长度只能是512 字节 单块写入时,命令为CMD24,当应答为0时说明可以写入数据,大小为512 字节 SD 卡对每个发送给自己的数据块都通过一个应答命令确认,它为1个字节长,当低 5位为00101 时,表明数据块被正确写入SD 卡     在需要读取SD 卡中数据的时候,读SD卡的命令字为CMD17,接收正确的第一个响应命令字节为0xFE,随后是512 个字节的用户数据块,最后为2 个字节的CRC验证码    可见,读写SD 卡的操作都是在初始化后基于 SD 卡命令和响应完成操作的,写、读 SD 卡的程序流程图如下所示  :

    (1)写SD卡流程

    image

    (2)读SD卡流程

    image

    五、SD卡的操作命令集合

    对SD卡的操作就靠这些命令来实现的。一下命令来自周立功的SD/MMC中间件。我查了好多地方都只显示CMD0、CMD1之类的东西,而没人说这些东西是什么。就贴到这里供参考,这也是我写这个博客的目的,因为这些命令我找了好久的。关于SD,我一句操作代码都没贴。。。

    /* 命令响应定义 define command's response */
    #define R1 1
    #define R1B 2
    #define R2 3
    #define R3 4
    
    /**********************************************
    
         SD卡SPI模式下命令集
    
    **********************************************/
    
    /******************************** 基本命令集 Basic command set **************************/
    /* 复位SD 卡 Reset cards to idle state */
    #define CMD0 0
    #define CMD0_R R1
    
    /* 读OCR寄存器 Read the OCR (MMC mode, do not use for SD cards) */
    #define CMD1 1
    #define CMD1_R R1
    
    /* 读CSD寄存器 Card sends the CSD */
    #define CMD9 9
    #define CMD9_R R1
    
    /* 读CID寄存器 Card sends CID */
    #define CMD10 10
    #define CMD10_R R1
    
    /* 停止读多块时的数据传输 Stop a multiple block (stream) read/write operation */
    #define CMD12 12
    #define CMD12_R R1B
    
    /* 读 Card_Status 寄存器 Get the addressed card's status register */
    #define CMD13 13
    #define CMD13_R R2
    
    /***************************** 块读命令集 Block read commands **************************/
    
    /* 设置块的长度 Set the block length */
    #define CMD16 16
    #define CMD16_R R1
    
    /* 读单块 Read a single block */
    #define CMD17 17
    #define CMD17_R R1
    
    /* 读多块,直至主机发送CMD12为止 Read multiple blocks until a CMD12 */
    #define CMD18 18
    #define CMD18_R R1
    
    /***************************** 块写命令集 Block write commands *************************/
    /* 写单块 Write a block of the size selected with CMD16 */
    #define CMD24 24
    #define CMD24_R R1
    
    /* 写多块 Multiple block write until a CMD12 */
    #define CMD25 25
    #define CMD25_R R1
    
    /* 写CSD寄存器 Program the programmable bits of the CSD */
    #define CMD27 27
    #define CMD27_R R1
    
    /***************************** 写保护 Write protection *****************************/
    /* Set the write protection bit of the addressed group */
    #define CMD28 28
    #define CMD28_R R1B
    
    /* Clear the write protection bit of the addressed group */
    #define CMD29 29
    #define CMD29_R R1B
    
    /* Ask the card for the status of the write protection bits */
    #define CMD30 30
    #define CMD30_R R1
    
    /***************************** 擦除命令 Erase commands *******************************/
    /* 设置擦除块的起始地址(只用于SD卡) Set the address of the first write block to be erased(only for SD) */
    #define CMD32 32
    #define CMD32_R R1
    
    /* 设置擦除块的终止地址(只用于SD卡) Set the address of the last write block to be erased(only for SD) */
    #define CMD33 33
    #define CMD33_R R1
    
    /* 设置擦除块的起始地址(只用于MMC卡) Set the address of the first write block to be erased(only for MMC) */
    #define CMD35 35
    #define CMD35_R R1
    
    /* 设置擦除块的终止地址(只用于MMC卡) Set the address of the last write block to be erased(only for MMC) */
    #define CMD36 36
    #define CMD36_R R1
    
    /* 擦除所选择的块 Erase the selected write blocks */
    #define CMD38 38
    #define CMD38_R R1B
    
    /***************************** 锁卡命令 Lock Card commands ***************************/
    /* 设置/复位密码或上锁/解锁卡 Set/reset the password or lock/unlock the card */
    #define CMD42 42
    #define CMD42_R    R1B
    /* Commands from 42 to 54, not defined here */
    
    /***************************** 应用命令 Application-specific commands ****************/
    /* 禁止下一个命令为应用命令  Flag that the next command is application-specific */
    #define CMD55 55
    #define CMD55_R R1
    
    /* 应用命令的通用I/O  General purpose I/O for application-specific commands */
    #define CMD56 56
    #define CMD56_R R1
    
    /* 读OCR寄存器  Read the OCR (SPI mode only) */
    #define CMD58 58
    #define CMD58_R R3
    
    /* 使能或禁止 CRC Turn CRC on or off */
    #define CMD59 59
    #define CMD59_R R1
    
    /***************************** 应用命令 Application-specific commands ***************/
    /* 获取 SD Status寄存器 Get the SD card's status */
    #define ACMD13 13
    #define ACMD13_R R2
    
    /* 得到已写入卡中的块的个数 Get the number of written write blocks (Minus errors ) */
    #define ACMD22 22
    #define ACMD22_R R1
    
    /* 在写之前,设置预先擦除的块的个数 Set the number of write blocks to be pre-erased before writing */
    #define ACMD23 23
    #define ACMD23_R R1
    
    /* 读取OCR寄存器 Get the card's OCR (SD mode) */
    #define ACMD41 41
    #define ACMD41_R R1
    
    /* 连接/断开CD/DATA[3]引脚上的上拉电阻 Connect or disconnect the 50kOhm internal pull-up on CD/DAT[3] */
    #define ACMD42 42
    #define ACMD42_R R1
    
    /* 读取SCR寄存器 Get the SD configuration register */
    #define ACMD51 51
    #define ACMD51_R R1
  • 相关阅读:
    leetcode 78. 子集 JAVA
    leetcode 91. 解码方法 JAVA
    leetcode 75. 颜色分类 JAVA
    leetcode 74 搜索二维矩阵 java
    leetcode 84. 柱状图中最大的矩形 JAVA
    last occurance
    first occurance
    classical binary search
    LC.234.Palindrome Linked List
    LC.142. Linked List Cycle II
  • 原文地址:https://www.cnblogs.com/LittleTiger/p/6214910.html
Copyright © 2011-2022 走看看