LPC54608 SST25VF016B SPI Flash Issue

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

LPC54608 SST25VF016B SPI Flash Issue

Jump to solution
3,213 Views
fatihozen
Contributor IV

Hello,

I have my own custom board and want to use sst25vf016b flash for bootloader. I have some problem about reading and writing. Actually reading.  I checked polarity and phase. In SPI_MasterGetDefaultConfig() function they arranged as spi mode 0 . sst25vf016b supports mode 0 and 3, so I didn't change it.

void vInitializeSpiFlash(void){

uint32_t srcFreq = 0;
spi_master_config_t MasterConfig = {0};

CLOCK_AttachClk(kFRO12M_to_FLEXCOMM2);
RESET_PeripheralReset(kFC2_RST_SHIFT_RSTn);

IOCON->PIO[4][19] = 0x0303;
IOCON->PIO[4][20] = 0x0303;
IOCON->PIO[4][21] = 0x0303;
IOCON->PIO[3][23] = 0x0B01;

IOCON->PIO[3][24] = 0x0300;
SPI_MasterGetDefaultConfig(&MasterConfig);
MasterConfig.sselNum = kSPI_Ssel0;
MasterConfig.sselPol = (spi_spol_t)kSPI_SpolActiveAllLow;
srcFreq = CLOCK_GetFreq(kCLOCK_Flexcomm2);
SPI_MasterInit(SPI2, &MasterConfig, srcFreq);
}

Reading jedec id issue:

///////////////////////////////

uint32_t E_Flash_Read_JedecID(){
volatile uint8_t a,b,c;
volatile uint32_t d;

SPI_WriteData(SPI2, 0x9F, 0);
a = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, 0);
a = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, 0);
b = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);
c = SPI_ReadData(SPI2);
d = (a<<16) | (b<<8) | (c) ;
return(d);
}

When I use this function to read jedec id I see 41ffbf.

///////////////////

uint32_t E_Flash_Read_JedecID(){
volatile uint8_t a,b,c;
volatile uint32_t d;

SPI_WriteData(SPI2, 0x9F, 0);

SPI_WriteData(SPI2, DUMMY_BYTE, 0);
a = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, 0);
a = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, 0);
b = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);
c = SPI_ReadData(SPI2);
d = (a<<16) | (b<<8) | (c) ;
return(d);
}

If I use this I see an expected data : bf2541. I just sent dummy data to flash after sending command data.
Anyway, When I want to read status register of flash I use this function. And I see "1c" as expected.

///////////////////////
int16_t E_Flash_Read_Status_Register(){
volatile int16_t pui32Data, dummy;
SPI_WriteData(SPI2, RDSR, 0);
dummy = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE,kSPI_FrameAssert);
pui32Data = SPI_ReadData(SPI2);
return(pui32Data);
dummy = dummy;
}

 ///////////
When it comes to read both or calling two or more functions, I see meanless datas.

E_Flash_Read_JedecID();
n = E_Flash_Read_Status_Register();

Eg: When I call these 2 functions I expect to see status register "1c". But I see "41". The last data of jedec id.
Why  that happens ?

Labels (1)
Tags (2)
1 Solution
2,427 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi Fatih ozen,

   After I modify your API, now it can get the correct data, please check my attached result:

int32_t E_Flash_Read_Byte_kerry(uint32_t ui32Address){
     int16_t dummy,dummy20, Testbuff[8];
     uint8_t i=0;
     uint32_t dummyTest=0;
     for(i=0;i<8;i++)
     {
          Testbuff[i]=0;
     }

     //CE_Clear();
     i=0;
     SPI9->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;

     while(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK)
     {
          dummyTest = SPI_ReadData(SPI9);//Put breakpoint here, if it really won't enter, this while code can be delete.
     }
     SPI9->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;


     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     { SPI_WriteData(SPI9, 0x0B, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x91, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, kSPI_FrameAssert);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     while (!(SPI9->FIFOSTAT & SPI_FIFOSTAT_TXEMPTY_MASK)){};




}‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

pastedImage_1.png

Just use while to wait the received status finished.

Your problem is caused by the received data is not received with if, but use while to wait, it will be enough time to get the received data.

Please try my new function again with your external flash


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

View solution in original post

0 Kudos
26 Replies
2,428 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi Fatih ozen,

   After I modify your API, now it can get the correct data, please check my attached result:

int32_t E_Flash_Read_Byte_kerry(uint32_t ui32Address){
     int16_t dummy,dummy20, Testbuff[8];
     uint8_t i=0;
     uint32_t dummyTest=0;
     for(i=0;i<8;i++)
     {
          Testbuff[i]=0;
     }

     //CE_Clear();
     i=0;
     SPI9->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;

     while(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK)
     {
          dummyTest = SPI_ReadData(SPI9);//Put breakpoint here, if it really won't enter, this while code can be delete.
     }
     SPI9->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;


     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     { SPI_WriteData(SPI9, 0x0B, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x91, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, 0);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     if (SPI_GetStatusFlags(SPI9) & kSPI_TxNotFullFlag)
     {SPI_WriteData(SPI9, 0x00, kSPI_FrameAssert);}
     while(!(SPI_GetStatusFlags(SPI9) & SPI_FIFOSTAT_RXNOTEMPTY_MASK));
     Testbuff[i++] = (SPI9->FIFORD);

     while (!(SPI9->FIFOSTAT & SPI_FIFOSTAT_TXEMPTY_MASK)){};




}‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

pastedImage_1.png

Just use while to wait the received status finished.

Your problem is caused by the received data is not received with if, but use while to wait, it will be enough time to get the received data.

Please try my new function again with your external flash


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,039 Views
fatihozen
Contributor IV

It is working now, thank you so much !

0 Kudos
2,039 Views
kerryzhou
NXP TechSupport
NXP TechSupport

The detail problem really in the E_Flash_Read_Byte function, I already check this function, it can reproduce the problem.

If you have time, you can use our SDK polling function, in the meanwhile, I will test your function to find the problem.


Have a great day,
TIC

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,048 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi Fatih ozen,

   I highly suggest you to use the logic analyzer tool to check the SPI bus wave.

   Then compare the SPI bus wave with your external SPI flash datasheet waveform and requirement, whether it meet the slave's demand?

   Another point you need to note, normally, use the MCU to control the external flash SPI interface, the SPI_SSEL we use the GPIO to control it, instead of the hardware SPI SSEL pin function.

   You can check the SPI bus wave, whether the SPI SSEL pin wave also correct with your code.

  Check the BUS wave will help you to locate the root problem.

Wish it helps you!

If you still have question about it, please kindly let me know.

  


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

2,048 Views
fatihozen
Contributor IV

Hello Kerry Zhou,

I did as you said now I can read write status register correctly and the successful about reading jedec ID. Problem is still about reading a byte. I am erasing all datas via Chip Erase Command and then write a byte to an address (0x000065) (Data : 0xAD). and then I try reading this byte from same address via reding command. I see data is on MISO line but I still see 0xff on my screen. Screenshots are below.
pastedImage_5.jpg

pastedImage_6.jpg

I little bit changed the code as you see below. 

///////////////////////////////////////////////////////

#define DUMMY_BYTE 0x00
#define READ 0x03
#define READ_FAST 0x0B
#define ERASE_4KB 0x20
#define ERASE_32KB 0x52
#define ERASE_64KB 0xD8
#define ERASE_CHIP 0x60
#define PROGRAM_BYTE 0x02
#define PROGRAM_AAI 0xAD
#define RDSR 0x05
#define EWRS 0x50
#define WRSR 0x01
#define WREN 0x06
#define WRDIS 0x04
#define RDID 0x90
#define R_JEDEC 0x9F
#define EBSY 0x70
#define DBSY 0x80
#define WRSR_NOT 0x9C
#define ENABLE_PROTECTION 0x1C
#define DISABLE_PROTECTION 0x00

void vInitializeSpiFlash(void){

uint32_t srcFreq = 0;
spi_master_config_t MasterConfig = {0};

CLOCK_AttachClk(kFRO12M_to_FLEXCOMM2);
RESET_PeripheralReset(kFC2_RST_SHIFT_RSTn);

IOCON->PIO[4][19] = 0x0303;
IOCON->PIO[4][20] = 0x0303;
IOCON->PIO[4][21] = 0x0303;
IOCON->PIO[3][23] = 0x0B41;
IOCON->PIO[3][24] = 0x0300;
gpio_pin_config_t pin_config = {kGPIO_DigitalOutput, 0};
GPIO_PortInit(GPIO, 3);
GPIO_PinInit(GPIO, 3, 24, &pin_config);

SPI_MasterGetDefaultConfig(&MasterConfig);
MasterConfig.sselNum = kSPI_Ssel0;
MasterConfig.sselPol = (spi_spol_t)kSPI_SpolActiveAllLow;
srcFreq = CLOCK_GetFreq(kCLOCK_Flexcomm2);
SPI_MasterInit(SPI2, &MasterConfig, srcFreq);
}

void WP_Set(void){GPIO_PinWrite(GPIO, 3, 24, 1);}

void WP_Clear(void){GPIO_PinWrite(GPIO, 3, 24, 0);}

void E_Flash_Protection_Enable(void){E_Flash_Write_Status_Register(WRSR_NOT);}

void E_Flash_Protection_Disable(void){E_Flash_Write_Status_Register(DISABLE_PROTECTION);}

void E_Flash_Write_Enable(void){
volatile uint16_t dummy;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, WREN, kSPI_FrameAssert);}
{dummy = SPI_ReadData(SPI2);}
dummy = dummy;
}

void E_Flash_Write_Disable(void){
volatile uint16_t dummy;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, WRDIS, kSPI_FrameAssert);}
{dummy = SPI_ReadData(SPI2);}
dummy = dummy;
}

void E_Flash_Enable_Write_Status_Register(void){
volatile uint16_t dummy;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, EWRS, kSPI_FrameAssert);}
{dummy = SPI_ReadData(SPI2);}
dummy=dummy;
}

void E_Flash_Write_Status_Register(int16_t value){
E_Flash_Enable_Write_Status_Register();
WP_Set();
volatile uint16_t dummy;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, WRSR, 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, value, kSPI_FrameAssert);}
{dummy = SPI_ReadData(SPI2);}
dummy=dummy;
WP_Clear();
}

int16_t E_Flash_Read_Status_Register(){
volatile int16_t pui32Data;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, RDSR, 0);}
{pui32Data = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE,kSPI_FrameAssert);}
{pui32Data = SPI_ReadData(SPI2);}
return(pui32Data);
}

uint32_t E_Flash_Read_JedecID(){
volatile uint8_t a,b,c;
volatile uint32_t d;
SPI_WriteData(SPI2, 0x9F, 0);
a = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, 0);
a = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, 0);
b = SPI_ReadData(SPI2);
SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);
c = SPI_ReadData(SPI2);
d = (a<<16) | (b<<8) | (c) ;
return(d);
}

void E_Flash_Write_Byte(uint32_t ui32Address, uint8_t data){
E_Flash_Protection_Disable();
E_Flash_Write_Enable();

volatile uint16_t dummy;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, PROGRAM_BYTE, 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, (ui32Address & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, data, kSPI_FrameAssert);}
{dummy = SPI_ReadData(SPI2);}
dummy = dummy;
}

int16_t E_Flash_Read_Byte(uint32_t ui32Address){
int16_t dummy,dummy20;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, READ, 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, (ui32Address & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);}
{dummy20 = SPI_ReadData(SPI2);}

return(dummy20);
}

void E_Flash_Chip_Erase(void){
E_Flash_Protection_Disable();
E_Flash_Write_Enable();

volatile int16_t dummy;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ERASE_CHIP, kSPI_FrameAssert);}
{dummy = SPI_ReadData(SPI2);}
dummy = dummy;

for(int i=0;i<750000;i++){__ASM("NOP");} // 50 ms waiting for erasing all chip according to datasheet.
}

0 Kudos
2,048 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi fatih ozen,

      Thank you for your updated information, it's good!

      Now,  your problem just in the external flash read.

     From the SST25VF016B SPI flash datasheet, we can know the read sequence:

pastedImage_2.png

So, now, from your SPI bus wave, your SPI slave already give feedback as 0XAD in the data field.

You said, in the LPC code, you still get the wrong data, it is 0XFF. So now the problem mainly in the SPI code side.

 I checked your code:

=============================================================
int16_t E_Flash_Read_Byte(uint32_t ui32Address){
int16_t dummy,dummy20;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, READ, 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, (ui32Address & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);}
{dummy20 = SPI_ReadData(SPI2);}

return(dummy20);
}

===================================================================

If you want to to read the data from the slave, just use SPI_ReadData to read is not enough, you need to wait the kSPI_RxNotEmptyFlag, just when the RX buffer have data, then you read it.

I think you can use while to wait it.

eg:

while(!(SPI_GetStatusFlags(SPI2) & kSPI_RxNotEmptyFlag));

dummy20 = SPI_ReadData(SPI2);}

Your problem is caused by the RX is not ready, so it will be 0XFF data.

Please modify the code and test it again.

If you still have problem about it, please kindly let me know.


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,048 Views
fatihozen
Contributor IV

Hi Kerry Zhou,

I have already tried it. I have referenced spi interrupt example and there is code below :

/* read data to avoid rxOverflow */
while (SPI_GetStatusFlags(EXAMPLE_SPI_MASTER) & kSPI_RxNotEmptyFlag)
{
SPI_ReadData(EXAMPLE_SPI_MASTER);
}t

I tried and did not be successfull . That is why I deleted it. Tried again as you said but nothing changed. Other suggestion ?
(No change at bus. Still same, data is there.)

0 Kudos
2,048 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi Fatih Ozen,

   Do you try my code?

   Your code is not correct!

   Let analysis it:

while (SPI_GetStatusFlags(EXAMPLE_SPI_MASTER) & kSPI_RxNotEmptyFlag)
{
SPI_ReadData(EXAMPLE_SPI_MASTER);
}

I have a question for your, if after your master send the clocks, but the MISO data still not into the receive buffer, what the status data of RXNotEmptyFlag?

It will be 0, so your while won't work, your read won't be processed.

You can use my code, when the RXbuff is empty, just wait, until the the buff is not empty, then read the buffer.

Please try it again.

Any updated information, just let me know.


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,048 Views
fatihozen
Contributor IV

I said I tried it too. I just showed a part of what i did before you comment to the topic.

int16_t E_Flash_Read_Byte(uint32_t ui32Address){
int16_t dummy,dummy2;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, READ, 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, (ui32Address & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);}
while(!(SPI_GetStatusFlags(SPI2) & kSPI_RxNotEmptyFlag))
{dummy2 = SPI_ReadData(SPI2);}
return(dummy2);
}

with above code the signals :

pastedImage_1.jpg

pastedImage_2.jpg

0 Kudos
2,047 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi fatih ozen,

   Thank you for your updated information and the effort.

   I find your SPI bus wave have problems:

pastedImage_1.png

You can find the receive byte clock just 7 bits. There should have some errors.

Do you have debugger?

Can you debug the code, check whether there have any errors or not?

Before you do the read operation, I think you also can clear the tx/rx erros and empty FIFOs:

    /* clear tx/rx errors and empty FIFOs */
    base->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;
    base->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;

If you still have problems, i think you also can try to use the SDK code spi_polling_b2b_transfer_master,  function SPI_MasterTransferBlocking.

Please debug your code at first, check the register, and also post the register to me.

If you have time, you also can try the SPI_MasterTransferBlocking, then

    xfer.txData = srcBuff;
    xfer.rxData = destBuff;

txDATA can input the commander and address, desbuff, just give 5 bytes, used to received the received data.

   


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,047 Views
fatihozen
Contributor IV

Hi Kerry Zhou,

When I checked the Fifo Status Register,

 Its value is 0x422. without while(!(SPI_GetStatusFlags(SPI2) & kSPI_RxNotEmptyFlag)).

 Its value is 0x10462 with while(!(SPI_GetStatusFlags(SPI2) & kSPI_RxNotEmptyFlag)).

According to table there is seen RXERR, TXNOTFULL, RXNOTEMPTY with your suggested code.

pastedImage_1.png

When I clear tx/rx errors and empty FIFOs before writing process, nothing changed.

//
SPI2->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;
SPI2->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;

//

pastedImage_2.png

I will try function SPI_MasterTransferBlocking as you suggested.

Thanks for help.

0 Kudos
2,048 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi

Add the ERR clear code before this code:

if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);}
while(!(SPI_GetStatusFlags(SPI2) & kSPI_RxNotEmptyFlag))
{dummy2 = SPI_ReadData(SPI2);}

Then try again.

From your test result, at least my code already find the RXnotEmptyFlag.


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,048 Views
fatihozen
Contributor IV

Hi,

int32_t E_Flash_Read_Byte(uint32_t ui32Address){

SPI2->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;
int32_t dummy,dummy2;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, READ, 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, (ui32Address & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}

SPI2->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);}
while(!(SPI_GetStatusFlags(SPI2) & kSPI_RxNotEmptyFlag))
// {dummy2 = SPI2->FIFORD;}
{dummy2 = SPI2->FIFOSTAT;}
return(dummy2);

}

I did as you said, and the results :

FIFOSTAT shows two different results: 0x420 and 0x10460.

pastedImage_1.png

But if I try to read :
{dummy2 = SPI2->FIFORD;}
// {dummy2 = SPI2->FIFOSTAT;}

Lcd and Flash stuck. No lcd and no spi datas after  "SPI2->FIFORD".

When I read data "SPI2->FIFORDNOPOP" via that way, Lcd doesn't stuck and I see again 0xFF on my side and  correct data(whatever I write) as above. 

0 Kudos
2,048 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi fatih ozen,

    Thank you for your updated information.

     Because I don't have your SPI slave, otherwise I will help you test it directly.

    But don't worry, let's do the deep test now, just follow my way. 

    I modify your E_Flash_Read_Byte function like this, you can try it:

int16_t E_Flash_Read_Byte_kerry(uint32_t ui32Address){
int16_t dummy,dummy20, Testbuff[8];
uint8_t i=0;
uint32_t dummyTest=0;
for(i=0;i<8;i++)
{
     Testbuff[i]=0;
}

SPI2->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;

//Double check it, make sure the buffer is empty, you also can add a break point here, to check the RXNOTEMPTY bit in FIFOSTAT register.

while(SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag) 
{
     dummyTest = SPI_ReadData(SPI2);//Put breakpoint here, if it really won't enter, this while code can be delete.
}
SPI2->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;

//Send Byte1
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, READ, 0);
}
//Send Byte2
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);
}
//Send Byte3
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);
}

//Send Byte4
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, (ui32Address & 0xff), 0);
}

//Send Byte5
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);
}
/* wait if TX FIFO of previous transfer is not empty */
 while (!(base->FIFOSTAT & SPI_FIFOSTAT_TXEMPTY_MASK)){};
 
 //read the bytes together
 
 for(i=0;i<8;i++)
 {
        if((SPI2->FIFOSTAT) & SPI_FIFOSTAT_RXNOTEMPTY_MASK)
        {
             Testbuff[i++] = (SPI2->FIFORD);
        }
 }
 
//then debug the code, stop here, check the TestBuff data, and i data.
//whether i=5, and Send me the TestBuff data. if TestBuff[4]= 0x60 as your SPI wave, then return this data.
return(Testbuff[5]);


/*

if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, READ, 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, (ui32Address & 0xff), 0);}
{dummy = SPI_ReadData(SPI2);}
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);}
{dummy20 = SPI_ReadData(SPI2);}

return(dummy20);
*/
}‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

Please debug it, add breakpoint at :

1. line 21

   Check Register FIFOSTAT, send me the data.

2. line 62

   Check TestBuff data and i data. Send me the data or the debug screen shoot.

   Check Register FIFOSTAT, send me the data.

Don't care about your lcd and flash code at first, after we make the external flash read works, we will modify it to meet your lcd and flash code demand.

Let's keep patience and check it again on your side.

Besides, still check the SPI bus wave , and send me with this function.


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,048 Views
fatihozen
Contributor IV

Well, there is news on my side.
I changed functions as you can see in attachment. There are two meaningless points:
First one is I can't see datas with Read Function but I can see them with Fast Read Function.
Second is I can't read first written data. I mean if I write only one byte I obviously see 0xff because of this problem.

Example:

E_Flash_Write_Byte(0x000091,0xaa);
E_Flash_Write_Byte(0x000092,0xbb);
E_Flash_Write_Byte(0x000093,0xcc);
E_Flash_Write_Byte(0x000094,0xdd);
E_Flash_Write_Byte(0x000095,0xee);
E_Flash_Write_Byte(0x000026,0xb3);
E_Flash_Write_Byte(0x000033,0x3b);

result=E_Flash_Read_Fast_Byte(0x000091);
result1=E_Flash_Read_Fast_Byte(0x000092);
result2=E_Flash_Read_Fast_Byte(0x000093);
result3=E_Flash_Read_Fast_Byte(0x000094);
result4=E_Flash_Read_Fast_Byte(0x000095);
result5=E_Flash_Read_Byte(0x000026);
result6=E_Flash_Read_Byte(0x000033);

After these, I see  : ff aa bb cc dd ff ff.
First written data can't be read and read byte function doesn't work here.

Any idea to solve this ?


(Everything looks good as before on scope side.Datas are seen at MISO line.)

0 Kudos
2,048 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi fatih ozen,

  Please also share me your example SPI bus wave to analysis.

  Just this one:

Example:

 

E_Flash_Write_Byte(0x000091,0xaa);
E_Flash_Write_Byte(0x000092,0xbb);
E_Flash_Write_Byte(0x000093,0xcc);
E_Flash_Write_Byte(0x000094,0xdd);
E_Flash_Write_Byte(0x000095,0xee);
E_Flash_Write_Byte(0x000026,0xb3);
E_Flash_Write_Byte(0x000033,0x3b);

 

result=E_Flash_Read_Fast_Byte(0x000091);
result1=E_Flash_Read_Fast_Byte(0x000092);
result2=E_Flash_Read_Fast_Byte(0x000093);
result3=E_Flash_Read_Fast_Byte(0x000094);
result4=E_Flash_Read_Fast_Byte(0x000095);
result5=E_Flash_Read_Byte(0x000026);
result6=E_Flash_Read_Byte(0x000033);


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,047 Views
fatihozen
Contributor IV

Hi,

You can find images and output files of recording at the attachment

0 Kudos
2,047 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi fatih ozen,

   Thank you for your image, your image help me to recall your question, it is really a long time, I nearly a little forget the detail.

   At first, sorry for my last function code, there has a mistake, which you have remove the line 14-17.

  I copy the wrong flag, please use this code and test it again:

int16_t E_Flash_Read_Byte_kerry(uint32_t ui32Address){
int16_t dummy,dummy20, Testbuff[8];
uint8_t i=0;
uint32_t dummyTest=0;
for(i=0;i<8;i++)
{
     Testbuff[i]=0;
}

SPI2->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;

//Double check it, make sure the buffer is empty, you also can add a break point here, to check the RXNOTEMPTY bit in FIFOSTAT register.

while(SPI_GetStatusFlags(SPI2) & SPI_FIFOSTAT_RXNOTEMPTY_MASK) 
{
     dummyTest = SPI_ReadData(SPI2);//Put breakpoint here, if it really won't enter, this while code can be delete.
}
SPI2->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;

//Send Byte1
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, READ_FAST, 0);
}
//Send Byte2
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);
}
//Send Byte3
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);
}

//Send Byte4
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, (ui32Address & 0xff), 0);
}

//Send Byte5
if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{
     SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);
}
/* wait if TX FIFO of previous transfer is not empty */
 while (!(base->FIFOSTAT & SPI_FIFOSTAT_TXEMPTY_MASK)){};
 
 //read the bytes together
 
 for(i=0;i<8;i++)
 {
        if((SPI2->FIFOSTAT) & SPI_FIFOSTAT_RXNOTEMPTY_MASK)
        {
             Testbuff[i++] = (SPI2->FIFORD);
        }
 }
 
//then debug the code, stop here, check the TestBuff data, and i data.
//whether i=5, and Send me the TestBuff data. if TestBuff[4]= 0x60 as your SPI wave, then return this data.
return(Testbuff[5]);


}‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

Line 14-17 should check SPI_FIFOSTAT_RXNOTEMPTY_MASK, not TX, just like my comment.

Please use API test this picture:

pastedImage_1.jpg

Please also follow your own orginal test, write address 0x91 with 0XAA data, then read it, but just use my API to read it.

Then give me all the TestBuff[0-7] data, and the according SPI bus wave.

Your problem really in the read function, so use my code, and give me your debug result when you read the address 0X91 which already have the 0XAA data.

I need to check the details.

Waiting for your quick reply, if too long feedback, maybe I will forget it again Smiley Happy


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos
2,047 Views
fatihozen
Contributor IV

Hi Kerry Zhou,

at line 10 FIFOSTAT = 0x30.
while block between lines 14-17 doesn't cause a problem so I did not delete it.
I added some dummy write because you wrote 'READ_FAST' there. The result is :pastedImage_3.jpg

pastedImage_4.jpg

pastedImage_5.jpg

 TestBuff[0] = 0xff, 
 TestBuff[1] = 0xff, 

 TestBuff[2]  = 0xff,

 TestBuff[3]  = 0xff,

 TestBuff[4]  = 0xff,

 TestBuff[5]  = 0,

 TestBuff[6]  = 0,

 TestBuff[7]  = 0.

When I modify your function for normal speed read, I see that result:
TestBuff is the same.

pastedImage_6.jpg

int16_t E_Flash_Read_Byte_kerry(uint32_t ui32Address){
int16_t dummy,dummy20, Testbuff[8];
uint8_t i=0;
uint32_t dummyTest=0;
for(i=0;i<8;i++)
{Testbuff[i]=0;}

SPI2->FIFOCFG |= SPI_FIFOCFG_EMPTYTX_MASK | SPI_FIFOCFG_EMPTYRX_MASK;

while(SPI_GetStatusFlags(SPI2) & SPI_FIFOSTAT_RXNOTEMPTY_MASK)
{
dummyTest = SPI_ReadData(SPI2);//Put breakpoint here, if it really won't enter, this while code can be delete.
}
SPI2->FIFOSTAT |= SPI_FIFOSTAT_TXERR_MASK | SPI_FIFOSTAT_RXERR_MASK;


if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{ SPI_WriteData(SPI2, READ, 0);}

if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 16) & 0xff), 0);}

if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, ((ui32Address >> 8) & 0xff), 0);}


if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, (ui32Address & 0xff), 0);}

if (SPI_GetStatusFlags(SPI2) & kSPI_TxNotFullFlag)
{SPI_WriteData(SPI2, DUMMY_BYTE, kSPI_FrameAssert);}

while (!(SPI2->FIFOSTAT & SPI_FIFOSTAT_TXEMPTY_MASK)){};

for(i=0;i<8;i++)
{
if((SPI2->FIFOSTAT) & SPI_FIFOSTAT_RXNOTEMPTY_MASK)
{Testbuff[i++] = (SPI2->FIFORD);}
}

return(Testbuff[5]);
}

0 Kudos
2,047 Views
kerryzhou
NXP TechSupport
NXP TechSupport

Hi Fatih ozen,

   Thank you for your effort.

   I have bought 3 SST25VF016B chips, it's on the way now, I will test it directly on my side.

   Please send me your whole test project which contains this SPI driver, I will test it on my LPCXpresso 54608 board, and connect to the SST25VF016B chip, then the discuss will be more valuable.

 Send me your whole test project, you can delete other module code, just give the project contains the flash driver, which can reflect the problem, then tell me what the IDE you are using, after I get the chip, I will test it on my side.

Please also share me your SST25VF016B external circuit, I will solder it.


Have a great day,
Kerry

-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------

0 Kudos