We found a bug for read flash value (address 0xA9FC)
Do you have any recommend?
CPU:C5515
Flash : mx25l6406e
Value error : Orginal : 0x6CEB , buffer value :0x55EB
BinFile address: 0xA9FC , flash address : 0x054FE
code:
main()
{
spirom_init();
spi_eeprom_read_n_words(0x80000000 + 0x05300,g_u16_buffer,512);
}
void spirom_init( )
{
Int16 i;
/* Reset Counter value */
SYS_PRCNTR = 0x04;
/* Reset SPI Module */
SYS_PRCNTRLR = 0x00ff;
for(i=0;i<100;i++) {;}
/* Enable SPICLK,RX,TX & CS0 */
//SYS_EXBUSSEL =(0x5<<12); // mode5 , Table 3-6. LCD Controller, SPI, UART, I2S2, I2S3, and GP[31:27, 20:18] Pin Multiplexing
SYS_EXBUSSEL =(0x6<<12); // mode6
//SPI init
SPI_SPICC2 = (0<<15); // Reset SPI
SPI_SPICC1 = 0x0031; // 2MHz input clock
SPI_SPIDC1 = 0x0000;
SPI_SPICR2 &= ~0x30F8; // Enable CS0
SPI_SPICR2 |= 0x0038; // Set word length as 1-byte
SPI_SPICC2 = (1<<15); // Enable SPI
while((SPI_SPISR1 & 0x0001) != 0) {}; // Wait for SPI ready
spirom_status_set( 0xc3 ); // Clear Block Protection
return;
}
Uint16 spi_eeprom_read_n_words(Uint32 address, Uint16 *buffer, Uint16 count)
{
Uint32 byte_address = (address*2) & 0xFFFFFF;
#ifdef DISABLE_TI_PACK
unsigned short ii;
#endif
unsigned short buffer2[24]; /* Buffer for unpacked bytes */
unsigned short commandbuffer[4]; /* Buffer for unpacked command */
unsigned short sixteenbitdevice;
/* Determine if 16- or 24-bit device is being used */
sixteenbitdevice = (address & 0x80000000) ? 0 : 1;
/* Create the command to be sent to the eeprom */
if(sixteenbitdevice){ // 16-bit SPI device
commandbuffer[0] = SPI_EEPROM_READ;
commandbuffer[1] = byte_address >> 8;
commandbuffer[2] = byte_address & 0xFF;
}
else { // 24-bit SPI device
commandbuffer[0] = SPI_EEPROM_READ;
commandbuffer[1] = byte_address >> 16;
commandbuffer[2] = (byte_address >> 8) & 0xFF;
commandbuffer[3] = byte_address & 0xFF;
}
SPI_READ_WRITE_N_BYTES(buffer2, count*2, commandbuffer, (sixteenbitdevice ? 3 : 4), SPI_CMD_READ);
#ifdef DISABLE_TI_PACK
for(ii = 0; ii < count; ii++)
{
buffer[ii] = buffer2[(2*ii)+1];
buffer[ii] |= (buffer2[(2*ii)] << 8);
}
#else
TI_pack(buffer, (unsigned char *)buffer2, count*2);
#endif
return 0;
}
void SPI_READ_WRITE_N_BYTES(unsigned short *buffer, unsigned short count,
unsigned short *cmdbuffer, unsigned short cmdcount, unsigned short readWrite )
{
unsigned short total_size;
unsigned short spi_cmd = 0;
unsigned short status;
int i;
//enable WIRQ//this should put to FLEN field in the command 1 register;
total_size = count + cmdcount;
//enable WIRQ and FIRQ
spi_cmd |= SPI_CMD_WIRQ | SPI_CMD_FIRQ;
//Frame length = total - 1;
spi_cmd |= (total_size - 1);
IOPORT_REG_SPI_CMD1 = spi_cmd;
//preconfig CMD2, 8bit per bytes, CS0
spi_cmd = (SPI_CMD_8BIT_WLEN << SPI_CMD_WLEN_SHIFT) | (SPI_CMD_CS0 << SPI_CMD_CS_SHIFT);
IOPORT_REG_SPI_CMD2 = spi_cmd;
//send out the command first
for (i=0;i<total_size;i++)
{
//send out the command first
if (i <cmdcount)
IOPORT_REG_SPI_DAT2 = (*cmdbuffer++ << 8);
//write data out
if ((readWrite == SPI_CMD_WRITE ) && (i >= cmdcount))
{
IOPORT_REG_SPI_DAT2 = (*buffer++ << 8);
}
//set the LSB to 0 first
IOPORT_REG_SPI_DAT1 = 0;
//send out write or right command
IOPORT_REG_SPI_CMD2 |= readWrite;
//check the status, word complete
do
{
status = IOPORT_REG_SPI_STAT1;
}
while ((status & SPI_STATUS_WC) != SPI_STATUS_WC);
//check the status, bus busy
do
{
status = IOPORT_REG_SPI_STAT1;
}
while ((status & SPI_STATUS_BUSY) == SPI_STATUS_BUSY);
//read data in
if ((readWrite == SPI_CMD_READ) && (i>=cmdcount))
{
*buffer++ = IOPORT_REG_SPI_DAT1 & 0xFF;
IOPORT_REG_SPI_DAT1 = 0;
IOPORT_REG_SPI_DAT2 = 0;
}
}
}
void TI_pack(Uint16 *data, const unsigned char *buffer, unsigned int count)
{
unsigned int i;
for(i=0; i<(count/2); i++)
{
data[i] = 0;
}
for(i=0; i<count; i++)
{
data[i/2] |=
(
/* UInt16s may be directly allocated on all our target processors */
((Uint16) (buffer[i] & 0xFF)) <<
#ifdef LITTLE_ENDIAN
((i%2) * 8)
#else
((1 - (i%2)) * 8)
#endif
);
}
}