#include <dataflash.h>
#define SPI_CLK 5000000
+#define AT91C_TIMEOUT_WRDY 200000
#define AT91C_SPI_PCS0_SERIAL_DATAFLASH 0xE /* Chip Select 0 : NPCS0 %1110 */
#define AT91C_SPI_PCS3_DATAFLASH_CARD 0x7 /* Chip Select 3 : NPCS3 %0111 */
/* Reset the SPI */
AT91C_BASE_SPI->SPI_CR = AT91C_SPI_SWRST;
- /* Configure SPI in Master Mode with No CS selected !!! */
+ /* Configure SPI in Master Mode with No CS selected !!! */
AT91C_BASE_SPI->SPI_MR = AT91C_SPI_MSTR | AT91C_SPI_MODFDIS | AT91C_SPI_PCS;
/* Configure CS0 and CS3 */
/*----------------------------------------------------------------------------*/
unsigned int AT91F_SpiWrite ( AT91PS_DataflashDesc pDesc )
{
- unsigned int timeout;
+ unsigned int timeout;
pDesc->state = BUSY;
- AT91C_BASE_SPI->SPI_PTCR = AT91C_PDC_TXTDIS + AT91C_PDC_RXTDIS;
+ AT91C_BASE_SPI->SPI_PTCR = AT91C_PDC_TXTDIS + AT91C_PDC_RXTDIS;
- /* Initialize the Transmit and Receive Pointer */
- AT91C_BASE_SPI->SPI_RPR = (unsigned int)pDesc->rx_cmd_pt ;
- AT91C_BASE_SPI->SPI_TPR = (unsigned int)pDesc->tx_cmd_pt ;
+ /* Initialize the Transmit and Receive Pointer */
+ AT91C_BASE_SPI->SPI_RPR = (unsigned int)pDesc->rx_cmd_pt ;
+ AT91C_BASE_SPI->SPI_TPR = (unsigned int)pDesc->tx_cmd_pt ;
- /* Intialize the Transmit and Receive Counters */
- AT91C_BASE_SPI->SPI_RCR = pDesc->rx_cmd_size;
- AT91C_BASE_SPI->SPI_TCR = pDesc->tx_cmd_size;
+ /* Intialize the Transmit and Receive Counters */
+ AT91C_BASE_SPI->SPI_RCR = pDesc->rx_cmd_size;
+ AT91C_BASE_SPI->SPI_TCR = pDesc->tx_cmd_size;
if ( pDesc->tx_data_size != 0 ) {
- /* Initialize the Next Transmit and Next Receive Pointer */
- AT91C_BASE_SPI->SPI_RNPR = (unsigned int)pDesc->rx_data_pt ;
+ /* Initialize the Next Transmit and Next Receive Pointer */
+ AT91C_BASE_SPI->SPI_RNPR = (unsigned int)pDesc->rx_data_pt ;
AT91C_BASE_SPI->SPI_TNPR = (unsigned int)pDesc->tx_data_pt ;
/* Intialize the Next Transmit and Next Receive Counters */
AT91C_BASE_SPI->SPI_RNCR = pDesc->rx_data_size ;
- AT91C_BASE_SPI->SPI_TNCR = pDesc->tx_data_size ;
- }
+ AT91C_BASE_SPI->SPI_TNCR = pDesc->tx_data_size ;
+ }
- /* arm simple, non interrupt dependent timer */
+ /* arm simple, non interrupt dependent timer */
reset_timer_masked();
timeout = 0;
AT91C_BASE_SPI->SPI_PTCR = AT91C_PDC_TXTEN + AT91C_PDC_RXTEN;
while(!(AT91C_BASE_SPI->SPI_SR & AT91C_SPI_RXBUFF) && ((timeout = get_timer_masked() ) < CFG_SPI_WRITE_TOUT));
- AT91C_BASE_SPI->SPI_PTCR = AT91C_PDC_TXTDIS + AT91C_PDC_RXTDIS;
- pDesc->state = IDLE;
+ AT91C_BASE_SPI->SPI_PTCR = AT91C_PDC_TXTDIS + AT91C_PDC_RXTDIS;
+ pDesc->state = IDLE;
if (timeout >= CFG_SPI_WRITE_TOUT){
printf("Error Timeout\n\r");
/* fill the command buffer */
pDataFlash->pDataFlashDesc->command[0] = OpCode;
- pDataFlash->pDataFlashDesc->command[1] = (unsigned char)((adr & 0x00FF0000) >> 16);
- pDataFlash->pDataFlashDesc->command[2] = (unsigned char)((adr & 0x0000FF00) >> 8);
- pDataFlash->pDataFlashDesc->command[3] = (unsigned char)(adr & 0x000000FF) ;
- pDataFlash->pDataFlashDesc->command[4] = 0;
+ if (pDataFlash->pDevice->pages_number >= 16384) {
+ pDataFlash->pDataFlashDesc->command[1] = (unsigned char)((adr & 0x0F000000) >> 24);
+ pDataFlash->pDataFlashDesc->command[2] = (unsigned char)((adr & 0x00FF0000) >> 16);
+ pDataFlash->pDataFlashDesc->command[3] = (unsigned char)((adr & 0x0000FF00) >> 8);
+ pDataFlash->pDataFlashDesc->command[4] = (unsigned char)(adr & 0x000000FF);
+ } else {
+ pDataFlash->pDataFlashDesc->command[1] = (unsigned char)((adr & 0x00FF0000) >> 16);
+ pDataFlash->pDataFlashDesc->command[2] = (unsigned char)((adr & 0x0000FF00) >> 8);
+ pDataFlash->pDataFlashDesc->command[3] = (unsigned char)(adr & 0x000000FF) ;
+ pDataFlash->pDataFlashDesc->command[4] = 0;
+ }
pDataFlash->pDataFlashDesc->command[5] = 0;
pDataFlash->pDataFlashDesc->command[6] = 0;
pDataFlash->pDataFlashDesc->command[7] = 0;
pDesc->command[1] = 0;
pDesc->DataFlash_state = GET_STATUS;
- pDesc->tx_data_size = 0 ; /* Transmit the command and receive response */
- pDesc->tx_cmd_pt = pDesc->command ;
- pDesc->rx_cmd_pt = pDesc->command ;
- pDesc->rx_cmd_size = 2 ;
- pDesc->tx_cmd_size = 2 ;
- status = AT91F_SpiWrite (pDesc);
+ pDesc->tx_data_size = 0 ; /* Transmit the command and receive response */
+ pDesc->tx_cmd_pt = pDesc->command ;
+ pDesc->rx_cmd_pt = pDesc->command ;
+ pDesc->rx_cmd_size = 2 ;
+ pDesc->tx_cmd_size = 2 ;
+ status = AT91F_SpiWrite (pDesc);
pDesc->DataFlash_state = *( (unsigned char *) (pDesc->rx_cmd_pt) +1);
do {
AT91F_DataFlashGetStatus(pDataFlashDesc);
timeout--;
- }
- while( ((pDataFlashDesc->DataFlash_state & 0x80) != 0x80) && (timeout > 0) );
+ } while( ((pDataFlashDesc->DataFlash_state & 0x80) != 0x80) && (timeout > 0) );
if((pDataFlashDesc->DataFlash_state & 0x80) != 0x80)
return DATAFLASH_ERROR;
}
-
/*------------------------------------------------------------------------------*/
/* Function Name : AT91F_DataFlashContinuousRead */
/* Object : Continuous stream Read */
/* Return value : State of the dataflash */
/*------------------------------------------------------------------------------*/
AT91S_DataFlashStatus AT91F_DataFlashContinuousRead (
- AT91PS_DataFlash pDataFlash,
+ AT91PS_DataFlash pDataFlash,
int src,
unsigned char *dataBuffer,
int sizeToRead )
{
+ AT91S_DataFlashStatus status;
/* Test the size to read in the device */
if ( (src + sizeToRead) > (pDataFlash->pDevice->pages_size * (pDataFlash->pDevice->pages_number)))
return DATAFLASH_MEMORY_OVERFLOW;
pDataFlash->pDataFlashDesc->tx_data_pt = dataBuffer;
pDataFlash->pDataFlashDesc->tx_data_size = sizeToRead;
+ status = AT91F_DataFlashSendCommand (pDataFlash, DB_CONTINUOUS_ARRAY_READ, 8, src);
/* Send the command to the dataflash */
- return(AT91F_DataFlashSendCommand (pDataFlash, DB_CONTINUOUS_ARRAY_READ, 8, src));
+ return(status);
}
-
/*------------------------------------------------------------------------------*/
/* Function Name : AT91F_DataFlashPagePgmBuf */
/* Object : Main memory page program through buffer 1 or buffer 2 */
unsigned int dest,
unsigned int SizeToWrite)
{
+ int cmdsize;
pDataFlash->pDataFlashDesc->tx_data_pt = src ;
pDataFlash->pDataFlashDesc->tx_data_size = SizeToWrite ;
pDataFlash->pDataFlashDesc->rx_data_pt = src;
pDataFlash->pDataFlashDesc->rx_data_size = SizeToWrite;
+ cmdsize = 4;
/* Send the command to the dataflash */
- return(AT91F_DataFlashSendCommand (pDataFlash, DB_PAGE_PGM_BUF1, 4, dest));
+ if (pDataFlash->pDevice->pages_number >= 16384)
+ cmdsize = 5;
+ return(AT91F_DataFlashSendCommand (pDataFlash, DB_PAGE_PGM_BUF1, cmdsize, dest));
}
unsigned char BufferCommand,
unsigned int page)
{
+ int cmdsize;
/* Test if the buffer command is legal */
if ((BufferCommand != DB_PAGE_2_BUF1_TRF) && (BufferCommand != DB_PAGE_2_BUF2_TRF))
return DATAFLASH_BAD_COMMAND;
/* no data to transmit or receive */
- pDataFlash->pDataFlashDesc->tx_data_size = 0;
-
- return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, 4, page*pDataFlash->pDevice->pages_size));
+ pDataFlash->pDataFlashDesc->tx_data_size = 0;
+ cmdsize = 4;
+ if (pDataFlash->pDevice->pages_number >= 16384)
+ cmdsize = 5;
+ return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, cmdsize, page*pDataFlash->pDevice->pages_size));
}
-
/*----------------------------------------------------------------------------- */
/* Function Name : AT91F_DataFlashWriteBuffer */
/* Object : Write data to the internal sram buffer 1 or 2 */
unsigned int bufferAddress,
int SizeToWrite )
{
+ int cmdsize;
/* Test if the buffer command is legal */
if ((BufferCommand != DB_BUF1_WRITE) && (BufferCommand != DB_BUF2_WRITE))
return DATAFLASH_BAD_COMMAND;
if ( (pDataFlash->pDataFlashDesc->state) != IDLE)
return DATAFLASH_BUSY;
- /* Send first Write Command */
- pDataFlash->pDataFlashDesc->command[0] = BufferCommand;
+ /* Send first Write Command */
+ pDataFlash->pDataFlashDesc->command[0] = BufferCommand;
pDataFlash->pDataFlashDesc->command[1] = 0;
- pDataFlash->pDataFlashDesc->command[2] = (unsigned char)(((unsigned int)(bufferAddress & pDataFlash->pDevice->byte_mask)) >> 8) ;
- pDataFlash->pDataFlashDesc->command[3] = (unsigned char)((unsigned int)bufferAddress & 0x00FF) ;
+ if (pDataFlash->pDevice->pages_number >= 16384) {
+ pDataFlash->pDataFlashDesc->command[2] = 0;
+ pDataFlash->pDataFlashDesc->command[3] = (unsigned char)(((unsigned int)(bufferAddress & pDataFlash->pDevice->byte_mask)) >> 8) ;
+ pDataFlash->pDataFlashDesc->command[4] = (unsigned char)((unsigned int)bufferAddress & 0x00FF) ;
+ cmdsize = 5;
+ } else {
+ pDataFlash->pDataFlashDesc->command[2] = (unsigned char)(((unsigned int)(bufferAddress & pDataFlash->pDevice->byte_mask)) >> 8) ;
+ pDataFlash->pDataFlashDesc->command[3] = (unsigned char)((unsigned int)bufferAddress & 0x00FF) ;
+ pDataFlash->pDataFlashDesc->command[4] = 0;
+ cmdsize = 4;
+ }
+
+ pDataFlash->pDataFlashDesc->tx_cmd_pt = pDataFlash->pDataFlashDesc->command ;
+ pDataFlash->pDataFlashDesc->tx_cmd_size = cmdsize ;
+ pDataFlash->pDataFlashDesc->rx_cmd_pt = pDataFlash->pDataFlashDesc->command ;
+ pDataFlash->pDataFlashDesc->rx_cmd_size = cmdsize ;
+ pDataFlash->pDataFlashDesc->rx_data_pt = dataBuffer ;
+ pDataFlash->pDataFlashDesc->tx_data_pt = dataBuffer ;
+ pDataFlash->pDataFlashDesc->rx_data_size = SizeToWrite ;
+ pDataFlash->pDataFlashDesc->tx_data_size = SizeToWrite ;
- pDataFlash->pDataFlashDesc->tx_cmd_pt = pDataFlash->pDataFlashDesc->command ;
- pDataFlash->pDataFlashDesc->tx_cmd_size = 4 ;
- pDataFlash->pDataFlashDesc->rx_cmd_pt = pDataFlash->pDataFlashDesc->command ;
- pDataFlash->pDataFlashDesc->rx_cmd_size = 4 ;
+ return AT91F_SpiWrite(pDataFlash->pDataFlashDesc);
+}
- pDataFlash->pDataFlashDesc->rx_data_pt = dataBuffer ;
- pDataFlash->pDataFlashDesc->tx_data_pt = dataBuffer ;
- pDataFlash->pDataFlashDesc->rx_data_size = SizeToWrite ;
- pDataFlash->pDataFlashDesc->tx_data_size = SizeToWrite ;
+/*------------------------------------------------------------------------------*/
+/* Function Name : AT91F_PageErase */
+/* Object : Erase a page */
+/* Input Parameters : DataFlash Service */
+/* : Page concerned */
+/* : */
+/* Return value : State of the dataflash */
+/*------------------------------------------------------------------------------*/
+AT91S_DataFlashStatus AT91F_PageErase(
+ AT91PS_DataFlash pDataFlash,
+ unsigned int page)
+{
+ int cmdsize;
+ /* Test if the buffer command is legal */
+ /* no data to transmit or receive */
+ pDataFlash->pDataFlashDesc->tx_data_size = 0;
- return AT91F_SpiWrite(pDataFlash->pDataFlashDesc);
+ cmdsize = 4;
+ if (pDataFlash->pDevice->pages_number >= 16384)
+ cmdsize = 5;
+ return(AT91F_DataFlashSendCommand (pDataFlash, DB_PAGE_ERASE, cmdsize, page*pDataFlash->pDevice->pages_size));
}
+/*------------------------------------------------------------------------------*/
+/* Function Name : AT91F_BlockErase */
+/* Object : Erase a Block */
+/* Input Parameters : DataFlash Service */
+/* : Page concerned */
+/* : */
+/* Return value : State of the dataflash */
+/*------------------------------------------------------------------------------*/
+AT91S_DataFlashStatus AT91F_BlockErase(
+ AT91PS_DataFlash pDataFlash,
+ unsigned int block)
+{
+ int cmdsize;
+ /* Test if the buffer command is legal */
+ /* no data to transmit or receive */
+ pDataFlash->pDataFlashDesc->tx_data_size = 0;
+ cmdsize = 4;
+ if (pDataFlash->pDevice->pages_number >= 16384)
+ cmdsize = 5;
+ return(AT91F_DataFlashSendCommand (pDataFlash, DB_BLOCK_ERASE,cmdsize, block*8*pDataFlash->pDevice->pages_size));
+}
+
/*------------------------------------------------------------------------------*/
/* Function Name : AT91F_WriteBufferToMain */
/* Object : Write buffer to the main memory */
unsigned char BufferCommand,
unsigned int dest )
{
+ int cmdsize;
/* Test if the buffer command is correct */
if ((BufferCommand != DB_BUF1_PAGE_PGM) &&
(BufferCommand != DB_BUF1_PAGE_ERASE_PGM) &&
/* no data to transmit or receive */
pDataFlash->pDataFlashDesc->tx_data_size = 0;
+ cmdsize = 4;
+ if (pDataFlash->pDevice->pages_number >= 16384)
+ cmdsize = 5;
/* Send the command to the dataflash */
- return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, 4, dest));
+ return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, cmdsize, dest));
}
/* Read the contents of the page in the Sram Buffer */
AT91F_MainMemoryToBufferTransfert(pDataFlash, DB_PAGE_2_BUF1_TRF, page);
- AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000);
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
/*Update the SRAM buffer */
AT91F_DataFlashWriteBuffer(pDataFlash, DB_BUF1_WRITE, src, AdrInPage, size);
- AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000);
+
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
+
+ /* Erase page if a 128 Mbits device */
+ if (pDataFlash->pDevice->pages_number >= 16384) {
+ AT91F_PageErase(pDataFlash, page);
+ /* Rewrite the modified Sram Buffer in the main memory */
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
+ }
/* Rewrite the modified Sram Buffer in the main memory */
return(AT91F_WriteBufferToMain(pDataFlash, DB_BUF1_PAGE_ERASE_PGM, (page*pDataFlash->pDevice->pages_size)));
}
-
/*------------------------------------------------------------------------------*/
-/* Function Name : AT91F_DataFlashWrite_Overloaded */
+/* Function Name : AT91F_DataFlashWrite */
/* Object : */
/* Input Parameters : <*src> = Source buffer */
/* : <dest> = dataflash adress */
int size )
{
unsigned int length;
+ unsigned int page;
+ unsigned int status;
AT91F_SpiEnable(pDataFlash->pDevice->cs);
- if ( (dest + size) > (pDataFlash->pDevice->pages_size * (pDataFlash->pDevice->pages_number)))
+ if ( (dest + size) > (pDataFlash->pDevice->pages_size * (pDataFlash->pDevice->pages_number)))
return DATAFLASH_MEMORY_OVERFLOW;
- /* If destination does not fit a page start address */
- if ((dest % ((unsigned int)(pDataFlash->pDevice->pages_size))) != 0 ) {
+ /* If destination does not fit a page start address */
+ if ((dest % ((unsigned int)(pDataFlash->pDevice->pages_size))) != 0 ) {
length = pDataFlash->pDevice->pages_size - (dest % ((unsigned int)(pDataFlash->pDevice->pages_size)));
if (size < length)
if(!AT91F_PartialPageWrite(pDataFlash,src, dest, length))
return DATAFLASH_ERROR;
- AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000);
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
/* Update size, source and destination pointers */
- size -= length;
- dest += length;
- src += length;
- }
+ size -= length;
+ dest += length;
+ src += length;
+ }
- while (( size - pDataFlash->pDevice->pages_size ) >= 0 ) {
+ while (( size - pDataFlash->pDevice->pages_size ) >= 0 ) {
/* program dataflash page */
- if(!AT91F_DataFlashPagePgmBuf(pDataFlash, src, dest, pDataFlash->pDevice->pages_size ))
+ page = (unsigned int)dest / (pDataFlash->pDevice->pages_size);
+
+ status = AT91F_DataFlashWriteBuffer(pDataFlash, DB_BUF1_WRITE, src, 0, pDataFlash->pDevice->pages_size);
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
+
+ status = AT91F_PageErase(pDataFlash, page);
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
+ if (!status)
+ return DATAFLASH_ERROR;
+
+ status = AT91F_WriteBufferToMain (pDataFlash, DB_BUF1_PAGE_PGM, dest);
+ if(!status)
return DATAFLASH_ERROR;
- AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000);
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
/* Update size, source and destination pointers */
- size -= pDataFlash->pDevice->pages_size ;
- dest += pDataFlash->pDevice->pages_size ;
- src += pDataFlash->pDevice->pages_size ;
- }
+ size -= pDataFlash->pDevice->pages_size ;
+ dest += pDataFlash->pDevice->pages_size ;
+ src += pDataFlash->pDevice->pages_size ;
+ }
- /* If still some bytes to read */
- if ( size > 0 ) {
+ /* If still some bytes to read */
+ if ( size > 0 ) {
/* program dataflash page */
if(!AT91F_PartialPageWrite(pDataFlash, src, dest, size) )
return DATAFLASH_ERROR;
- AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000);
+ AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY);
}
- return DATAFLASH_OK;
+ return DATAFLASH_OK;
}
AT91F_SpiEnable(pDataFlash->pDevice->cs);
- if(AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000) != DATAFLASH_OK)
+ if(AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY) != DATAFLASH_OK)
return -1;
while (size) {
SizeToRead = (size < 0x8000)? size:0x8000;
- if (AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000) != DATAFLASH_OK)
+ if (AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY) != DATAFLASH_OK)
return -1;
if (AT91F_DataFlashContinuousRead (pDataFlash, addr, buffer, SizeToRead) != DATAFLASH_OK)
buffer += SizeToRead;
}
- return DATAFLASH_OK;
+ return DATAFLASH_OK;
}
int AT91F_DataflashProbe(int cs, AT91PS_DataflashDesc pDesc)
{
AT91F_SpiEnable(cs);
- AT91F_DataFlashGetStatus(pDesc);
- return((pDesc->command[1] == 0xFF)? 0: pDesc->command[1] & 0x3C);
+ AT91F_DataFlashGetStatus(pDesc);
+ return((pDesc->command[1] == 0xFF)? 0: pDesc->command[1] & 0x3C);
}
#endif