| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729 |
- #include "user.h"
- #define CMD0 (0) /* GO_IDLE_STATE */
- #define CMD1 (1) /* SEND_OP_COND */
- #define CMD2 (2)
- #define ACMD41 (0x80+41) /* SEND_OP_COND (SDC) */
- #define CMD8 (8) /* SEND_IF_COND */
- #define CMD9 (9) /* SEND_CSD */
- #define CMD10 (10) /* SEND_CID */
- #define CMD12 (12) /* STOP_TRANSMISSION */
- #define CMD13 (13) /* SEND_STATUS */
- #define ACMD13 (0x80+13) /* SD_STATUS (SDC) */
- #define CMD16 (16) /* SET_BLOCKLEN */
- #define CMD17 (17) /* READ_SINGLE_BLOCK */
- #define CMD18 (18) /* READ_MULTIPLE_BLOCK */
- #define CMD23 (23) /* SET_BLOCK_COUNT */
- #define ACMD23 (0x80+23) /* SET_WR_BLK_ERASE_COUNT (SDC) */
- #define CMD24 (24) /* WRITE_BLOCK */
- #define CMD25 (25) /* WRITE_MULTIPLE_BLOCK */
- #define CMD32 (32) /* ERASE_ER_BLK_START */
- #define CMD33 (33) /* ERASE_ER_BLK_END */
- #define CMD38 (38) /* ERASE */
- #define CMD55 (55) /* APP_CMD */
- #define CMD58 (58) /* READ_OCR */
- #define SD_CMD_GO_IDLE_STATE 0 /* CMD0 = 0x40 */
- #define SD_CMD_SEND_OP_COND 1 /* CMD1 = 0x41 */
- #define SD_CMD_SEND_IF_COND 8 /* CMD8 = 0x48 */
- #define SD_CMD_SEND_CSD 9 /* CMD9 = 0x49 */
- #define SD_CMD_SEND_CID 10 /* CMD10 = 0x4A */
- #define SD_CMD_STOP_TRANSMISSION 12 /* CMD12 = 0x4C */
- #define SD_CMD_SEND_STATUS 13 /* CMD13 = 0x4D */
- #define SD_CMD_SET_BLOCKLEN 16 /* CMD16 = 0x50 */
- #define SD_CMD_READ_SINGLE_BLOCK 17 /* CMD17 = 0x51 */
- #define SD_CMD_READ_MULT_BLOCK 18 /* CMD18 = 0x52 */
- #define SD_CMD_SET_BLOCK_COUNT 23 /* CMD23 = 0x57 */
- #define SD_CMD_WRITE_SINGLE_BLOCK 24 /* CMD24 = 0x58 */
- #define SD_CMD_WRITE_MULT_BLOCK 25 /* CMD25 = 0x59 */
- #define SD_CMD_PROG_CSD 27 /* CMD27 = 0x5B */
- #define SD_CMD_SET_WRITE_PROT 28 /* CMD28 = 0x5C */
- #define SD_CMD_CLR_WRITE_PROT 29 /* CMD29 = 0x5D */
- #define SD_CMD_SEND_WRITE_PROT 30 /* CMD30 = 0x5E */
- #define SD_CMD_SD_ERASE_GRP_START 32 /* CMD32 = 0x60 */
- #define SD_CMD_SD_ERASE_GRP_END 33 /* CMD33 = 0x61 */
- #define SD_CMD_UNTAG_SECTOR 34 /* CMD34 = 0x62 */
- #define SD_CMD_ERASE_GRP_START 35 /* CMD35 = 0x63 */
- #define SD_CMD_ERASE_GRP_END 36 /* CMD36 = 0x64 */
- #define SD_CMD_UNTAG_ERASE_GROUP 37 /* CMD37 = 0x65 */
- #define SD_CMD_ERASE 38 /* CMD38 = 0x66 */
- #define SD_CMD_SD_APP_OP_COND 41 /* CMD41 = 0x69 */
- #define SD_CMD_APP_CMD 55 /* CMD55 = 0x77 */
- #define SD_CMD_READ_OCR 58 /* CMD55 = 0x79 */
- #define SD_DEFAULT_BLOCK_SIZE (512)
- #define SD_DBG DBG_INFO
- enum
- {
- DEV_SDCARD_SPI_DONE = SERVICE_EVENT_ID_START + 1,
- SDCARD_STATE_IDLE = 0,
- SDCARD_STATE_RUN,
- SDCARD_STATE_READ,
- SDCARD_STATE_WRITE,
- };
- static void SDHC_SpiCS(SDHC_SPICtrlStruct *Ctrl, uint8_t OnOff)
- {
- uint8_t Temp[1] = {0xff};
- GPIO_Output(Ctrl->CSPin, !OnOff);
- if (!OnOff)
- {
- SPI_BlockTransfer(Ctrl->SpiID, Temp, Temp, 1);
- }
- }
- static int32_t SPIFlash_SpiIrqCB(void *pData, void *pParam)
- {
- SDHC_SPICtrlStruct *Ctrl = (SDHC_SPICtrlStruct *)pParam;
- #ifdef __BUILD_OS__
- if (Ctrl->NotifyTask)
- {
- Task_SendEvent(Ctrl->NotifyTask, DEV_SDHC_SPI_DONE, 0, 0, 0);
- }
- #endif
- return 0;
- }
- static uint8_t CRC7(uint8_t * chr, int cnt)
- {
- int i,a;
- uint8_t crc,Data;
- crc=0;
- for (a=0;a<cnt;a++)
- {
- Data=chr[a];
- for (i=0;i<8;i++)
- {
- crc <<= 1;
- if ((Data & 0x80)^(crc & 0x80))
- crc ^=0x09;
- Data <<= 1;
- }
- }
- crc=(crc<<1)|1;
- return(crc);
- }
- static void SDHC_SpiXfer(SDHC_SPICtrlStruct *Ctrl, uint8_t *Buf, uint16_t TxLen)
- {
- #ifdef __BUILD_OS__
- Task_EventStruct Event;
- #endif
- #ifdef __BUILD_OS__
- if (Ctrl->NotifyTask && Ctrl->TaskCB)
- {
- Ctrl->SPIError = 0;
- SPI_SetCallbackFun(Ctrl->SpiID, SPIFlash_SpiIrqCB, Ctrl);
- SPI_Transfer(Ctrl->SpiID, Buf, Buf, TxLen, Ctrl->IsSpiDMAMode);
- if (Task_GetEvent(Ctrl->NotifyTask, DEV_SDHC_SPI_DONE, &Event, Ctrl->TaskCB, TxLen * CORE_TICK_1US + CORE_TICK_1MS))
- {
- Ctrl->SPIError = 1;
- SPI_TransferStop(Ctrl->SpiID);
- }
- SPI_SetCallbackFun(Ctrl->SpiID, NULL, NULL);
- }
- else
- #endif
- {
- SPI_BlockTransfer(Ctrl->SpiID, Buf, Buf, TxLen);
- }
- }
- static int32_t SDHC_SpiCmd(SDHC_SPICtrlStruct *Ctrl, uint8_t Cmd, uint32_t Arg, uint8_t NeedStop)
- {
- uint64_t OpEndTick;
- uint8_t i, TxLen, DummyLen;
- int32_t Result = -ERROR_OPERATION_FAILED;
- SDHC_SpiCS(Ctrl, 1);
- Ctrl->TempData[0] = 0x40|Cmd;
- BytesPutBe32(Ctrl->TempData + 1, Arg);
- Ctrl->TempData[5] = CRC7(Ctrl->TempData, 5);
- memset(Ctrl->TempData + 6, 0xff, 8);
- TxLen = 14;
- if (Ctrl->IsPrintData)
- {
- DBG_HexPrintf(Ctrl->TempData, TxLen);
- }
- Ctrl->SPIError = 0;
- Ctrl->SDHCError = 0;
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, TxLen);
- if (Ctrl->IsPrintData)
- {
- DBG_HexPrintf(Ctrl->TempData, TxLen);
- }
- for(i = 7; i < TxLen; i++)
- {
- if (Ctrl->TempData[i] != 0xff)
- {
- Ctrl->SDHCState = Ctrl->TempData[i];
- if ((Ctrl->SDHCState == !Ctrl->IsInitDone) || !Ctrl->SDHCState)
- {
- Result = ERROR_NONE;
- }
- DummyLen = TxLen - i - 1;
- memcpy(Ctrl->ExternResult, &Ctrl->TempData[i + 1], DummyLen);
- Ctrl->ExternLen = DummyLen;
- break;
- }
- }
- if (NeedStop)
- {
- SDHC_SpiCS(Ctrl, 0);
- }
- return Result;
- }
- static int32_t SDHC_SpiReadRegData(SDHC_SPICtrlStruct *Ctrl, uint8_t *RegDataBuf, uint8_t DataLen)
- {
- uint64_t OpEndTick;
- int Result = ERROR_NONE;
- uint16_t DummyLen;
- uint16_t i,findResult;
- Ctrl->SPIError = 0;
- Ctrl->SDHCError = 0;
- OpEndTick = GetSysTick() + Ctrl->SDHCReadBlockTo;
- findResult = 0;
- for(i = 0; i < Ctrl->ExternLen; i++)
- {
- if (0xfe == Ctrl->ExternResult[i])
- {
- DummyLen = Ctrl->ExternLen - i - 1;
- if (Ctrl->IsPrintData)
- {
- DBG_HexPrintf(&Ctrl->ExternResult[i], DummyLen + 1);
- }
- memcpy(RegDataBuf, &Ctrl->ExternResult[i + 1], DummyLen);
- memset(RegDataBuf + DummyLen, 0xff, DataLen - DummyLen);
- SDHC_SpiXfer(Ctrl, RegDataBuf + DummyLen, DataLen - DummyLen);
- if (Ctrl->IsPrintData)
- {
- DBG_HexPrintf(RegDataBuf + DummyLen, DataLen - DummyLen);
- }
- goto SDHC_SPIREADREGDATA_DONE;
- }
- }
- while((GetSysTick() < OpEndTick) && !Ctrl->SDHCError)
- {
- memset(Ctrl->TempData, 0xff, 40);
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, 40);
- if (Ctrl->IsPrintData)
- {
- DBG_HexPrintf(Ctrl->TempData, 40);
- }
- for(i = 0; i < 40; i++)
- {
- if (0xfe == Ctrl->TempData[i])
- {
- DummyLen = 40 - i - 1;
- if (DummyLen >= DataLen)
- {
- memcpy(RegDataBuf, &Ctrl->TempData[i + 1], DataLen);
- goto SDHC_SPIREADREGDATA_DONE;
- }
- else
- {
- memcpy(RegDataBuf, &Ctrl->TempData[i + 1], DummyLen);
- memset(RegDataBuf + DummyLen, 0xff, DataLen - DummyLen);
- SDHC_SpiXfer(Ctrl, RegDataBuf + DummyLen, DataLen - DummyLen);
- goto SDHC_SPIREADREGDATA_DONE;
- }
- }
- }
- }
- Result = -ERROR_OPERATION_FAILED;
- SDHC_SPIREADREGDATA_DONE:
- SDHC_SpiCS(Ctrl, 0);
- return Result;
- }
- static int32_t SDHC_SpiWriteBlockData(SDHC_SPICtrlStruct *Ctrl)
- {
- uint64_t OpEndTick;
- int Result = -ERROR_OPERATION_FAILED;
- uint16_t TxLen, DoneFlag, waitCnt;
- uint16_t i, crc16;
- uint8_t *pBuf;
- Ctrl->SPIError = 0;
- Ctrl->SDHCError = 0;
- OpEndTick = GetSysTick() + Ctrl->SDHCWriteBlockTo * CORE_TICK_1MS;
- while( (Ctrl->DataBuf.Pos < Ctrl->DataBuf.MaxLen) && (GetSysTick() < OpEndTick) )
- {
- Ctrl->TempData[0] = 0xff;
- Ctrl->TempData[1] = 0xff;
- //SD_DBG("%u,%u", Ctrl->DataBuf.Pos, Ctrl->DataBuf.MaxLen);
- Ctrl->TempData[2] = 0xfc;
- memcpy(Ctrl->TempData + 3, Ctrl->DataBuf.Data + Ctrl->DataBuf.Pos * __SDHC_BLOCK_LEN__, __SDHC_BLOCK_LEN__);
- crc16 = CRC16Cal(Ctrl->DataBuf.Data + Ctrl->DataBuf.Pos * __SDHC_BLOCK_LEN__, __SDHC_BLOCK_LEN__, 0, CRC16_CCITT_GEN, 0);
- BytesPutBe16(Ctrl->TempData + 3 + __SDHC_BLOCK_LEN__, crc16);
- Ctrl->TempData[5 + __SDHC_BLOCK_LEN__] = 0xff;
- TxLen = 6 + __SDHC_BLOCK_LEN__;
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, TxLen);
- if ((Ctrl->TempData[5 + __SDHC_BLOCK_LEN__] & 0x1f) != 0x05)
- {
- DBG("write data error ! x%02x", Ctrl->TempData[5 + __SDHC_BLOCK_LEN__]);
- Ctrl->SDHCError = 1;
- goto SDHC_SPIWRITEBLOCKDATA_DONE;
- }
- DoneFlag = 0;
- waitCnt = 0;
- while( (GetSysTick() < OpEndTick) && !DoneFlag )
- {
- TxLen = Ctrl->WriteWaitCnt?Ctrl->WriteWaitCnt:40;
- memset(Ctrl->TempData, 0xff, TxLen);
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, TxLen);
- for(i = 0; i < TxLen; i++)
- {
- if (Ctrl->TempData[i] == 0xff)
- {
- DoneFlag = 1;
- if ((i + waitCnt) < sizeof(Ctrl->TempData))
- {
- if ((i + waitCnt) != Ctrl->WriteWaitCnt)
- {
- // DBG("%u", Ctrl->WriteWaitCnt);
- Ctrl->WriteWaitCnt = i + waitCnt;
- }
- }
- break;
- }
- }
- waitCnt += TxLen;
- }
- if (!DoneFlag)
- {
- DBG("write data timeout!");
- Ctrl->SDHCError = 1;
- goto SDHC_SPIWRITEBLOCKDATA_DONE;
- }
- Ctrl->DataBuf.Pos++;
- OpEndTick = GetSysTick() + Ctrl->SDHCWriteBlockTo * CORE_TICK_1MS;
- }
- Result = ERROR_NONE;
- SDHC_SPIWRITEBLOCKDATA_DONE:
- Ctrl->TempData[0] = 0xfd;
- SPI_BlockTransfer(Ctrl->SpiID, Ctrl->TempData, Ctrl->TempData, 1);
- OpEndTick = GetSysTick() + Ctrl->SDHCWriteBlockTo * CORE_TICK_1MS * Ctrl->DataBuf.MaxLen;
- DoneFlag = 0;
- while( (GetSysTick() < OpEndTick) && !DoneFlag )
- {
- TxLen = sizeof(Ctrl->TempData);
- memset(Ctrl->TempData, 0xff, TxLen);
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, TxLen);
- for(i = 0; i < TxLen; i++)
- {
- if (Ctrl->TempData[i] == 0xff)
- {
- DoneFlag = 1;
- break;
- }
- }
- }
- SDHC_SpiCS(Ctrl, 0);
- return Result;
- }
- static int32_t SDHC_SpiReadBlockData(SDHC_SPICtrlStruct *Ctrl)
- {
- uint64_t OpEndTick;
- int Result = -ERROR_OPERATION_FAILED;
- uint16_t ReadLen, DummyLen, RemainingLen;
- uint16_t i, crc16, crc16_check;
- uint8_t *pBuf;
- Ctrl->SPIError = 0;
- Ctrl->SDHCError = 0;
- OpEndTick = GetSysTick() + Ctrl->SDHCReadBlockTo * CORE_TICK_1MS;
- while( (Ctrl->DataBuf.Pos < Ctrl->DataBuf.MaxLen) && (GetSysTick() < OpEndTick) )
- {
- DummyLen = (__SDHC_BLOCK_LEN__ >> 1);
- memset(Ctrl->TempData, 0xff, DummyLen);
- // SD_DBG("%u,%u", Ctrl->DataBuf.Pos, Ctrl->DataBuf.MaxLen);
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, DummyLen);
- RemainingLen = 0;
- for(i = 0; i < DummyLen; i++)
- {
- if (Ctrl->TempData[i] == 0xfe)
- {
- ReadLen = (DummyLen - i - 1);
- RemainingLen = __SDHC_BLOCK_LEN__ - ReadLen;
- if (ReadLen)
- {
- memcpy(Ctrl->DataBuf.Data + Ctrl->DataBuf.Pos * __SDHC_BLOCK_LEN__, Ctrl->TempData + i + 1, ReadLen);
- }
- // SD_DBG("%u,%u", ReadLen, RemainingLen);
- goto READ_REST_DATA;
- }
- }
- continue;
- READ_REST_DATA:
- pBuf = Ctrl->DataBuf.Data + Ctrl->DataBuf.Pos * __SDHC_BLOCK_LEN__ + ReadLen;
- memset(pBuf, 0xff, RemainingLen);
- SDHC_SpiXfer(Ctrl, pBuf, RemainingLen);
- memset(Ctrl->TempData, 0xff, 2);
- SPI_BlockTransfer(Ctrl->SpiID, Ctrl->TempData, Ctrl->TempData, 2);
- crc16 = CRC16Cal(Ctrl->DataBuf.Data + Ctrl->DataBuf.Pos * __SDHC_BLOCK_LEN__, __SDHC_BLOCK_LEN__, 0, CRC16_CCITT_GEN, 0);
- crc16_check = BytesGetBe16(Ctrl->TempData);
- if (crc16 != crc16_check)
- {
- DBG("crc16 error %04x %04x", crc16, crc16_check);
- Result = ERROR_NONE;
- goto SDHC_SPIREADBLOCKDATA_DONE;
- }
- Ctrl->DataBuf.Pos++;
- OpEndTick = GetSysTick() + Ctrl->SDHCReadBlockTo * CORE_TICK_1MS;
- }
- Result = ERROR_NONE;
- SDHC_SPIREADBLOCKDATA_DONE:
- return Result;
- }
- void SDHC_SpiInitCard(void *pSDHC)
- {
- uint8_t i;
- uint64_t OpEndTick;
- SDHC_SPICtrlStruct *Ctrl = (SDHC_SPICtrlStruct *)pSDHC;
- memset(Ctrl->TempData, 0xff, 20);
- Ctrl->IsInitDone = 0;
- Ctrl->SDHCState = 0xff;
- Ctrl->Info.CardCapacity = 0;
- Ctrl->WriteWaitCnt = 40;
- GPIO_Output(Ctrl->CSPin, 0);
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, 20);
- GPIO_Output(Ctrl->CSPin, 1);
- memset(Ctrl->TempData, 0xff, 20);
- SDHC_SpiXfer(Ctrl, Ctrl->TempData, 20);
- Ctrl->IsMMC = 0;
- if (SDHC_SpiCmd(Ctrl, CMD0, 0, 1))
- {
- goto INIT_DONE;
- }
- OpEndTick = GetSysTick() + 1 * CORE_TICK_1S;
- if (SDHC_SpiCmd(Ctrl, CMD8, 0x1aa, 1)) //只支持2G以上的SDHC卡
- {
- goto INIT_DONE;
- }
- WAIT_INIT_DONE:
- if (GetSysTick() >= OpEndTick)
- {
- goto INIT_DONE;
- }
- if (SDHC_SpiCmd(Ctrl, SD_CMD_APP_CMD, 0, 1))
- {
- goto INIT_DONE;
- }
- if (SDHC_SpiCmd(Ctrl, SD_CMD_SD_APP_OP_COND, 0x40000000, 1))
- {
- goto INIT_DONE;
- }
- Ctrl->IsInitDone = !Ctrl->SDHCState;
- if (!Ctrl->IsInitDone)
- {
- goto WAIT_INIT_DONE;
- }
- if (SDHC_SpiCmd(Ctrl, CMD58, 0, 1))
- {
- goto INIT_DONE;
- }
- Ctrl->OCR = BytesGetBe32(Ctrl->ExternResult);
- // SD_DBG("sdcard init OK OCR:0x%08x!", Ctrl->OCR);
- return;
- INIT_DONE:
- if (!Ctrl->IsInitDone)
- {
- SD_DBG("sdcard init fail!");
- }
- return;
- }
- void SDHC_SpiReadCardConfig(void *pSDHC)
- {
- SDHC_SPICtrlStruct *Ctrl = (SDHC_SPICtrlStruct *)pSDHC;
- uint8_t CSD_Tab[18];
- uint8_t CID_Tab[18];
- SD_CSD* Csd = &Ctrl->Info.Csd;
- SD_CID* Cid = &Ctrl->Info.Cid;
- SD_CardInfo *pCardInfo = &Ctrl->Info;
- uint64_t Temp;
- uint8_t flag_SDHC = (Ctrl->OCR & 0x40000000) >> 30;
- if (Ctrl->Info.CardCapacity) return;
- if (SDHC_SpiCmd(Ctrl, CMD9, 0, 0))
- {
- goto READ_CONFIG_ERROR;
- }
- if (Ctrl->SDHCState)
- {
- goto READ_CONFIG_ERROR;
- }
- if (SDHC_SpiReadRegData(Ctrl, CSD_Tab, 18))
- {
- goto READ_CONFIG_ERROR;
- }
- /*************************************************************************
- CSD header decoding
- *************************************************************************/
- /* Byte 0 */
- Csd->CSDStruct = (CSD_Tab[0] & 0xC0) >> 6;
- Csd->Reserved1 = CSD_Tab[0] & 0x3F;
- /* Byte 1 */
- Csd->TAAC = CSD_Tab[1];
- /* Byte 2 */
- Csd->NSAC = CSD_Tab[2];
- /* Byte 3 */
- Csd->MaxBusClkFrec = CSD_Tab[3];
- /* Byte 4/5 */
- Csd->CardComdClasses = (CSD_Tab[4] << 4) | ((CSD_Tab[5] & 0xF0) >> 4);
- Csd->RdBlockLen = CSD_Tab[5] & 0x0F;
- /* Byte 6 */
- Csd->PartBlockRead = (CSD_Tab[6] & 0x80) >> 7;
- Csd->WrBlockMisalign = (CSD_Tab[6] & 0x40) >> 6;
- Csd->RdBlockMisalign = (CSD_Tab[6] & 0x20) >> 5;
- Csd->DSRImpl = (CSD_Tab[6] & 0x10) >> 4;
- /*************************************************************************
- CSD v1/v2 decoding
- *************************************************************************/
- if(!flag_SDHC)
- {
- Csd->version.v1.Reserved1 = ((CSD_Tab[6] & 0x0C) >> 2);
- Csd->version.v1.DeviceSize = ((CSD_Tab[6] & 0x03) << 10)
- | (CSD_Tab[7] << 2)
- | ((CSD_Tab[8] & 0xC0) >> 6);
- Csd->version.v1.MaxRdCurrentVDDMin = (CSD_Tab[8] & 0x38) >> 3;
- Csd->version.v1.MaxRdCurrentVDDMax = (CSD_Tab[8] & 0x07);
- Csd->version.v1.MaxWrCurrentVDDMin = (CSD_Tab[9] & 0xE0) >> 5;
- Csd->version.v1.MaxWrCurrentVDDMax = (CSD_Tab[9] & 0x1C) >> 2;
- Csd->version.v1.DeviceSizeMul = ((CSD_Tab[9] & 0x03) << 1)
- |((CSD_Tab[10] & 0x80) >> 7);
- }
- else
- {
- Csd->version.v2.Reserved1 = ((CSD_Tab[6] & 0x0F) << 2) | ((CSD_Tab[7] & 0xC0) >> 6);
- Csd->version.v2.DeviceSize= ((CSD_Tab[7] & 0x3F) << 16) | (CSD_Tab[8] << 8) | CSD_Tab[9];
- Csd->version.v2.Reserved2 = ((CSD_Tab[10] & 0x80) >> 8);
- }
- Csd->EraseSingleBlockEnable = (CSD_Tab[10] & 0x40) >> 6;
- Csd->EraseSectorSize = ((CSD_Tab[10] & 0x3F) << 1)
- |((CSD_Tab[11] & 0x80) >> 7);
- Csd->WrProtectGrSize = (CSD_Tab[11] & 0x7F);
- Csd->WrProtectGrEnable = (CSD_Tab[12] & 0x80) >> 7;
- Csd->Reserved2 = (CSD_Tab[12] & 0x60) >> 5;
- Csd->WrSpeedFact = (CSD_Tab[12] & 0x1C) >> 2;
- Csd->MaxWrBlockLen = ((CSD_Tab[12] & 0x03) << 2)
- |((CSD_Tab[13] & 0xC0) >> 6);
- Csd->WriteBlockPartial = (CSD_Tab[13] & 0x20) >> 5;
- Csd->Reserved3 = (CSD_Tab[13] & 0x1F);
- Csd->FileFormatGrouop = (CSD_Tab[14] & 0x80) >> 7;
- Csd->CopyFlag = (CSD_Tab[14] & 0x40) >> 6;
- Csd->PermWrProtect = (CSD_Tab[14] & 0x20) >> 5;
- Csd->TempWrProtect = (CSD_Tab[14] & 0x10) >> 4;
- Csd->FileFormat = (CSD_Tab[14] & 0x0C) >> 2;
- Csd->Reserved4 = (CSD_Tab[14] & 0x03);
- Csd->crc = (CSD_Tab[15] & 0xFE) >> 1;
- Csd->Reserved5 = (CSD_Tab[15] & 0x01);
- #if 0
- if (SDHC_SpiCmd(Ctrl, CMD10, 0, 0))
- {
- goto READ_CONFIG_ERROR;
- }
- if (Ctrl->SDHCState)
- {
- goto READ_CONFIG_ERROR;
- }
- if (SDHC_SpiReadRegData(Ctrl, CID_Tab, 18))
- {
- goto READ_CONFIG_ERROR;
- }
- /* Byte 0 */
- Cid->ManufacturerID = CID_Tab[0];
- /* Byte 1 */
- Cid->OEM_AppliID = CID_Tab[1] << 8;
- /* Byte 2 */
- Cid->OEM_AppliID |= CID_Tab[2];
- /* Byte 3 */
- Cid->ProdName1 = CID_Tab[3] << 24;
- /* Byte 4 */
- Cid->ProdName1 |= CID_Tab[4] << 16;
- /* Byte 5 */
- Cid->ProdName1 |= CID_Tab[5] << 8;
- /* Byte 6 */
- Cid->ProdName1 |= CID_Tab[6];
- /* Byte 7 */
- Cid->ProdName2 = CID_Tab[7];
- /* Byte 8 */
- Cid->ProdRev = CID_Tab[8];
- /* Byte 9 */
- Cid->ProdSN = CID_Tab[9] << 24;
- /* Byte 10 */
- Cid->ProdSN |= CID_Tab[10] << 16;
- /* Byte 11 */
- Cid->ProdSN |= CID_Tab[11] << 8;
- /* Byte 12 */
- Cid->ProdSN |= CID_Tab[12];
- /* Byte 13 */
- Cid->Reserved1 |= (CID_Tab[13] & 0xF0) >> 4;
- Cid->ManufactDate = (CID_Tab[13] & 0x0F) << 8;
- /* Byte 14 */
- Cid->ManufactDate |= CID_Tab[14];
- /* Byte 15 */
- Cid->CID_CRC = (CID_Tab[15] & 0xFE) >> 1;
- Cid->Reserved2 = 1;
- #endif
- if(flag_SDHC)
- {
- pCardInfo->LogBlockSize = 512;
- pCardInfo->CardBlockSize = 512;
- Temp = 1024 * pCardInfo->LogBlockSize;
- pCardInfo->CardCapacity = (pCardInfo->Csd.version.v2.DeviceSize + 1) * Temp;
- pCardInfo->LogBlockNbr = (pCardInfo->Csd.version.v2.DeviceSize + 1) * 1024;
- }
- else
- {
- pCardInfo->CardCapacity = (pCardInfo->Csd.version.v1.DeviceSize + 1) ;
- pCardInfo->CardCapacity *= (1 << (pCardInfo->Csd.version.v1.DeviceSizeMul + 2));
- pCardInfo->LogBlockSize = 512;
- pCardInfo->CardBlockSize = 1 << (pCardInfo->Csd.RdBlockLen);
- pCardInfo->CardCapacity *= pCardInfo->CardBlockSize;
- pCardInfo->LogBlockNbr = (pCardInfo->CardCapacity) / (pCardInfo->LogBlockSize);
- }
- // DBG("卡容量 %lluKB", pCardInfo->CardCapacity/1024);
- return;
- READ_CONFIG_ERROR:
- Ctrl->IsInitDone = 0;
- Ctrl->SDHCError = 1;
- return;
- }
- void SDHC_SpiReadBlocks(void *pSDHC, uint8_t *Buf, uint32_t StartLBA, uint32_t BlockNums)
- {
- uint8_t Retry = 0;
- SDHC_SPICtrlStruct *Ctrl = (SDHC_SPICtrlStruct *)pSDHC;
- Buffer_StaticInit(&Ctrl->DataBuf, Buf, BlockNums);
- SDHC_SPIREADBLOCKS_START:
- if (SDHC_SpiCmd(Ctrl, CMD18, StartLBA + Ctrl->DataBuf.Pos, 0))
- {
- goto SDHC_SPIREADBLOCKS_ERROR;
- }
- if (SDHC_SpiReadBlockData(Ctrl))
- {
- goto SDHC_SPIREADBLOCKS_ERROR;
- }
- if (SDHC_SpiCmd(Ctrl, CMD12, 0, 1))
- {
- goto SDHC_SPIREADBLOCKS_ERROR;
- }
- if (Ctrl->DataBuf.Pos != Ctrl->DataBuf.MaxLen)
- {
- Retry++;
- DBG("%d", Retry);
- if (Retry > 3)
- {
- Ctrl->SDHCError = 1;
- goto SDHC_SPIREADBLOCKS_ERROR;
- }
- goto SDHC_SPIREADBLOCKS_START;
- }
- return;
- SDHC_SPIREADBLOCKS_ERROR:
- DBG("!");
- Ctrl->IsInitDone = 0;
- Ctrl->SDHCError = 1;
- return;
- }
- void SDHC_SpiWriteBlocks(void *pSDHC, const uint8_t *Buf, uint32_t StartLBA, uint32_t BlockNums)
- {
- uint8_t Retry = 0;
- SDHC_SPICtrlStruct *Ctrl = (SDHC_SPICtrlStruct *)pSDHC;
- Buffer_StaticInit(&Ctrl->DataBuf, Buf, BlockNums);
- SDHC_SPIREADBLOCKS_START:
- if (SDHC_SpiCmd(Ctrl, CMD25, StartLBA + Ctrl->DataBuf.Pos, 0))
- {
- goto SDHC_SPIREADBLOCKS_ERROR;
- }
- if (SDHC_SpiWriteBlockData(Ctrl))
- {
- goto SDHC_SPIREADBLOCKS_ERROR;
- }
- if (Ctrl->DataBuf.Pos != Ctrl->DataBuf.MaxLen)
- {
- Retry++;
- if (Retry > 3)
- {
- Ctrl->SDHCError = 1;
- goto SDHC_SPIREADBLOCKS_ERROR;
- }
- goto SDHC_SPIREADBLOCKS_START;
- }
- return;
- SDHC_SPIREADBLOCKS_ERROR:
- Ctrl->IsInitDone = 0;
- Ctrl->SDHCError = 1;
- return;
- }
- void *SDHC_SpiCreate(uint8_t SpiID, uint8_t CSPin)
- {
- SDHC_SPICtrlStruct *Ctrl = zalloc(sizeof(SDHC_SPICtrlStruct));
- Ctrl->CSPin = CSPin;
- Ctrl->SpiID = SpiID;
- Ctrl->SDHCReadBlockTo = 5 * CORE_TICK_1MS;
- Ctrl->SDHCWriteBlockTo = 25 * CORE_TICK_1MS;
- // Ctrl->IsPrintData = 1;
- return Ctrl;
- }
- uint32_t SDHC_GetLogBlockNbr(void *pSDHC)
- {
- SDHC_SPICtrlStruct *Ctrl = (SDHC_SPICtrlStruct *)pSDHC;
- return Ctrl->Info.LogBlockNbr;
- }
- uint8_t SDHC_IsReady(void *pSDHC)
- {
- SDHC_SPICtrlStruct *Ctrl = (SDHC_SPICtrlStruct *)pSDHC;
- if (!Ctrl->SDHCState && Ctrl->IsInitDone)
- {
- return 1;
- }
- else
- {
- return 0;
- }
- }
|