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

📄 mci_device.c

📁 (1)基于部分u-boot代码自己调试的vxworks BSP (2)实现了nand/nor flash的tffs文件系统 (3)实现了对spi dataflash的访问 (4)实现了对启动参数
💻 C
📖 第 1 页 / 共 2 页
字号:
/*----------------------------------------------------------------------------*         ATMEL Microcontroller Software Support  -  ROUSSET  -*----------------------------------------------------------------------------* The software is delivered "AS IS" without warranty or condition of any* kind, either express, implied or statutory. This includes without* limitation any warranty or condition with respect to merchantability or* fitness for any particular purpose, or against the infringements of* intellectual property rights of others.*----------------------------------------------------------------------------* File Name           : mci_device.c* Object              : TEST DataFlash Functions* Creation            : FB   26/11/2002**----------------------------------------------------------------------------*/#include "AT91C_MCI_Device.h"/*----------------------------------------------------------------------------* \fn    AT91F_MCI_SendCommand* \brief Generic function to send a command to the MMC or SDCard*----------------------------------------------------------------------------*/AT91S_MCIDeviceStatus AT91F_MCI_SendCommand (	AT91PS_MciDevice pMCI_Device,	unsigned int Cmd,	unsigned int Arg){	unsigned int	error,status;	/*unsigned int	tick=0;*/    /* Send the command*/    AT91C_BASE_MCI->MCI_ARGR = Arg;    AT91C_BASE_MCI->MCI_CMDR = Cmd;	/* wait for CMDRDY Status flag to read the response*/	do	{		status = AT91C_BASE_MCI->MCI_SR;		/*tick++;*/	}	while( !(status & AT91C_MCI_CMDRDY) );/*&& (tick<100) );*/    /* Test error  ==> if crc error and response R3 ==> don't check error*/    error = (AT91C_BASE_MCI->MCI_SR) & AT91C_MCI_SR_ERROR;	if(error != 0 )	{		/* if the command is SEND_OP_COND the CRC error flag is always present (cf : R3 response)*/		if ( (Cmd != AT91C_SDCARD_APP_OP_COND_CMD) && (Cmd != AT91C_MMC_SEND_OP_COND_CMD) )			return ((AT91C_BASE_MCI->MCI_SR) & AT91C_MCI_SR_ERROR);		else		{			if (error != AT91C_MCI_RCRCE)				return ((AT91C_BASE_MCI->MCI_SR) & AT91C_MCI_SR_ERROR);		}	}    return AT91C_CMD_SEND_OK;}/*----------------------------------------------------------------------------* \fn    AT91F_MCI_SDCard_SendAppCommand* \brief Specific function to send a specific command to the SDCard*----------------------------------------------------------------------------*/AT91S_MCIDeviceStatus AT91F_MCI_SDCard_SendAppCommand (	AT91PS_MciDevice pMCI_Device,	unsigned int Cmd_App,	unsigned int Arg	){	unsigned int status;	/*unsigned int	tick=0;*/	/* Send the CMD55 for application specific command*/    AT91C_BASE_MCI->MCI_ARGR = (pMCI_Device->pMCI_DeviceFeatures->Relative_Card_Address << 16 );    AT91C_BASE_MCI->MCI_CMDR = AT91C_APP_CMD;	/* wait for CMDRDY Status flag to read the response*/	do	{		status = AT91C_BASE_MCI->MCI_SR;		/*tick++;*/	}	while( !(status & AT91C_MCI_CMDRDY) );/*&& (tick<100) );	*/    /* if an error occurs*/    if (((AT91C_BASE_MCI->MCI_SR) & AT91C_MCI_SR_ERROR) != 0 )		return ((AT91C_BASE_MCI->MCI_SR) & AT91C_MCI_SR_ERROR);    /* check if it is a specific command and then send the command*/	if ( (Cmd_App && AT91C_SDCARD_APP_ALL_CMD) == 0)		return AT91C_CMD_SEND_ERROR;   return( AT91F_MCI_SendCommand(pMCI_Device,Cmd_App,Arg) );}/**----------------------------------------------------------------------------*//** \fn    AT91F_MCI_GetStatus*//** \brief Addressed card sends its status register*//**----------------------------------------------------------------------------*/AT91S_MCIDeviceStatus AT91F_MCI_GetStatus(AT91PS_MciDevice pMCI_Device,unsigned int relative_card_address){	if (AT91F_MCI_SendCommand(pMCI_Device,								AT91C_SEND_STATUS_CMD,								relative_card_address <<16) == AT91C_CMD_SEND_OK)    	return (AT91C_BASE_MCI->MCI_RSPR[0]);    return AT91C_CMD_SEND_ERROR;}/**----------------------------------------------------------------------------*//** \fn    AT91F_MCI_Device_Handler*//** \brief MCI C interrupt handler*//**----------------------------------------------------------------------------*/void AT91F_MCI_Device_Handler(	AT91PS_MciDevice pMCI_Device,	unsigned int status){	/* If End of Tx Buffer Empty interrupt occurred*/	if ( status & AT91C_MCI_TXBUFE )    {		AT91C_BASE_MCI->MCI_IDR = AT91C_MCI_TXBUFE; 		AT91C_BASE_PDC_MCI->PDC_PTCR = AT91C_PDC_TXTDIS;        			pMCI_Device->pMCI_DeviceDesc->state = AT91C_MCI_IDLE;	}	/* End of if AT91C_MCI_TXBUFF		*/	    /* If End of Rx Buffer Full interrupt occurred*/    if ( status & AT91C_MCI_RXBUFF )    {               	AT91C_BASE_MCI->MCI_IDR = AT91C_MCI_RXBUFF; 		AT91C_BASE_PDC_MCI->PDC_PTCR = AT91C_PDC_RXTDIS;			pMCI_Device->pMCI_DeviceDesc->state = AT91C_MCI_IDLE;	}	/* End of if AT91C_MCI_RXBUFF*/}/**----------------------------------------------------------------------------*//** \fn    AT91F_MCI_ReadBlock*//** \brief Read an ENTIRE block or PARTIAL block*//**----------------------------------------------------------------------------*/AT91S_MCIDeviceStatus AT91F_MCI_ReadBlock(	AT91PS_MciDevice pMCI_Device,	int src,	unsigned int *dataBuffer,	int sizeToRead ){    /********************************/    if(pMCI_Device->pMCI_DeviceDesc->state != AT91C_MCI_IDLE)    	return AT91C_READ_ERROR;        if( (AT91F_MCI_GetStatus(pMCI_Device,pMCI_Device->pMCI_DeviceFeatures->Relative_Card_Address) & AT91C_SR_READY_FOR_DATA) != AT91C_SR_READY_FOR_DATA)    	return AT91C_READ_ERROR;    	    if ( (src + sizeToRead) > pMCI_Device->pMCI_DeviceFeatures->Memory_Capacity )		return AT91C_READ_ERROR;    /* If source does not fit a begin of a block*/	if ( (src % pMCI_Device->pMCI_DeviceFeatures->Max_Read_DataBlock_Length) != 0 )		return AT91C_READ_ERROR;        /* Test if the MMC supports Partial Read Block*/     /* ALWAYS SUPPORTED IN SD Memory Card*/     if( (sizeToRead < pMCI_Device->pMCI_DeviceFeatures->Max_Read_DataBlock_Length)     	&& (pMCI_Device->pMCI_DeviceFeatures->Read_Partial == 0x00) )   		return AT91C_READ_ERROR;   		    if( sizeToRead > pMCI_Device->pMCI_DeviceFeatures->Max_Read_DataBlock_Length)   		return AT91C_READ_ERROR;    /********************************/          /* Init Mode Register*/	AT91C_BASE_MCI->MCI_MR |= ((pMCI_Device->pMCI_DeviceFeatures->Max_Read_DataBlock_Length << 16) | AT91C_MCI_PDCMODE);	     if (sizeToRead %4)		sizeToRead = (sizeToRead /4)+1;	else		sizeToRead = sizeToRead/4;	AT91C_BASE_PDC_MCI->PDC_PTCR = (AT91C_PDC_TXTDIS | AT91C_PDC_RXTDIS);    AT91C_BASE_PDC_MCI->PDC_RPR  = (unsigned int)dataBuffer;    AT91C_BASE_PDC_MCI->PDC_RCR  = sizeToRead;	/* Send the Read single block command*/    if ( AT91F_MCI_SendCommand(pMCI_Device, AT91C_READ_SINGLE_BLOCK_CMD, src) != AT91C_CMD_SEND_OK )    	return AT91C_READ_ERROR;	pMCI_Device->pMCI_DeviceDesc->state = AT91C_MCI_RX_SINGLE_BLOCK;	/* Enable AT91C_MCI_RXBUFF Interrupt*/    AT91C_BASE_MCI->MCI_IER = AT91C_MCI_RXBUFF;	/* (PDC) Receiver Transfer Enable*/	AT91C_BASE_PDC_MCI->PDC_PTCR = AT91C_PDC_RXTEN;		return AT91C_READ_OK;}/**----------------------------------------------------------------------------*//** \fn    AT91F_MCI_WriteBlock*//** \brief  Write an ENTIRE block but not always PARTIAL block !!!*//**----------------------------------------------------------------------------*/AT91S_MCIDeviceStatus AT91F_MCI_WriteBlock(	AT91PS_MciDevice pMCI_Device,	int dest,	unsigned int *dataBuffer,	int sizeToWrite ){    /********************************/	if( pMCI_Device->pMCI_DeviceDesc->state != AT91C_MCI_IDLE)    	return AT91C_WRITE_ERROR;        if( (AT91F_MCI_GetStatus(pMCI_Device,pMCI_Device->pMCI_DeviceFeatures->Relative_Card_Address) & AT91C_SR_READY_FOR_DATA) != AT91C_SR_READY_FOR_DATA)    	return AT91C_WRITE_ERROR;    	    if ( (dest + sizeToWrite) > pMCI_Device->pMCI_DeviceFeatures->Memory_Capacity )		return AT91C_WRITE_ERROR;    /* If source does not fit a begin of a block*/	if ( (dest % pMCI_Device->pMCI_DeviceFeatures->Max_Read_DataBlock_Length) != 0 )		return AT91C_WRITE_ERROR;       /* Test if the MMC supports Partial Write Block */    if( (sizeToWrite < pMCI_Device->pMCI_DeviceFeatures->Max_Write_DataBlock_Length)     	&& (pMCI_Device->pMCI_DeviceFeatures->Write_Partial == 0x00) )   		return AT91C_WRITE_ERROR;   		   	if( sizeToWrite > pMCI_Device->pMCI_DeviceFeatures->Max_Write_DataBlock_Length )   		return AT91C_WRITE_ERROR;      /* Init Mode Register*/	AT91C_BASE_MCI->MCI_MR |= ((pMCI_Device->pMCI_DeviceFeatures->Max_Write_DataBlock_Length << 16) | AT91C_MCI_PDCMODE);		if (sizeToWrite %4)		sizeToWrite = (sizeToWrite /4)+1;	else		sizeToWrite = sizeToWrite/4;	/* Init PDC for write sequence*/    AT91C_BASE_PDC_MCI->PDC_PTCR = (AT91C_PDC_TXTDIS | AT91C_PDC_RXTDIS);    AT91C_BASE_PDC_MCI->PDC_TPR = (unsigned int) dataBuffer;    AT91C_BASE_PDC_MCI->PDC_TCR = sizeToWrite;	/* Send the write single block command*/    if ( AT91F_MCI_SendCommand(pMCI_Device, AT91C_WRITE_BLOCK_CMD, dest) != AT91C_CMD_SEND_OK)    	return AT91C_WRITE_ERROR;	pMCI_Device->pMCI_DeviceDesc->state = AT91C_MCI_TX_SINGLE_BLOCK;	/* Enable AT91C_MCI_TXBUFE Interrupt*/    AT91C_BASE_MCI->MCI_IER = AT91C_MCI_TXBUFE;    	/* Enables TX for PDC transfert requests*/    AT91C_BASE_PDC_MCI->PDC_PTCR = AT91C_PDC_TXTEN;  	return AT91C_WRITE_OK;}/**------------------------------------------------------------------------------------------------------------*//** \fn    AT91F_MCI_MMC_SelectCard*//** \brief Toggles a card between the Stand_by and Transfer states or between Programming and Disconnect states*//**------------------------------------------------------------------------------------------------------------*/AT91S_MCIDeviceStatus AT91F_MCI_MMC_SelectCard(AT91PS_MciDevice pMCI_Device, unsigned int relative_card_address){    int status;		/** Check if the MMC card chosen is already the selected one*/	status = AT91F_MCI_GetStatus(pMCI_Device,relative_card_address);	if (status < 0)		return AT91C_CARD_SELECTED_ERROR;	if ((status & AT91C_SR_CARD_SELECTED) == AT91C_SR_CARD_SELECTED)		return AT91C_CARD_SELECTED_OK;	/** Search for the MMC Card to be selected, status = the Corresponding Device Number*/	status = 0;	while( (pMCI_Device->pMCI_DeviceFeatures[status].Relative_Card_Address != relative_card_address)		   && (status < AT91C_MAX_MCI_CARDS) )		status++;	if (status > AT91C_MAX_MCI_CARDS)    	return AT91C_CARD_SELECTED_ERROR;    if (AT91F_MCI_SendCommand( pMCI_Device,

⌨️ 快捷键说明

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