EMI stuck in busy state when performing EMI_EraseAll

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
KaBr_4818621
Level 1
Level 1
Welcome!

Hello everyone!

I am currently working on an older (2017) project and codebase to resolve a problem that exists during a FOTA update (Bootloader + Bootloadable). The code appears to be based on the Project051_NOR_Flash_Bootloader example.

What I am seeing with the PSoC4 debugger is that it seems to get stuck in the ExternalMemoryInterface in the while loop that waits for the EMI_IsBusy() state to resolve. This is all happening while performing EMI_EraseAll, just before the FOTA update is about to start.

Is this something you have seen before, that you are aware of?

Maybe what I need to do to resolve this, is to simply update to the latest codebase of the example, because it appears to be slightly different. Was a bug like this resolved in the past? If so which part of the codebase would have to be updated? Some advice would be well appreciated.

Thank you for your help!

Karl

0 Likes
5 Replies
SudheeshK
Moderator
Moderator
Moderator
250 sign-ins First question asked 750 replies posted

Hello,

EMI_Busy() function will read status register of external NOR flash and check if the flash device is busy or not. We would like to know some more details about your application to assist you with this thread.

1. Which is the NOR flash device that you use in your application?

2. This error might happen when flash is in protected state. Please double check and confirm that flash is not in protected state. Both program and erase operations will fail when flash is protected.

Thanks and Regards,

Sudheesh

0 Likes

Hi Sudheesh,

I'm also part of Karl's team. He's back to work on Monday but I already wanted to provide some information to you:

The NOR flash component which was used is the Dragon Winner DW25Q16 16M BIT SPI NOR FLASH. Here's the data sheet: DW25Q16_v2.4.pdf - Google Drive

0 Likes

Hello,

Thank you for the datasheet. As I mentioned earlier, this issue may happen if the flash device is in protected state. Please double check and confirm that flash is in unprotected state. Are you able to perform normal program, read and erase operations on the flash device?

Thanks and Regards,

Sudheesh

0 Likes

Thank you for these pointers. I have tried checking the results of the status register read operations and what I am seeing is that whenever I encounter this busy-state issue, both bytes (tmpBuffer[0] and tmpBuffer[1]) of the status register read operations are showing a value of 0xFF!

/* Read 2 bytes data from the RX buffer */     
tmpBuffer[0] = (uint8) EMI_SPIM_ReadRxData();    
tmpBuffer[1] = (uint8) EMI_SPIM_ReadRxData();         

if(tmpBuffer[1] & EMI_BUSY_BIT_FIELD) {        
    /* External memory is busy */        
    status = true;    
} else {        
    /* External memory is available to accept next command */        
    status = false;    
}

Because of this the program considers the flash device to be busy.

I have added another function (mostly copied from EMI_IsBusy()) to be able to read out both status registers:

#define NOR_FLASH_INSTRUCTION_READ_SR1          (0x05) 
#define NOR_FLASH_INSTRUCTION_READ_SR2          (0x35) 
uint8 EMI_ReadStatus(uint8 readStatusInstruction) {    
    bool status = false;    
    uint8 dataPointer = 1;    
    uint8 tmpBuffer[2] = {0};    
    emiWriteBuffer[0] = readStatusInstruction;    
    emiWriteBuffer[1] = 0;    
    dataPointer = 2;
    /* Clear Rx and Tx Buffer */    
    EMI_SPIM_ClearRxBuffer();    
    EMI_SPIM_ClearTxBuffer();
    /* Pull Slave select low */    
    EMI_SPIM_SlaveSelect_Write(0);
    /* Write dummy content so MOSI is busy while MISO takes data */    
    EMI_SPIM_PutArray(emiWriteBuffer, dataPointer);    
    while(dataPointer != EMI_SPIM_GetRxBufferSize())
    {        
        /* Wait until the RX FIFO has the same entries as the amount         
         * transmitted - signifies a completed transfer.         
         */    
    }
    /* Pull Slave select high */    
    EMI_SPIM_SlaveSelect_Write(1);
    /* Read 2 bytes data from the RX buffer */    
    tmpBuffer[0] = (uint8) EMI_SPIM_ReadRxData();    
    tmpBuffer[1] = (uint8) EMI_SPIM_ReadRxData();     
    return tmpBuffer[1];
}

// Invoke status read
uint8 status1 = EMI_ReadStatus(NOR_FLASH_INSTRUCTION_READ_SR1);
uint8 status2 = EMI_ReadStatus(NOR_FLASH_INSTRUCTION_READ_SR2);

So, here I am also reading 255 on both, status1 and status2 whenever the problem appears.

However, I am not always seeing this behavior and I am not sure what causes this to happen. Sometimes I see tmpBuffer[0]=255 and tmpBuffer[1]=0 and in that scenario everything seems to run without problems.

Do you have any idea what might be going on? Do any of these statuses make sense to you?

Thanks!

0 Likes

Hello,

tmpBuffer[0]=255 and tmpBuffer[1]=0 looks like the correct status register value (0x00). When tmpBuffer[1] = 0xFF, I suspect that the flash devices is not driving any data on the SO line after receiving RDSR command, Or the flash device did not receive the RDSR command properly. Is it possible for your to capture logic analyzer traces for SR1 and SR2 read operations in both working and failing cases? We can compare them and see if there are any differences.

Also, in your previous response you have mentioned that there is some difference between our example project and your application. Could you please let us know the differences between the two projects? If possible, please attach your project to this forum thread, we can review it and let you know if there are any issues.

Thanks and Regards,

Sudheesh

0 Likes