📄 sd.c
字号:
C_SIZE_MUTI = SdRespBuf[10] & 0x3;
C_SIZE_MUTI <<= 1;
C_SIZE_MUTI |= (SdRespBuf[11] >> 7);
SdAvailableBlocks = (INT32U)((C_SIZE + 1) << (C_SIZE_MUTI + 2 + (READ_BL_LEN - BYTES_PER_SECTOR_SHIFT)));
SdAvailableBlocks -= 1;
return STATUS_SUCCESS;
}
STATUS SdGoTransferState()
{
STATUS Status;
BYTE CurrentState;
*((INT32U *)(&SdCmdBuf[1])) = RCA;
Status = SdSendCmd(SELECT_CARD, SdCmdBuf);
if(Status != STATUS_SUCCESS)
return Status;
*((INT32U *)(&SdCmdBuf[1])) = RCA;
Status = SdSendCmd(SEND_STATUS, SdCmdBuf);
if(Status != STATUS_SUCCESS)
return Status;
CurrentState = (SdRespBuf[3] >> 1) & 0x0F;
if(CurrentState == TRANSFER_STATE)
{
SdHiClk();
if(CardType == CARD_SD)
{
Status = SdChangeBusWidth(4); /////
if(Status != STATUS_SUCCESS)
return Status;
}
else // MMC 3.1,only 1bit Mode
{
Status = SdChangeBusWidth(8);
if(Status != STATUS_SUCCESS)
return Status;
}
}
else
return STATUS_FLASH_ERROR;
return STATUS_SUCCESS;
}
//----------------------------------------------------------------------------
STATUS SdChangeBusWidth(BYTE busWidth) //
{
STATUS Status;
if(CardType == CARD_SD)
{
if(busWidth==4)
*((INT32U *)(&SdCmdBuf[1])) = RCA | 0x02; //4bits bus width
else
*((INT32U *)(&SdCmdBuf[1])) = RCA;
Status = SdSendAppCmd(SET_BUS_WIDTH,SdCmdBuf);
if(Status == STATUS_SUCCESS)
{
if(busWidth==4)
{
SDMI_CTL&=~bmSD_BUS_8BIT_EN;
SDMI_CTL|=bmSD_BUS_4BIT_EN;
}
else
{
SDMI_CTL&=~bmSD_BUS_8BIT_EN;
SDMI_CTL&=~bmSD_BUS_4BIT_EN;
}
}
}
else // MMC
{
if(MmcProtol) // MMC 4.0 surport 1/4/8 bits mode
{
if(busWidth==8)
*((INT32U *)(&SdCmdBuf[1])) = 0x03b70200;
else if(busWidth==4)
*((INT32U *)(&SdCmdBuf[1])) = 0x03b70100;
else
*((INT32U *)(&SdCmdBuf[1])) = 0x03b70000;
//*((INT32U *)(&SdCmdBuf[1])) = 0x03b70000;
Status = SdSendCmd(SWITCH, SdCmdBuf);
if(Status == STATUS_SUCCESS)
{
*((INT32U *)(&SdCmdBuf[1])) = RCA;
Status = SdSendCmd(SEND_STATUS, SdCmdBuf);
if(Status == STATUS_SUCCESS)
{
if(busWidth==8)
{
SDMI_CTL|=bmSD_BUS_8BIT_EN;
SDMI_CTL&=~bmSD_BUS_4BIT_EN;
}
else if((busWidth==4))
{
SDMI_CTL&=~bmSD_BUS_8BIT_EN;
SDMI_CTL|=bmSD_BUS_4BIT_EN;
}
else
{
SDMI_CTL&=~bmSD_BUS_4BIT_EN;
SDMI_CTL&=~bmSD_BUS_8BIT_EN;
}
}
}
}
else // MMC 3.1 surpport 1bit only
{
SDMI_CTL&=~bmSD_BUS_4BIT_EN;
SDMI_CTL&=~bmSD_BUS_8BIT_EN;
}
}
return Status;
}
//----------------------------------------------------------------------------
// Description:
// Stop the read or write command
//----------------------------------------------------------------------------
STATUS SdStopCmd()
{
STATUS Status;
int i;
SDMI_CTL&=~bmSD_AUTO_CLK_EN;
for(i = 1; i <= 4; i++)
SdCmdBuf[i] = 0;
Status = SdSendCmd(STOP_TRANS, SdCmdBuf);
if(Status != STATUS_SUCCESS)
return Status;
SdWaitCard();
return STATUS_SUCCESS;
}
//----------------------------------------------------------------------------
STATUS SdWaitCmd()
{
CmdTimer = SD_CMD_TIMEOUT;
while((!(SDMI_INT&bmSD_COMPLETE_INT))&&CmdTimer); //
SDMI_INT&=~bmSD_COMPLETE_INT; //
if (CmdTimer)
return STATUS_SUCCESS;
else
{
SdCtrlReset();
return STATUS_FLASH_ERROR;
}
}
//----------------------------------------------------------------------------
/*
STATUS SdSetBlockLen(INT16U len)
{
STATUS Status;
SdWaitCard();
*((INT32U *)(&SdCmdBuf[1]))=len;
Status = SdSendCmd(SET_BLOCK_LEN,SdCmdBuf);
if(Status == STATUS_SUCCESS)
{
SDMI_LENH=len>>8;
SDMI_LENL=len;
}
return Status;
}
*/
//--------------------------------------------------------------------
// Read first sector of data from SD/MMC
//--------------------------------------------------------------------
STATUS SdReadOneSector()
{
STATUS Status;
int RetryCount1 , RetryCount2;
BOOL ReadyForData;
if (!SdCardExist())
return STATUS_FLASH_ERROR;
if(SectorStart > SdAvailableBlocks)
return STATUS_PARAM_ERROR;
SdWaitCard();
for(RetryCount1 = 0; RetryCount1 < 5; RetryCount1++)
{
ReadyForData = FALSE;
for(RetryCount2 = 0; RetryCount2 < 20; RetryCount2++)
{
*((INT32U *)(&SdCmdBuf[1])) = RCA;
Status = SdSendCmd(SEND_STATUS, SdCmdBuf);
if(Status != STATUS_SUCCESS)
continue;
if(SdRespBuf[3] & 0x01) // READY_FOR_DATA in Card Status
{
ReadyForData = TRUE;
break;
}
}
if(!ReadyForData)
continue;
//SDMI_BUFBASE=0xEC; //FIFOA0
*((INT32U *)(&SdCmdBuf[1])) =
SectorStart << BYTES_PER_SECTOR_SHIFT;
//***********************8
if (SectorCount > 1) // Muti-Read.
{
SDMI_CTL|=bmSD_AUTO_CLK_EN;
Status = SdSendCmd(READ_MUL_BLOCK, SdCmdBuf);
if(Status != STATUS_SUCCESS)
continue;
}
else
{
Status = SdSendCmd(READ_BLOCK, SdCmdBuf);
if(Status != STATUS_SUCCESS)
continue;
}
//*******************************
if(SDMI_ST&bmSD_CRC16_ERR)//
{
SDMI_ST &=~bmSD_CRC16_ERR;
continue;
}
else
return STATUS_SUCCESS;
}
return STATUS_FLASH_ERROR;
}
//----------------------------------------------------------------------------
// Description:
// Read one sector of data from the SD device
//----------------------------------------------------------------------------
STATUS SdReadNextSectorData()
{
STATUS Status;
bit Stop;
Stop = SectorCount == 1;
SDMI_CMD=SD_CMD_RX_DATA_ONLY; //
SDMI_CTL|=bmSD_AUTO_CLK_EN; //
if ((Status = SdWaitCmd()) != STATUS_SUCCESS)//
return Status;
if(SDMI_ST&bmSD_CRC16_ERR) // CRC7 Error
{
SDMI_ST&=~bmSD_CRC16_ERR; // Clear INT
return STATUS_DATA_ERROR;
}
if (Stop)
return SdStopCmd();
return STATUS_SUCCESS;
}
STATUS SdReadSector()
{
STATUS Status = SdReadOneSector();
SectorStart ++;
return Status;
}
STATUS SdReadNextSector()
{
BYTE RetryCount;
STATUS Status = SdReadNextSectorData();
if(Status != STATUS_SUCCESS)
{
for(RetryCount = 0 ; RetryCount < 5; RetryCount ++)
{
Status = SdStopCmd();
if(Status != STATUS_SUCCESS)
continue;
Status = SdReadOneSector();
break;
}
}
SectorStart ++;
return Status;
}
//--------------------------------------------------------------------
// Write one sector of data to SD/MMC
//--------------------------------------------------------------------
STATUS SdWriteOneSector()
{
STATUS Status;
BYTE CrcSts;
int RetryCount1 , RetryCount2;
BOOL ReadyForData;
if(SDMI_ST & bmSD_WR_PROTECT)
return STATUS_WRITE_PROTECT;
SdWaitCard();
//MMCtest ++;
for(RetryCount1 = 0; RetryCount1 < 5; RetryCount1++)
{
ReadyForData = FALSE;
for(RetryCount2 = 0; RetryCount2 < 20; RetryCount2++)
{
*((INT32U *)(&SdCmdBuf[1])) = RCA;
Status = SdSendCmd(SEND_STATUS, SdCmdBuf);
if(Status != STATUS_SUCCESS) //MMCerror1++;
continue;
if(SdRespBuf[3] & 0x01) // READY_FOR_DATA in Card Status
{
ReadyForData = TRUE;
break;
}
}
if(!ReadyForData) //MMCerror2++;
continue;
//SDMI_BUFBASE=0xF0; //FIFOB0
*((INT32U *)(&SdCmdBuf[1])) = SectorStart << BYTES_PER_SECTOR_SHIFT;
//***********************8
if (SectorCount > 1) // Muti-Read.
{
Status = SdSendCmd(WRITE_MUL_BLOCK, SdCmdBuf);
if(Status != STATUS_SUCCESS)
continue;
}
else
{
Status = SdSendCmd(WRITE_BLOCK, SdCmdBuf);
if(Status != STATUS_SUCCESS)
continue;
}
//*******************************
CrcSts = (SDMI_ST&0x38) >> 3;
if(CrcSts != GOOD_CRC16_STS) //MMCerror3++;
continue;
else //*/
return STATUS_SUCCESS;
}
return STATUS_FLASH_ERROR;
}
//----------------------------------------------------------------------------
// Description:
// Write one sector of data from the SD device
//----------------------------------------------------------------------------
STATUS SdWriteNextSector()
{
STATUS Status;
BYTE CrcSts;
bit Stop;
Stop = SectorCount == 1;
SdWaitCard();
//SDMI_BUFBASE=0xF0; //FIFOB0
SDMI_CMD=SD_CMD_TX_DATA_ONLY;
if ((Status = SdWaitCmd()) != STATUS_SUCCESS)
return Status;
CrcSts = (SDMI_ST&0x38) >> 3;
if (CrcSts != GOOD_CRC16_STS)
return STATUS_DATA_ERROR;
if (Stop)
return SdStopCmd();
return STATUS_SUCCESS;
}
STATUS SdWriteSector()
{
STATUS Status = SdWriteOneSector();
SectorStart ++;
return Status;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -