📄 sdi.c
字号:
{
U32 CmdIndex;
//rSDICARG = rSDICARG & ~(0xffffffff) | CmdArg;
rSDICARG = CmdArg;
CmdIndex = Command | 0x40;
rSDICCON = (WithData<<11)|(LongResp<<10)|(WaitResp<<9)|(CmdIndex);
//Command Start
rSDICCON |= (1<<8);
}
void SDIO_BlockSizeSetting(U32 Size)
{
rSDIBSIZE = (Size & 0xFFF);
}
void SDIO_TypeSetting(U32 ClkType, U32 ByteType)
{
if(ClkType == SDIO_SD_TYPE)
rSDICON &= ~CLOCK_TYPE;
else if(ClkType == SDIO_MMC_TYPE)
rSDICON |= CLOCK_TYPE;
if(ByteType == SDIO_TYPE_A)
rSDICON &= ~BYTE_ORDER;
else if(ByteType == SDIO_TYPE_B)
rSDICON |= BYTE_ORDER;
}
int Check_CMDend(CommandType cmd, int be_resp)
//0: Timeout
{
int finish0;
if(!be_resp) // No response
{
finish0=rSDICSTA;
while((finish0&CMD_END)!=CMD_END) // Check cmd end
finish0=rSDICSTA;
rSDICSTA=finish0;// Clear cmd end state
return 1;
}
else // With response
{
finish0=rSDICSTA;
while( !( (finish0&RESP_END) | (finish0&CMD_TOUT) )) // Check cmd/rsp end
finish0=rSDICSTA;
if(cmd==SEND_OP_CMD | cmd==41) // CRC no check, CMD9 is a long Resp. command.
{
if( (finish0&0xf00) != CMD_END|RESP_END ) // Check error
{
rSDICSTA=finish0; // Clear error state
if(((finish0&CMD_TOUT)==CMD_TOUT))
return 0; // Timeout error
}
rSDICSTA=finish0; // Clear cmd & rsp end state
}
else // CRC check
{
if( (finish0&0x1f00) != CMD_END|RESP_END) // Check error
{
//printf("CMD%d:rSDICSTA=0x%x, rSDIRSP0=0x%x\n",cmd, rSDICSTA, rSDIRSP0);
rSDICSTA=finish0; // Clear error state
if(((finish0&CMD_TOUT)==CMD_TOUT))
return 0; // Timeout error
}
rSDICSTA=finish0;
}
return 1;
}
}
int Check_BUSYend(void)
{
int finish;
#if 1
while ( 1 ) {
finish=rSDIDSTA;
if ( finish & (1<<3) ) {
// printf ("busy finish %x\n", finish );
break;
}
else if ( finish & (1<<4) ) {
// printf ("data finish %x\n", finish );
return 0;
}
else if ( finish & (1<<5) ) {
// printf ( "timeout %x\n", finish );
break;
}
else {
}
}
#else
finish=rSDIDSTA;
printf("\nBusy end =%x",finish);
while( !( ((finish&(1<<3))==(1<<3)) | ((finish&(1<<5))==(1<<5)) ))
finish=rSDIDSTA;
while( (finish&(1<<3)) != (1<<3) )
{
printf("\nDATA:finish=0x%x\n", finish);
finish=rSDIDSTA;
//return 0;
}
#endif
rSDIDSTA=0xf4; //clear error state
return 1;
}
CardType Check_OCR(void) {
int i;
// MMC Command include OCR Command But, SD Command is OCR CMD after APP Command.
// MMC Card Test
for(i=0;i<600;i++) { // original 200 time -> 600 with VDD range 2.7 ~ 3.6V(0xFF8000)
SDIO_Command(0xff8000, SEND_OP_CMD, SDIO_WAIT_RESP, SDIO_SHORT_RESP, SDIO_WITHOUT_DATA);
if(Check_CMDend(SEND_OP_CMD, 1)) {
if(rSDIRSP0==0x80ff8080) {
rSDICSTA |= CMD_END|RESP_END;
printf("\n\n[In MoviNand Memory ready....]\n");
return MOVI_NAND_CARD;
}
else if((rSDIRSP0>>16)==0x80ff) { //[31]:Card Power up status bit (busy)
rSDICSTA |= CMD_END|RESP_END;
printf("\n\n[In MMC Memory ready....]\n");
return MMC_CARD; // Success
}
}
}
// SD Card Test
RCA = 0; // initially RCA must set zero.
for(i=0;i<600;i++) {// original 200 time -> 600
SDIO_Command((RCA<<16), APP_CMD, SDIO_WAIT_RESP, SDIO_SHORT_RESP, SDIO_WITH_DATA);
while(Check_CMDend(APP_CMD, 1) != 1)
{
printf("\nCommand55 Fail...");
return ERROR_CARD;
}
// 41 - SD_SEND_OP_COND with VDD range 2.7 ~ 3.6V(0xFF8000)
SDIO_Command(0xff8000, 41, SDIO_WAIT_RESP, SDIO_SHORT_RESP, SDIO_WITHOUT_DATA);
// Detecting Busy signal mean SD Card initialization
// Busy signal is asserted by not finished power up sequence.
if( Check_CMDend(41, 1) & rSDIRSP0==0x80ff8000 )
{
rSDICSTA= CMD_END|RESP_END; // Clear cmd_end(with rsp)
printf("\n\n[In SD/TFlash Memory Ready State....]\n");
return SD_CARD; // Success
}
Delay(200); // Wait Card power up status
}
return ERROR_CARD;
}
#if 0
int Check_DATend(void)
{
int finish;
finish=rSDIDSTA;
while( !( ((finish&0x10)==0x10) || ((finish&0x20)==0x20) ))// Chek timeout or data end
{
//printf("\nData End Check =%x",finish);
finish=rSDIDSTA;
}
if( (finish &0x10) != 0x10 )
{
//printf("\nDATA:finish=0x%x\n", finish);
rSDIDSTA=finish; // Clear error state
return 0;
}
return 1;
}
#else
int Check_DATend(void)
{
int finish;
// finish=rSDIDSTA;
//printf("DATA:finish=0x%x\n", finish);
// printf("DATA end check\n");
while(1) {
finish=rSDIDSTA;
if ( finish & DATA_FINISH )
return 1;
if ( finish & DATA_TOUT ) {
printf ("Data time out\n");
break;
}
if ( finish & BUSY_FINISH ) {
printf ("Busy Finish\n");
break;
}
if ( finish & CRC_STAT_FAIL ) {
printf ( "CRC_STAT_FAIL\n");
break;
}
if ( finish & RECEIVE_CRC_FAIL ) {
printf ( "RECEIVE_CRC_FAIL\n");
break;
}
}
/*
while( !((finish&DATA_FINISH)==DATA_FINISH))// Chek timeout or data end
{
printf("x");
finish=rSDIDSTA;
}
printf ( "Check_DATend End\n" );
if( (rSDIDSTA&0xfc) != DATA_FINISH )
{
//printf("DATA:finish=0x%x\n", finish);
rSDIDSTA=0xec; // Clear error state
return 0;
}
*/
rSDIDSTA=0xec; // Clear error state
return 0;
}
#endif
int Check_DATend2(void)
{
int finish;
int i;
while(1) {
finish=rSDIDSTA;
if ( finish & DATA_FINISH )
return 1;
if ( finish & DATA_TOUT ) {
printf ("Data time out\n");
// rSDIDCON = (rSDIDCON & ~(0x3<<12)) | (1<<12);
break;
}
if ( finish & BUSY_FINISH ) {
printf ("Busy Finish\n");
break;
}
if ( finish & CRC_STAT_FAIL ) {
// printf ( "CRC_STAT_FAIL\n");
break;
}
if ( finish & RECEIVE_CRC_FAIL ) {
printf ( "RECEIVE_CRC_FAIL\n");
break;
}
}
// rSDIDSTA=0xec; // Clear error state
return 0;
}
void __irq DMA_end(void)
{
//printf("\nDMA ISR\n");
//rSUBSRCPND |= BIT_SUB_DMA0;
ClearPending(BIT_DMA0);
TR_end=1;
}
void __irq Rd_Int(void)
{
U32 i,status;
rINTSUBMSK |= BIT_SUB_SDI;
rINTMSK |= BIT_SDI_CF;
rSUBSRCPND |= BIT_SUB_SDI;
ClearPending(BIT_SDI_CF);
status=rSDIFSTA;
if( (status & (1<<9) ) == (1<<9) ) // Check Last interrupt?
{
for(i=(status & 0x7f)/4;i>0;i--)
{
*Rx_buffer++=rSDIDAT;
rd_cnt++;
}
rSDIFSTA = rSDIFSTA & (1<<9); //Clear Rx FIFO Last data Ready, YH 040221
}
else if( (status&0x80) == 0x80 ) // Check Half interrupt?
{
// FIFO size is 8 word.
for(i=0;i<8;i++)
{
*Rx_buffer++=rSDIDAT;
rd_cnt++;
}
}
rINTMSK &= ~(BIT_SDI_CF);
rINTSUBMSK &= ~(BIT_SUB_SDI);
}
void __irq Wt_Int(void)
{
rINTSUBMSK |= BIT_SUB_SDI;
rINTMSK |= BIT_SDI_CF;
rSUBSRCPND |= BIT_SUB_SDI;
ClearPending(BIT_SDI_CF);
rINTMSK |= (BIT_SDI_CF);
rSDIDAT=*Tx_buffer++;
wt_cnt++;
if(wt_cnt==(Card_OneBlockSize/4)*BlockNum)
{
rINTMSK |= BIT_SDI_CF;
rSDIDAT=*Tx_buffer;
TR_end=1;
}
rINTMSK &= ~(BIT_SDI_CF);
rINTSUBMSK &= ~(BIT_SUB_SDI);
}
void stream_write_test ( void ) {
int i, Offset;
int status;
BlockNum = 10;
Offset = 0;
rSDICON |=(1<<5); // YH 0519, MMC Type SDCLK
rSDIFSTA |=(1<<16); //FIFO reset
Delay(10); // wait until FIFO reset.
wt_cnt = 0;
Tx_buffer = (U32 *)SDI_Tx_buffer;
for(i=0 ; i<(Card_OneBlockSize/4*BlockNum) ; i++)
*(Tx_buffer+i) = (i+Offset);
// rSDIDCON=(2<<22)|(1<<20)|(0<<17)|(0<<16)|(3<<12); // stream mode
rSDIDCON=(2<<22)|(1<<20)|(0<<17)|(0<<16)|(1<<14)|(3<<12)|BlockNum; // stream mode
do {
// start address is 0
SDIO_Command( 0, WRITE_DAT_UNTIL_STOP_CMD, SDIO_WAIT_RESP, SDIO_SHORT_RESP, SDIO_WITH_DATA);
} while ( Check_CMDend( WRITE_DAT_UNTIL_STOP_CMD, 1 ) != 1 );
rSDICSTA = CMD_END|RESP_END; // Clear cmd_end(with rsp)
while(wt_cnt<128*BlockNum)
{
// status=rSDIFSTA;
// if((status&TX_FIFO_AVAILABLE_DETECT)==TX_FIFO_AVAILABLE_DETECT)
if(rSDIFSTA&TX_FIFO_AVAILABLE_DETECT)
rSDIDAT=*(Tx_buffer+wt_cnt++);
}
//-- Check end of DATA
while( rSDIFSTA&0x400 );
Delay(10); // for the empty of DATA line(Hardware)
// rSDIDCON=(1<<20)|(0<<17)|(0<<16)|(1<<14)|(0<<12);
rSDIDCON=(1<<20)|(0<<17)|(0<<16); //YH 040220
rSDIDCON=rSDIDCON&~(7<<12); //YH 040220, no operation, data ready
while( (rSDIDSTA&0x3)!=0x0 );
if(rSDIDSTA!=0x0)
printf("rSDIDSTA=0x%x\n", rSDIDSTA);
rSDIDSTA=0xff; //Clear rSDIDSTA
// stop command--------------------------------
// rSDIDCON=(1<<18)|(1<<17)|(0<<16)|(1<<12);
rSDIDCON=(1<<18)|(1<<17)|(0<<16)|(1<<14)|(1<<12);
do {
SDIO_Command( 0, STOP_TRANSMISSION_CMD, TRUE, FALSE, FALSE);
} while ( Check_CMDend( STOP_TRANSMISSION_CMD, TRUE ) !=1 );
rSDICSTA=(1<<11) | (1<<9);//0xa00; // Clear cmd_end(with rsp)
//-- Check end of DATA(with busy state)
if(!Check_BUSYend())
printf("error\n");
rSDIDSTA=0x08;
printf ("end write test \n");
}
void stream_read_test(void)
{
int i;
int status, rd_cnt=0;
printf("\n[Stream read test]\n");
Tx_buffer = (U32 *)SDI_Tx_buffer;
Rx_buffer = (U32 *)SDI_Rx_buffer;
// rSDIDCON=(2<<22)|(1<<19)|(0<<17)|(0<<16)|(2<<12);
rSDIDCON=(2<<22)|(1<<19)|(0<<17)|(0<<16)|(1<<14)|(2<<12);
do {
// start address is 0
SDIO_Command( 0, READ_DAT_CMD, SDIO_WAIT_RESP, SDIO_SHORT_RESP, SDIO_WITH_DATA);
} while ( Check_CMDend( READ_DAT_CMD, 1 ) != 1 );
rSDICSTA=0xa00; // Clear cmd_end(with rsp)
BlockNum = 10;
while(rd_cnt<128*BlockNum)
{
if( (rSDIDSTA&0x20) == 0x20 )
{
printf("Read timeout error");
return ;
}
if ( rSDIFSTA & RX_FIFO_AVAILABLE_DETECT ) {
Rx_buffer[rd_cnt++]=rSDIDAT;
}
}
//-- Check end of DATA
// rSDIDCON=(2<<22)|(1<<19)|(0<<17)|(0<<16)|(1<<14)|(0<<12);
rSDIDCON=(2<<22)|(1<<19)|(0<<17)|(0<<16); //YH 040220
rSDIDCON=rSDIDCON&~(7<<12); //YH 040220, no operation, data ready
// wait until data(rx/tx) progress.
while( rSDIDSTA & ((1<<1)|(1)) != 0x0 );
if(rSDIDSTA!=0)
printf("rSDIDSTA=0x%x\n", rSDIDSTA);
rSDIDSTA=0xff; //YH 040221
do {
// start address is 0
SDIO_Command( 0, STOP_TRANSMISSION_CMD, SDIO_WAIT_RESP, SDIO_SHORT_RESP, SDIO_WITHOUT_DATA);
} while ( Check_CMDend( STOP_TRANSMISSION_CMD, 1 ) != 1 );
rSDICSTA = (1<<11) | (1<<9);// 0xa00; // Clear cmd_end(with rsp)
rSDIFSTA = rSDIFSTA & (1<<9); //Clear Rx FIFO Last data Ready, YH 040221
//-- Display Tx data and Rx Data
for(i=0;i<512/4*BlockNum;i++)
{
if(Rx_buffer[i] != Tx_buffer[i])
{
printf("%08x, %08x\n",Tx_buffer[i], Rx_buffer[i]);
}
}
printf("rSDIFSTA1=0x%x\n", rSDIFSTA); //YH 040221
rSDIFSTA = rSDIFSTA & (1<<9);//0x200; //Clear Rx FIFO Last data Ready, YH 040221
printf("rSDIFSTA2=0x%x\n", rSDIFSTA); //YH 040221
printf("\n--End stream read test\n");
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -