SD卡的初始化和读写程序(4)

2018-12-23 23:25

//------------------------------------------------------------------------ //获取SD卡的容量(字节) //返回值:0: 取容量出错 // 其他:SD卡的容量(字节) u32 SD_GetCapacity(void) {

u8 csd[16]; u32 Capacity; u8 r1; u16 i;

u16 temp;

//取CSD信息,如果期间出错,返回0 if(SD_GetCSD(csd)!=0) return 0;

//如果为SDHC卡,按照下面方式计算 if((csd[0]&0xC0)==0x40) {

Capacity=((u32)csd[8])<<8;

Capacity+=(u32)csd[9]+1;

Capacity = (Capacity)*1024;//得到扇区数 Capacity*=512;//得到字节数 } else {

i = csd[6]&0x03; i<<=8;

i += csd[7]; i<<=2;

i += ((csd[8]&0xc0)>>6); //C_SIZE_MULT r1 = csd[9]&0x03; r1<<=1;

r1 += ((csd[10]&0x80)>>7); r1+=2;//BLOCKNR temp = 1; while(r1) {

temp*=2; r1--; }

Capacity = ((u32)(i+1))*((u32)temp); // READ_BL_LEN i = csd[5]&0x0f;

//BLOCK_LEN temp = 1; while(i) {

temp*=2; i--; }

//The final result

Capacity *= (u32)temp;//字节为单位 }

return (u32)Capacity; }

//-------------------------------------------------------------------- //读SD卡的一个block

//输入:u32 sector 取地址(sector值,非物理地址) // u8 *buffer 数据存储地址(大小至少512byte) //返回值:0: 成功

// other:失败

u8 SD_ReadSingleBlock(u32 sector, u8 *buffer) {

u8 r1;

//设置为高速模式

//SPIx_SetSpeed(SPI_SPEED_4);

//spi_high_speed();

//如果不是SDHC,给定的是sector地址,将其转换成byte地址 if(SD_Type!=SD_TYPE_V2HC) {

sector = sector<<9;

}

r1 = SD_SendCommand(CMD17, sector, 0);//读命令 if(r1 != 0x00)return r1;

r1 = SD_ReceiveData(buffer, 512, RELEASE); if(r1 != 0)return r1; //读数据出错! else return 0; }

/*u8 SD_ReadSingleBlock(u32 sector, u8 *buffer) {

u8 r1;

//设置为高速模式

//SPIx_SetSpeed(SPI_SPEED_4);

spi_high_speed();

//如果不是SDHC,给定的是sector地址,将其转换成byte地址 if(SD_Type!=SD_TYPE_V2HC) {

sector = sector<<9;

}

r1 = SD_SendCommand(CMD17, sector, 0);//读命令 if(r1 != 0x00)return r1;

r1 = SD_ReceiveData(buffer, 512, RELEASE); if(r1 != 0)return r1; //读数据出错! else return 0; }*/

//---------------------------------------------------------------------- //写入SD卡的一个block(未实际测试过)

//输入:u32 sector 扇区地址(sector值,非物理地址) // u8 *buffer 数据存储地址(大小至少512byte) //返回值:0: 成功

// other:失败

u8 SD_WriteSingleBlock(u32 sector, const u8 *data) {

u8 r1; u16 i; u16 retry;

//设置为高速模式

//SPIx_SetSpeed(SPI_SPEED_4);

//如果不是SDHC,给定的是sector地址,将其转换成byte地址 if(SD_Type!=SD_TYPE_V2HC) {

sector = sector<<9; }

r1 = SD_SendCommand(CMD24, sector, 0x00); if(r1 != 0x00)

{

return r1; //应答不正确,直接返回 }

//开始准备数据传输 sd_cs_0;

//先放3个空数据,等待SD卡准备好 SPIx_ReadWriteByte(0xff); SPIx_ReadWriteByte(0xff); SPIx_ReadWriteByte(0xff); //放起始令牌0xFE

SPIx_ReadWriteByte(0xFE); //放一个sector的数据 for(i=0;i<512;i++) {

SPIx_ReadWriteByte(*data++); }

//发2个Byte的dummy CRC SPIx_ReadWriteByte(0xff); SPIx_ReadWriteByte(0xff); //等待SD卡应答

r1 = SPIx_ReadWriteByte(0xff); if((r1&0x1F)!=0x05) {

sd_cs_1; return r1; }

//等待操作完成 retry = 0;

while(!SPIx_ReadWriteByte(0xff)) {

retry++;

if(retry>0xfffe) //如果长时间写入没有完成,报错退出 {

sd_cs_1;

return 1; //写入超时返回1 } }

//写入完成,片选置1 sd_cs_1;

SPIx_ReadWriteByte(0xff); return 0; }

//------------------------------------------------------------------- //读SD卡的多个block(实际测试过)

//输入:u32 sector 扇区地址(sector值,非物理地址) // u8 *buffer 数据存储地址(大小至少512byte) // u8 count 连续读count个block //返回值:0: 成功

// other:失败

u8 SD_ReadMultiBlock(u32 sector, u8 *buffer, u8 count) {

u8 r1;

//SPIx_SetSpeed(SPI_SPEED_4);//设置为高速模式 //如果不是SDHC,将sector地址转成byte地址 if(SD_Type!=SD_TYPE_V2HC)sector = sector<<9; //SD_WaitDataReady();

//发读多块命令

r1 = SD_SendCommand(CMD18, sector, 0);//读命令 if(r1 != 0x00)return r1; do//开始接收数据 {

if(SD_ReceiveData(buffer, 512, NO_RELEASE) != 0x00)break; buffer += 512;

} while(--count);

//全部传输完毕,发送停止命令 SD_SendCommand(CMD12, 0, 0); //释放总线

sd_cs_1;

SPIx_ReadWriteByte(0xFF);

if(count != 0)return count; //如果没有传完,返回剩余个数 else return 0; }

//------------------------------------------------------------------------ //写入SD卡的N个block(未实际测试过)

//输入:u32 sector 扇区地址(sector值,非物理地址) // u8 *buffer 数据存储地址(大小至少512byte) // u8 count 写入的block数目 //返回值:0: 成功 // other:失败

u8 SD_WriteMultiBlock(u32 sector, const u8 *data, u8 count) { u8 r1; u16 i;

//SPIx_SetSpeed(SPI_SPEED_4);//设置为高速模式

if(SD_Type != SD_TYPE_V2HC)sector = sector<<9;//如果不是SDHC,给定的是sector地址,将其转换成byte地址

if(SD_Type != SD_TYPE_MMC) r1 = SD_SendCommand(ACMD23, count, 0x00);//如果目标卡不是MMC卡,启用ACMD23指令使能预擦除

r1 = SD_SendCommand(CMD25, sector, 0x00);//发多块写入指令 if(r1 != 0x00)return r1; //应答不正确,直接返回

sd_cs_0;//开始准备数据传输

SPIx_ReadWriteByte(0xff);//先放3个空数据,等待SD卡准备好 SPIx_ReadWriteByte(0xff);


SD卡的初始化和读写程序(4).doc 将本文的Word文档下载到电脑 下载失败或者文档不完整,请联系客服人员解决!

下一篇:文言文解析:《狼》

相关阅读
本类排行
× 注册会员免费下载(下载后可以自由复制和排版)

马上注册会员

注:下载文档有可能“只有目录或者内容不全”等情况,请下载之前注意辨别,如果您已付费且无法下载或内容有问题,请联系我们协助你处理。
微信: QQ: