Encountered the following issue with the iMX8 SPI after moving from fsl_ecspi.c driver to fsl_ecspi_cmsis.c driver. fsl_ecspi_cmsis.c driver being top layer above the fsl_ecspi.c driver.
iMX8 SPI FIFO is 64 entries deep 32 bits wide (4 bytes wide). The fsl_ecspi.c driver treats all transfers as 32-bit wide, as seen below.
In my application, I needed to receive 76 bytes, which is 19 32-bit transfers. I called CMSIS method ECSPI_InterruptReceive() with data pointer to 76 bytes and num equal to 19. Burst Length is configured to 32 (32 is stored as 31 in hardware register). ECSPI_InterruptReceive() calculates xfer.dataSize to equal 76 under this situation [76 = 19 * ((31 + 8)/8)]. xfer.dataSize equal 76 causes SPI receive interrupt to perform 76 32-bit transfers into data pointer and therefore causes memory corruption because data pointer only points to 76 bytes. Changing ECSPI_InterruptReceive() as below for xfer.dataSize equal to 19 resolved my issue. xfer.dataSize equal to 19 causes SPI receive interrupt to perform 19 32-bit transfer into data pointer, which is the correct 76 bytes.
Hello @frank9,
I hope you are doing well.
Please accept my apology for the delayed response.
Can you share error logs to debug them?
It will help us to narrow down the issue.
Thanks & Regards,
Sanket Parekh
I really do not have any error logs to share beyond what I posted. With the posted modification to ECSPI_InterruptReceive() my application appears to be functioning correctly. I just wanted to share a modification that I needed to implement.
Hello @frank9,
I hope you are doing well.
->From the description it appears that the fsl_ecspi_cmsis.c driver is treating all transfers as 32-bit wide, while the SPI FIFO is only 64 entries deep.
->This means that the driver can only transfer 64 bytes at a time. When the driver is called to transfer 76 bytes, it will actually perform 76 32-bit transfers, which will cause memory corruption because the data pointer only points to 76 bytes.
Please make sure to change the fsl_ecspi_cmsis.c driver to treat transfers as 8-bit wide.
Split the transfer into two parts: 64 bytes and 12 bytes.
Please check with the above suggestion, It may help you!
Thanks & Regards,
Sanket Parekh