⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sd.c

📁 F:worksip2440a board可启动u-boot-like.tar.gz F:worksip2440a board可启动u-boot-like.tar.gz
💻 C
📖 第 1 页 / 共 2 页
字号:
void Card_sel_desel(char sel_desel){	S3C2410_SDI * const sdi = S3C2410_GetBase_SDI();	//-- Card select or deselect	if(sel_desel)	{RECMDS7:		sdi->SDICARG=RCA<<16;	// CMD7(RCA,stuff bit)		sdi->SDICCON= (0x1<<9)|(0x1<<8)|0x47;   // sht_resp, wait_resp, start, CMD7		//-- Check end of CMD7		if(!Chk_CMDend(7, 1))			goto RECMDS7;		sdi->SDICSTA=0xa00;	// Clear cmd_end(with rsp)		//--State(transfer) check		if( sdi->SDIRSP0 & (0x1e00!=0x800) )			goto RECMDS7;	}	else	{RECMDD7:		sdi->SDICARG=0<<16;		//CMD7(RCA,stuff bit)		sdi->SDICCON=(0x1<<8)|0x47;	//no_resp, start, CMD7		//-- Check end of CMD7		if(!Chk_CMDend(7, 0))			goto RECMDD7;		sdi->SDICSTA=0x800;	// Clear cmd_end(no rsp)	}}void SD_Read(unsigned char * pucdata, unsigned long ulLBA, unsigned long ulSectors);void SD_Write(unsigned char * pucdata, unsigned long ulLBA, unsigned long ulSectors);unsigned int SD_card_init(void);ulong mmc_bread(int dev_num, ulong blknr, ulong blkcnt, ulong *dst){//	int mmc_block_size = MMC_BLOCK_SIZE;//	ulong src = blknr * mmc_block_size + CFG_MMC_BASE;	if(blkcnt==0)	{		printf("Why block_cnt == 0?? \n");		return 0;	}//	mmc_read(src, (uchar *)dst, blkcnt*mmc_block_size);//	printf("mmc_bread LBA=%d, Count=%d\n",blknr,blkcnt);	SD_Read((uchar *)dst, blknr, blkcnt);//	printf("mmc_bread end\n");		return blkcnt;}int mmc_write(uchar *src, ulong dst, int size){	printf("\nmmc_write should not be called !!!!\n");	//SD_Write(}int mmc_read(ulong src, uchar *dst, int size){	printf("\nmmc_read should not be called !!!!\n");	//SD_Write(}#define INICLK	400000#define SDCLK	25000000	#define MMCCLK	15000000	int mmc_init_once = 0;int mmc_init(int verbose){	SD_card_init();	return 0;}#define CFG_MMC_BASE 0int mmc2info(ulong addr){	/* FIXME hard codes to 32 MB device */	if (addr >= CFG_MMC_BASE && addr < CFG_MMC_BASE + (CardSize/512))	{		return 1;	}	return 0;}unsigned int SD_card_init(void){	int i;	unsigned long pclk;	S3C2410_SDI * const sdi = S3C2410_GetBase_SDI();	if(mmc_init_once==1) return 1;// already done !!			pclk = get_PCLK();	//printf("\nSystem Frequency is %dHz\n",pclk);	sdi->SDIPRE = pclk/(INICLK)-1;	// 400KHz	//printf("\nInit. Frequency is %dHz\n",(pclk/(sdi->SDIPRE+1)));	sdi->SDICON=(0<<4)|1;	// Type A, clk enable	(For Little Endian by Salamander)		sdi->SDIFSTA   = sdi->SDIFSTA|(1<<16);	// FIFO reset	sdi->SDIBSIZE  = 0x200;			// 512byte(128word)	sdi->SDIDTIMER = 0x7fffff;		// Set timeout count	for(i=0;i<0x1000;i++);  // Wait 74SDCLK for MMC card	CMD0();  // Goto idel state	//-- Check MMC card OCR	if(Chk_MMC_OCR())	{		printf("\nMMC found.\n");		isMMC=1;		goto RECMD2;	}	//printf("MMC check end!!\n");		//-- Check SD card OCR	if(Chk_SD_OCR()) printf("\nSD found : ");	else	{		printf("\nSD Initialize fail..\n\n");		return 0;	}RECMD2:	//-- Check attaced cards, it makes card identification state	sdi->SDICARG=0x0;   // CMD2(stuff bit)	sdi->SDICCON=(0x1<<10)|(0x1<<9)|(0x1<<8)|0x42; //lng_resp, wait_resp, start, CMD2	//-- Check end of CMD2	if(!Chk_CMDend(2, 1)) 		goto RECMD2;	sdi->SDICSTA=0xa00;	// Clear cmd_end(with rsp)	//printf("\nEnd id\n");RECMD3:	//--Send RCA	sdi->SDICARG = isMMC<<16;	   	// CMD3(MMC:Set RCA, SD:Ask RCA-->SBZ)	sdi->SDICCON = (0x1<<9)|(0x1<<8)|0x43;	// sht_resp, wait_resp, start, CMD3	//-- Check end of CMD3	if(!Chk_CMDend(3, 1)) 		goto RECMD3;	sdi->SDICSTA = 0xa00;	// Clear cmd_end(with rsp)	//--Publish RCA	if(isMMC) {		RCA=1;		sdi->SDIPRE=(pclk/MMCCLK)-1;			printf("MMC Frequency is %dMHz\n",(pclk/(sdi->SDIPRE+1))/1000000);	}	else	{		RCA=( sdi->SDIRSP0 & 0xffff0000 )>>16;		//printf("RCA=0x%x\n",RCA);		sdi->SDIPRE=pclk/(SDCLK);	// Salamander pclk=66Mhz, prescaler = 2, SD_CLK = 22Mhz		//sdi->SDIPRE=3;  // test 16Mhz		//printf("SD Frequency is %dMHz\n",(pclk/(sdi->SDIPRE+1))/1000000);	}		//--State(stand-by) check	if( sdi->SDIRSP0 & (0x1e00!=0x600) )  // CURRENT_STATE check		goto RECMD3;	//printf("\nIn stand-by\n");	Card_sel_desel(1);	// Select	if(!isMMC)	{		CardBusWidth=1;		SetBus();	// For SD	}	else	{		CardBusWidth=0;		SetBus();	// For MMC	}	Card_sel_desel(0);	// DeSelect for IDLE	if(!CMD9())		printf("Get CSD fail!!!\n");	Card_sel_desel(1);	// Select	{		/* fill in device description */		mmc_dev.if_type = IF_TYPE_MMC;		mmc_dev.dev = 0;		mmc_dev.lun = 0;		mmc_dev.type = 0;		/* FIXME fill in the correct size (is set to 32MByte) */		mmc_dev.blksz = 512;		//mmc_dev.lba = 0x10000;		mmc_dev.lba = CardSize / 512;		mmc_dev.part_type = PART_TYPE_DOS;		/*		sprintf(mmc_dev.vendor,"Man %02x%02x%02x Snr %02x%02x%02x",				cid->id[0], cid->id[1], cid->id[2],				cid->sn[0], cid->sn[1], cid->sn[2]);		sprintf(mmc_dev.product,"%s",cid->name);		sprintf(mmc_dev.revision,"%x %x",cid->hwrev, cid->fwrev);		*/		sprintf(mmc_dev.vendor,"Man aESOP1 Snr 123456");		sprintf(mmc_dev.product,"%s","SDxxxMB");		sprintf(mmc_dev.revision,"%x %x",0x123,0x456);		mmc_dev.removable = 0;		mmc_dev.block_read = mmc_bread;		fat_register_device(&mmc_dev,1); /* partitions start counting with 1 */	}	mmc_init_once = 1;	return 1;}unsigned int *Rx_buffer1;	//128[word]*16[blk]=8192[byte]void SD_Read(unsigned char * pucdata, unsigned long ulLBA, unsigned long ulSectors){	S3C2410_SDI * const sdi = S3C2410_GetBase_SDI();	int status, state, rd_cnt, total_word;	//unsigned int *Rx_buffer1;	//128[word]*16[blk]=8192[byte]//	unsigned int *Rx_buffer1;	//128[word]*16[blk]=8192[byte]	Rx_buffer1 = (unsigned int *)(pucdata);//	printf("Rx_buffer1 = 0x%x\n",Rx_buffer1);	rd_cnt=0;	sdi->SDIFSTA = sdi->SDIFSTA|(1<<16);	// FIFO reset	sdi->SDIDCON=(2<<22)|(1<<19)|(1<<17)|(CardBusWidth<<16)|(1<<14)|(2<<12)|(ulSectors<<0);	//Salamander	//Word Rx, Rx after cmd, blk, 4bit bus, Rx start, blk num, data start, data transmit mode	sdi->SDICARG=ulLBA*512;	// CMD17/18(addr)RERDCMD:	//printf("RERCMD!!\n");	if(ulSectors<2)	// SINGLE_READ	{		sdi->SDICCON=(0x1<<9)|(0x1<<8)|0x51;    // sht_resp, wait_resp, dat, start, CMD17		if(!Chk_CMDend(17, 1))	//-- Check end of CMD17			goto RERDCMD;	}	else	// MULTI_READ	{		sdi->SDICCON=(0x1<<9)|(0x1<<8)|0x52;    // sht_resp, wait_resp, dat, start, CMD18		if(!Chk_CMDend(18, 1))	//-- Check end of CMD18 			goto RERDCMD;	}	state = sdi->SDICSTA;	sdi->SDICSTA = state;	// Clear cmd_end(with rsp)	    	//printf("\n Read CMD end\n");	total_word = 128*ulSectors; 	while(rd_cnt < total_word)	// 512*block bytes	{		state = sdi->SDIDSTA;		if((state&0x20)==0x20) // Check timeout 		{			sdi->SDIDSTA=(0x1<<0x5);  // Clear timeout flag			printf("\n[Time Out !!!] %d, state=%x  status=%x\n",rd_cnt,state,sdi->SDIFSTA);			while(1);			break;		}		status = sdi->SDIFSTA;		if( (status&0x1000) == 0x1000 )	// Is Rx data?		{			*Rx_buffer1++=sdi->SDIDAT;			//printf("%08x ",Rx_buffer1[rd_cnt]);			rd_cnt++;			//if(rd_cnt%8==0) printf("\n");					}	}	//printf("\n After Read loop %d\n",rd_cnt);			//-- Check end of DATA	//printf("\n[Start Chk_DATend !!!]\n");	if(!Chk_DATend()) 		printf("dat error\n");	//printf("\n[End Chk_DATend !!!]\n");		sdi->SDIDCON = sdi->SDIDCON & ~(7<<12);	// Clear Data Transfer mode => no operation, Cleata Data Transfer start	sdi->SDIFSTA = sdi->SDIFSTA & 0x200;	// Clear Rx FIFO Last data Ready,	sdi->SDIDSTA = 0x10;			// Clear data Tx/Rx end detect	if(ulSectors>1)	{RERCMD12:		//--Stop cmd(CMD12)		sdi->SDICARG=0x0;	    		//CMD12(stuff bit)		sdi->SDICCON=(0x1<<9)|(0x1<<8)|0x4c;	//sht_resp, wait_resp, start, CMD12		//-- Check end of CMD12		if(!Chk_CMDend(12, 1)) 			goto RERCMD12;		sdi->SDICSTA=0xa00;			// Clear cmd_end(with rsp)	}}void SD_Write(unsigned char * pucdata, unsigned long ulLBA, unsigned long ulSectors){	S3C2410_SDI * const sdi = S3C2410_GetBase_SDI();	int status,wt_cnt;	unsigned int *Tx_buffer1;	//128[word]*16[blk]=8192[byte]	Tx_buffer1 = (unsigned int *)(pucdata);	wt_cnt=0;	sdi->SDIFSTA = sdi->SDIFSTA|(1<<16);		sdi->SDIDCON = (2<<22)|(1<<20)|(1<<17)|(CardBusWidth<<16)|(1<<14)|(3<<12)|(ulSectors<<0);			//Word Tx, Tx after rsp, blk, 4bit bus, Tx start, blk num	sdi->SDICARG = ulLBA*512;	    // CMD24/25(addr)REWTCMD:	if(ulSectors<2)	// SINGLE_WRITE	{		sdi->SDICCON=(0x1<<9)|(0x1<<8)|0x58;	//sht_resp, wait_resp, dat, start, CMD24		if(!Chk_CMDend(24, 1))	//-- Check end of CMD24			goto REWTCMD;	}	else	// MULTI_WRITE	{		sdi->SDICCON = (0x1<<9)|(0x1<<8)|0x59;	//sht_resp, wait_resp, dat, start, CMD25		if(!Chk_CMDend(25, 1))	//-- Check end of CMD25			goto REWTCMD;	}	sdi->SDICSTA = 0xa00;	// Clear cmd_end(with rsp)	while(wt_cnt<128*ulSectors)	{		status = sdi->SDIFSTA;		if((status&0x2000)==0x2000)		{			sdi->SDIDAT = *Tx_buffer1++;							wt_cnt++;//				printf("Block No.=%d, wt_cnt=%d\n",block,wt_cnt);		}	}	//-- Check end of DATA	if(!Chk_DATend()) 		printf("dat error\n");	sdi->SDIDCON = sdi->SDIDCON & ~(7<<12);		//Clear Data Transfer mode => no operation, Cleata Data Transfer start	sdi->SDIDSTA = 0x10;	// Clear data Tx/Rx end	if(ulSectors>1)	{		//--Stop cmd(CMD12)REWCMD12:		sdi->SDIDCON = (1<<18)|(1<<17)|(0<<16)|(1<<14)|(1<<12)|(ulLBA<<0); 			sdi->SDICARG = 0x0;	    		  //CMD12(stuff bit)		sdi->SDICCON = (0x1<<9)|(0x1<<8)|0x4c;    //sht_resp, wait_resp, start, CMD12		//-- Check end of CMD12		if(!Chk_CMDend(12, 1)) 			goto REWCMD12;		sdi->SDICSTA = 0xa00;	// Clear cmd_end(with rsp)		//-- Check end of DATA(with busy state)		if(!Chk_BUSYend()) 			printf("Write error!\n");		sdi->SDIDSTA = 0x08;	//! Should be cleared by writing '1'.	}}#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -