STM32对SD卡的读、写、擦除操作(SDIO模式)(DMA)

这篇具有很好参考价值的文章主要介绍了STM32对SD卡的读、写、擦除操作(SDIO模式)(DMA)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

对于STM32操作SD卡来说,最重要的就算初始化写操作读操作擦除这几个操作了。

对于初始化部分上一篇文章已经分析,本篇就主要分析写、读、擦除操作。

本篇函数来自于STM32提供的例程。参考野火的程序进行了解释,与野火函数有些不同。

这几种函数完成之后,就是开始实现对SD卡进行操作了。😀 😀 😀


SD卡擦除函数

SD卡擦除函数比较简单,只用到CMD32、CMD33、CMD38指令。

STM32对SD卡的读、写、擦除操作(SDIO模式)(DMA)

最后需要确保SD卡擦除完成才能退出SD_Erase函数。通过IsCardProgramming函数实现。

/**
 * @brief 控制 SD 卡擦除指定的数据区域
 * @param startaddr: 擦除的开始地址
 * @param endaddr: 擦除的结束地址
 * @retval SD_Error: SD 返回的错误代码
 */
SD_Error SD_Erase(uint32_t startaddr, uint32_t endaddr)
{
  SD_Error errorstatus = SD_OK;
  uint32_t delay = 0;
  __IO uint32_t maxdelay = 0;
  uint8_t cardstate = 0;

  /*!< 检查SD卡是否支持擦除操作 */
  if (((CSD_Tab[1] >> 20) & SD_CCCC_ERASE) == 0)
  {
    errorstatus = SD_REQUEST_NOT_APPLICABLE;
    return(errorstatus);
  }

  maxdelay = 120000 / ((SDIO->CLKCR & 0xFF) + 2);    //延时,根据时钟分频设计来计算

  if (SDIO_GetResponse(SDIO_RESP1) & SD_CARD_LOCKED)    //卡上锁
  {
    errorstatus = SD_LOCK_UNLOCK_FAILED;
    return(errorstatus);
  }

  /* SDHC卡,地址参数为块地址,每块512字节,SDSC卡地址为字节地址 */
  if (CardType == SDIO_HIGH_CAPACITY_SD_CARD) 
  {
    startaddr /= 512;
    endaddr /= 512;
  }
  
  /*!<  ERASE_GROUP_START (CMD32) and SD_CMD_SD_ERASE_GRP_END(CMD33) */
  if ((SDIO_STD_CAPACITY_SD_CARD_V1_1 == CardType) || 
      (SDIO_STD_CAPACITY_SD_CARD_V2_0 == CardType) || 
      (SDIO_HIGH_CAPACITY_SD_CARD == CardType))
  {
    /*!< Send CMD32 SD_ERASE_GRP_START with startaddr  */
    SDIO_CmdInitStructure.SDIO_Argument = startaddr;
    SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_SD_ERASE_GRP_START;
    SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;
    SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
    SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
    SDIO_SendCommand(&SDIO_CmdInitStructure);
    errorstatus = CmdResp1Error(SD_CMD_SD_ERASE_GRP_START);
    if (errorstatus != SD_OK)
    {
      return(errorstatus);
    }

    /*!< Send CMD33 SD_ERASE_GRP_END with endaddr  */
    SDIO_CmdInitStructure.SDIO_Argument = endaddr;
    SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_SD_ERASE_GRP_END;
    SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;
    SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
    SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
    SDIO_SendCommand(&SDIO_CmdInitStructure);
    errorstatus = CmdResp1Error(SD_CMD_SD_ERASE_GRP_END);
    if (errorstatus != SD_OK)
    {
      return(errorstatus);
    }
  }

  /*!< Send CMD38 ERASE */
  SDIO_CmdInitStructure.SDIO_Argument = 0;
  SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_ERASE;
  SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;
  SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
  SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
  SDIO_SendCommand(&SDIO_CmdInitStructure);
  errorstatus = CmdResp1Error(SD_CMD_ERASE);
  if (errorstatus != SD_OK)
  {
    return(errorstatus);
  }

  for (delay = 0; delay < maxdelay; delay++){}
  /*!< 等待SD卡的内部时序操作完成 */
  errorstatus = IsCardProgramming(&cardstate);

  while ((errorstatus == SD_OK) && 
         ((SD_CARD_PROGRAMMING == cardstate) || (SD_CARD_RECEIVING == cardstate)))
          //SD卡编程 || SD卡接收
  {
    errorstatus = IsCardProgramming(&cardstate);    //检测SD卡是否在读写操作
  }
  return(errorstatus);
}

数据写入操作(单块写入、DMA传输方式)

STM32对SD卡的读、写、擦除操作(SDIO模式)(DMA)

因为分析DMA传输模式,故有关轮询的函数删掉了。

数据写入函数

/**
 * @brief 向 sd 卡写入一个 BLOCK 的数据(512 字节)
 * @note 本函数使用后需要调用如下两个函数来等待数据传输完成
 * - SD_WaitWriteOperation(): 确认 DMA 已把数据传输到 SDIO 接口
 * - SD_GetStatus(): 确认 SD 卡内部已经把数据写入完毕
 * @param writebuff: 指向要写入的数据
 * @param WriteAddr: 要把数据写入到 sd 卡的地址
 * @param BlockSize: 块大小,sdhc 卡为 512 字节
 * @retval SD_Error: 返回的 sd 错误代码
 */
SD_Error SD_WriteBlock(uint8_t *writebuff, uint32_t WriteAddr, uint16_t BlockSize)
{
  SD_Error errorstatus = SD_OK;

  TransferError = SD_OK;
  TransferEnd = 0;
  StopCondition = 0;
  
  SDIO->DCTRL = 0x0;

  if (CardType == SDIO_HIGH_CAPACITY_SD_CARD)
  {
    BlockSize = 512;
    WriteAddr /= 512;
  }
  
//+++++++++++++++++++++++++++++++++++野火添加的函数++++++++++++++++++++++++++++++++++++
  /*-------------- add , 没有这一段容易卡死在DMA检测中 -------------------*/
  /* Set Block Size for Card,cmd16,
   * 若是sdsc卡,可以用来设置块大小,
   * 若是sdhc卡,块大小为512字节,不受cmd16影响 
   */
  /*!< Send CMD 16 */
  SDIO_CmdInitStructure.SDIO_Argument = (uint32_t) BlockSize;
  SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_SET_BLOCKLEN;
  SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;   
  SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
  SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
  SDIO_SendCommand(&SDIO_CmdInitStructure);
  errorstatus = CmdResp1Error(SD_CMD_SET_BLOCKLEN);
  if (SD_OK != errorstatus)
  {
    return(errorstatus);
  }
//+++++++++++++++++++++++++++++++++++野火添加的函数++++++++++++++++++++++++++++++++++++

  /*!< Send CMD24 WRITE_SINGLE_BLOCK */
  SDIO_CmdInitStructure.SDIO_Argument = WriteAddr;    //写入地址
  SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_WRITE_SINGLE_BLOCK;
  SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;
  SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
  SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
  SDIO_SendCommand(&SDIO_CmdInitStructure);
  errorstatus = CmdResp1Error(SD_CMD_WRITE_SINGLE_BLOCK);
  if (errorstatus != SD_OK)
  {
    return(errorstatus);
  }
  /*!< 配置SDIO的写数据寄存器 */
  SDIO_DataInitStructure.SDIO_DataTimeOut = SD_DATATIMEOUT;
  SDIO_DataInitStructure.SDIO_DataLength = BlockSize;
  SDIO_DataInitStructure.SDIO_DataBlockSize = (uint32_t) 9 << 4;    //可用此参数代替SDIO_DataBlockSize_512b
  SDIO_DataInitStructure.SDIO_TransferDir = SDIO_TransferDir_ToCard;    //写数据
  SDIO_DataInitStructure.SDIO_TransferMode = SDIO_TransferMode_Block;
  SDIO_DataInitStructure.SDIO_DPSM = SDIO_DPSM_Enable;    //开启数据通道状态机
  SDIO_DataConfig(&SDIO_DataInitStructure);

  SDIO_ITConfig(SDIO_IT_DATAEND, ENABLE);    //数据传输结束中断
  SD_LowLevel_DMA_TxConfig((uint32_t *)writebuff, BlockSize);    //配置DMA
  SDIO_DMACmd(ENABLE);    //使能SDIO的DMA请求

  return(errorstatus);
}

首先,设置SDIO->DCTRL清零,清除之前的传输设置。

发送CMD16指定块的大小。对于标准卡,要写入 BlockSize 长度字节的块;对于 SDHC 卡,写入固定为 512 字节的块。

发送CMD24通知 SD 卡要进行数据写入操作,并指定待写入数据的目标地址。

通过结构体配置数据传输的超时、块数量、块大小、传输方向等参数。

调用 SDIO_ITConfig 函数使能 SDIO 数据结束传输结束中断,传输结束时,会跳转到 SDIO 的 中断服务函数运行。

调用前面讲解的 SD_LowLevel_DMA_TxConfig 函数,配置使能 SDIO 数据向 SD 卡的数据传输的 DMA 请求。为使 SDIO 发送 DMA 请求,需要调用 SDIO_DMACmd 函数使能。

SDIO 外设会自动生成 DMA 发送请求,将指定数据使用 DMA 传输写入到 SD 卡内。

写入DMA配置

/*
 * 函数名:SD_DMA_RxConfig
 * 描述  :为SDIO发送数据配置DMA2的通道4的请求
 * 输入  :BufferDST:装载了数据的变量指针
 *  	   BufferSize:	缓冲区大小
 * 输出  :无
 */
void SD_LowLevel_DMA_TxConfig(uint32_t *BufferSRC, uint32_t BufferSize)
{

  DMA_InitTypeDef DMA_InitStructure;

  DMA_ClearFlag(DMA2_FLAG_TC4 | DMA2_FLAG_TE4 | DMA2_FLAG_HT4 | DMA2_FLAG_GL4);

  /*!< DMA2 Channel4 disable */
  DMA_Cmd(DMA2_Channel4, DISABLE);

  /*!< DMA2 Channel4 Config */
  DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)SDIO_FIFO_ADDRESS;
  DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)BufferSRC;
  DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralDST;//外设为写入目标
  DMA_InitStructure.DMA_BufferSize = BufferSize / 4;
  DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;	//外设地址不自增
  DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
  DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Word;
  DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Word;
  DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;
  DMA_InitStructure.DMA_Priority = DMA_Priority_High;
  DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;
  DMA_Init(DMA2_Channel4, &DMA_InitStructure);

  /*!< DMA2 Channel4 enable */
  DMA_Cmd(DMA2_Channel4, ENABLE);  
}

写入操作等待函数

/**
 * @brief 本函数会一直等待到 DMA 传输结束
 * 在 SDIO_WriteBlock() 和 SDIO_WriteMultiBlocks() 函数后必须被调用以确保DMA 数据传输完成
 * @param None.
 * @retval SD_Error: 返回的 sd 错误代码.
 */
SD_Error SD_WaitWriteOperation(void)
{
  SD_Error errorstatus = SD_OK;
  //等待 DMA 是否传输结束
  while ((SD_DMAEndOfTransferStatus() == RESET) 
        && (TransferEnd == 0) && (TransferError == SD_OK))
  {}

  if (TransferError != SD_OK)
  {
    return(TransferError);
  }

  /*!< 清除标志 */
  SDIO_ClearFlag(SDIO_STATIC_FLAGS);

  return(errorstatus);
}

调用库函数 SD_DMAEndOfTransferStatus 一直检测 DMA 的传输完成标志,当 DMA 传输 结束时,该函数会返回 SET 值。另外,while 循环中的判断条件使用的 TransferEnd 和 TransferError是全局变量,它们会在 SDIO 的中断服务函数根据传输情况被设置,传输结束后,根据TransferError 的值来确认是否正确传输,若不正确则直接返回错误代码。SD_WaitWriteOperation 函数最后是清 除相关标志位并返回错误。由于这个函数里的 while 循环的存在,它会确保 DMA 的传输结束。


数据读取操作(单块读取、DMA传输方式)

STM32对SD卡的读、写、擦除操作(SDIO模式)(DMA)

数据读取函数

/**
 * @brief 向 sd 卡写入一个 BLOCK 的数据(512 字节)
 * @note 本函数使用后需要调用如下两个函数来等待数据传输完成
 * - SD_WaitWriteOperation(): 确认 DMA 已把数据传输到 SDIO 接口
 * - SD_GetStatus(): 确认 SD 卡内部已经把数据写入完毕
 * @param writebuff: 指向要写入的数据
 * @param WriteAddr: 要把数据写入到 sd 卡的地址
 * @param BlockSize: 块大小,sdhc 卡为 512 字节
 * @retval SD_Error: 返回的 sd 错误代码
 */

SD_Error SD_ReadBlock(uint8_t *readbuff, uint32_t ReadAddr, uint16_t BlockSize)
{
  SD_Error errorstatus = SD_OK;

  TransferError = SD_OK;
  TransferEnd = 0;    //传输结束标志位,在中断服务中置1
  StopCondition = 0;
  
  SDIO->DCTRL = 0x0;
  
  if (CardType == SDIO_HIGH_CAPACITY_SD_CARD)
  {
    BlockSize = 512;
    ReadAddr /= 512;
  }
  //+++++++++++++++++++++++++++++++++++野火添加的函数++++++++++++++++++++++++++++++++++++
  /*-------------- add , 没有这一段容易卡死在DMA检测中 -------------------*/
  /* Set Block Size for Card,cmd16,
   * 若是sdsc卡,可以用来设置块大小,
   * 若是sdhc卡,块大小为512字节,不受cmd16影响 
   */
  /*!< Send CMD 16 */
  SDIO_CmdInitStructure.SDIO_Argument = (uint32_t) BlockSize;
  SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_SET_BLOCKLEN;
  SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;   
  SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
  SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
  SDIO_SendCommand(&SDIO_CmdInitStructure);
  errorstatus = CmdResp1Error(SD_CMD_SET_BLOCKLEN);
  if (SD_OK != errorstatus)
  {
    return(errorstatus);
  }
  //+++++++++++++++++++++++++++++++++++野火添加的函数++++++++++++++++++++++++++++++++++++
  
  SDIO_DataInitStructure.SDIO_DataTimeOut = SD_DATATIMEOUT;
  SDIO_DataInitStructure.SDIO_DataLength = BlockSize;
  SDIO_DataInitStructure.SDIO_DataBlockSize = (uint32_t) 9 << 4;
  SDIO_DataInitStructure.SDIO_TransferDir = SDIO_TransferDir_ToSDIO;    //数据传输方向
  SDIO_DataInitStructure.SDIO_TransferMode = SDIO_TransferMode_Block;
  SDIO_DataInitStructure.SDIO_DPSM = SDIO_DPSM_Enable;
  SDIO_DataConfig(&SDIO_DataInitStructure);

  /*!< Send CMD17 READ_SINGLE_BLOCK */
  SDIO_CmdInitStructure.SDIO_Argument = (uint32_t)ReadAddr;
  SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_READ_SINGLE_BLOCK;
  SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;
  SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
  SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
  SDIO_SendCommand(&SDIO_CmdInitStructure);
  errorstatus = CmdResp1Error(SD_CMD_READ_SINGLE_BLOCK);
  if (errorstatus != SD_OK)
  {
    return(errorstatus);
  }

  SDIO_ITConfig(SDIO_IT_DATAEND, ENABLE);    //启用或禁用SDIO中断,第一个为指定禁用值
  SDIO_DMACmd(ENABLE);    //启用或禁用SDIO DMA请求。 
  SD_LowLevel_DMA_RxConfig((uint32_t *)readbuff, BlockSize);

  return(errorstatus);
}

数据读操作和写操作类似!

首先,设置SDIO->DCTRL清零,清除之前的传输设置。

发送CMD16指定块的大小。对于标准卡,要写入 BlockSize 长度字节的块;对于 SDHC 卡,写入固定为 512 字节的块。

通过结构体配置数据传输的超时、块数量、块大小、传输方向等参数。

发送CMD17,SD卡在接收到命令后就会通过数据线把书记传输到SDIO的数据FIFO中。

调用 SDIO_ITConfig 函数使能 SDIO 数据结束传输结束中断,传输结束时,会跳转到 SDIO 的 中断服务函数运行。

调用前面讲解的 SD_LowLevel_DMA_RxConfig 函数,配置使能 SDIO 从 SD 卡读取数据的 DMA 请求。为使 SDIO 发送 DMA 请求,需要调用 SDIO_DMACmd 函数使能。

SD 卡发出的数据将会传输到 STM32 的 SDIO 外设,而 SDIO 外设激发 DMA 请求,把 数据搬运到内存中。

读取DMA配置

 /*
  * 函数名:SD_DMA_RxConfig
  * 描述  :为SDIO接收数据配置DMA2的通道4的请求
  * 输入  :BufferDST:用于装载数据的变量指针
  *	      : BufferSize:	缓冲区大小
  * 输出  :无
  */
void SD_LowLevel_DMA_RxConfig( uint32_t *BufferDST, uint32_t BufferSize )
{
    DMA_InitTypeDef DMA_InitStructure;
 
    DMA_ClearFlag(DMA2_FLAG_TC4 | DMA2_FLAG_TE4 | DMA2_FLAG_HT4 | DMA2_FLAG_GL4);//清除DMA标志位
 
    /*!< DMA2 Channel4 disable */
    DMA_Cmd(DMA2_Channel4, DISABLE);    //SDIO为第四通道
 
    /*!< DMA2 Channel4 Config */
    DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)SDIO_FIFO_ADDRESS;    //外设地址,fifo
    DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)BufferDST;    //目标地址
    DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;    //外设为源地址
    DMA_InitStructure.DMA_BufferSize = BufferSize / 4;    //除以4,把字转成字节单位
    DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;    //使能外设地址不自增
    DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;    //使能存储目标地址自增
    DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Word;    //外设数据大小为字,32位
    DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Word;    //外设数据大小为字,32位
    DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;    //不循环,循环模式主要用在adc上
    DMA_InitStructure.DMA_Priority = DMA_Priority_High;    //通道优先级高
    DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;    //非 存储器至存储器模式
    DMA_Init(DMA2_Channel4, &DMA_InitStructure);
 
    /*!< DMA2 Channel4 enable */
    DMA_Cmd(DMA2_Channel4, ENABLE);
}

读取操作等待函数

/**
 * @brief 本函数会一直等待到 DMA 传输结束
 * SDIO_ReadMultiBlocks() 函数后必须被调用以确保 DMA 数据传输完成
 * @param None.
 * @retval SD_Error: 返回的 sd 错误代码.
 */
SD_Error SD_WaitWriteOperation(void)
{
  SD_Error errorstatus = SD_OK;
    
  //等待 DMA 传输结束
  while ((SD_DMAEndOfTransferStatus() == RESET) 
        && (TransferEnd == 0) && (TransferError == SD_OK))
  {}

  if (TransferError != SD_OK)
  {
    return(TransferError);
  }

  /*!< Clear all the static flags */
  SDIO_ClearFlag(SDIO_STATIC_FLAGS);

  return(errorstatus);
}

其中,写入读取操作分为单块和多块,但是相差不大,故本篇文章仅仅分析了单块读取操作


SDIO的中断服务操作

中断服务操作在 stm32f10x_it.c 文件中。需要注意!!!!!

在进行数据传输操作时都会使能相关标志中断,用于跟踪传输进程和错误检测。

中断服务接口

stm32f10x_it.c 文件中需要设置:(其实设置到sdio用户自定文件中也可!)

void SDIO_IRQHandler(void) 
{		
    /* Process All SDIO Interrupt Sources */									
 	SD_ProcessIRQSrc();
}	

中断服务函数

SD_Error SD_ProcessIRQSrc(void)
{
  if (StopCondition == 1)    //发送读、写命令时设置为1
  {
    SDIO->ARG = 0x0;    //命令参数寄存器
    SDIO->CMD = 0x44C;    //命令寄存器 0100-0100-1100
                          /*    CPSMEN[10]    WAITRESP[7:6]  CMDINDEX[5:0]
                           *    0100          01             001100
                           *    开启命令状态机  短响应         命令索引:CMD12
                           */
    TransferError = CmdResp1Error(SD_CMD_STOP_TRANSMISSION);
  }
  else
  {
    TransferError = SD_OK;
  }
  SDIO_ClearITPendingBit(SDIO_IT_DATAEND);    //清除中断
  SDIO_ITConfig(SDIO_IT_DATAEND, DISABLE);    //关闭SDIO中断使能
  TransferEnd = 1;
  return(TransferError);
}

函数首先判断 StopCondition !多块读写中被置为1,单块读写中是置为0 。SD卡要求多块读写命令有 CMD12 结束,SD卡收到 CMD12 时才停止多块的传输!发送命令直接采用向寄存器写入命令和参数的方式。此外,根据传输情况设置全局变量 TransferError、TransferEnd 。


至此,大部分的STM32 的 SDIO 功能就基本上看到了。可根据此执行一些简单的读写操作了。

晚安 ~

STM32对SD卡的读、写、擦除操作(SDIO模式)(DMA)

 文章来源地址https://www.toymoban.com/news/detail-404144.html

到了这里,关于STM32对SD卡的读、写、擦除操作(SDIO模式)(DMA)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • STM32CubeMX教程27 SDIO - 读写SD卡

    正点原子stm32f407探索者开发板V2.4 STM32CubeMX软件(Version 6.10.0) keil µVision5 IDE(MDK-Arm) ST-LINK/V2驱动 逻辑分析仪nanoDLA 野火DAP仿真器 XCOM V2.6串口助手 使用STM32CubeMX软件配置STM32F407开发板 SDIO读写4线SD卡,实现轮询方式读写SD卡、以中断方式读取SD卡和以DMA方式读取SD卡 安全数码

    2024年02月19日
    浏览(67)
  • STM32——SDIO的学习(驱动SD卡)(实战篇)

    目录 一、SDIO寄存器 1.1 SDIO电源控制寄存器(SDIO_POWER) 1.2 SDIO时钟控制寄存器(SDIO_CLKCR) 1.3 SDIO参数寄存器(SDIO_ARG) 1.4 SDIO命令寄存器(SDIO_CMD) 1.5 SDIO命令响应寄存器(SDIO_RESPCMD) 1.6 SDIO响应 1..4 寄存器(SDIO_RESPx) 1.7 SDIO数据定时器寄存器(SDIO_DTIMER) 1.8 SDIO数据长度寄存器(SDIO_DLEN) 1.9 SDI

    2024年02月16日
    浏览(67)
  • STM32CubeMX系列09——SDIO(SD卡读写、SD卡移植FATFS文件系统)

    ==== 文章汇总(有代码汇总) ==== 准备看看这方面的知识,一时间还没不清有什么区别,先补补课,不需要的跳过。 参考文章(内容来源):http://www.360doc.com/content/21/1125/22/59057945_1005908465.shtml 主要写这两个:SD卡、TF卡 共同点:SD、TF、MMC都是在MMC基础上演化发展不同的规范,

    2024年02月09日
    浏览(49)
  • STM32用一线式驱动SD NAND,SDIO的一线式驱动

    SDIO的一线式和四线式 SDIO(Secure Digital Input/Output)是一种用于在嵌入式系统中连接外部设备的标准接口。在SDIO标准中,一线式和四线式是指SDIO接口的不同工作模式。 一线式(Single-Line Mode): 工作原理: 在一线式模式下,SDIO接口仅使用单个数据线进行通信。这个模式通常用

    2024年01月17日
    浏览(41)
  • STM32CubeMX教程28 SDIO - 使用FatFs文件系统读写SD卡

    正点原子stm32f407探索者开发板V2.4 STM32CubeMX软件(Version 6.10.0) keil µVision5 IDE(MDK-Arm) ST-LINK/V2驱动 野火DAP仿真器 XCOM V2.6串口助手 使用STM32CubeMX软件配置STM32F407开发板 SDIO使用FatFs中间件读写4线SD卡,并实现以轮询方式读写SD卡或以DMA方式读取SD卡 FatFs文件系统相关知识请读者

    2024年02月19日
    浏览(50)
  • STM32F4X SDIO(七) 例程讲解-SD_InitializeCards & SD_GetCardInfo

    本节例程基于 野火电子的STM32F407的SD卡读写例程 进行讲解。上一节中讲解了SD卡上电过程,这节将会讲解一下SD卡的初始化过程,包括 获取SD卡的CID、CSD和SD卡RCA地址 。 CMD2的作用是 通知所有卡通过CMD线返回CID值 ,CID值包括 SD卡的识别号、制造商ID、OEMID、产品名称、版本号、

    2024年02月05日
    浏览(50)
  • stm32读写SD卡(SPI模式)

    目录 一、SD卡简介 二、源码下载 三、移植条件 1、芯片参数 2、硬件连接 四、驱动代码 1、依赖宏如下 2、驱动代码实现 3、测试代码 4、运行截图 SD卡有SD驱动模式和SPI驱动模式,本例中使用SPI模式驱动SD卡。 https://download.csdn.net/download/qq_30095023/88014550 1、芯片参数 芯片类型:

    2024年02月07日
    浏览(46)
  • GD32或STM32:DMA循环模式与普通模式(串口IDLE)

    USART+DMA+循环队列接收不定长数据-CSDN博客 STM32 DMA 循环模式DMA_Mode_Circular详解-CSDN博客 推荐以上两个链接。 Normal(普通)模式的DMA+串口IDLE中断,流程如下: 1、初始化时:开启串口IDLE中断;dma_circulation_disable,失能DMA的循环; 2、在串口IDLE中断里面: (1) 清除idle的flag;dma_c

    2024年02月21日
    浏览(47)
  • 【STM32笔记】STM32的串口数据收发基础(四)(USART DMA模式)

         在STM32中编写串口通信数据收发有三种方式: 轮询模式 (阻塞方式), 中断模式 (非阻塞方式)以及 DMA模式 。      打开STM32CubeMX,前部分配置流程如串口数据收发基础(三)节里一样。配置好USART1的基本参数,开启定时器中断后,接下来就要开启USART1的DMA。

    2024年02月03日
    浏览(40)
  • 【STM32】- 定时器+DMA+ADC 双重模式

    目录   1 前言 2 ADC介绍 2.1 多重工作模式 2.2 多重ADC框图 2.3 规则同时模式 3 程序设计 3.1 时序图 3.2 初始化流程图 3.3 初始化代码 4 结论        关于ADC,相信大家都比较了解,关于STM32的学习教程都会有所讲解,但以查询方式、单通道讲解的较多,主要告诉大家基本的原理。

    2024年02月10日
    浏览(56)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包