_esdhc_read, SD, and cache?

cancel
Showing results for 
Search instead for 
Did you mean: 

_esdhc_read, SD, and cache?

1,767 Views
pbanta
Contributor IV

My environment:  MQX 4.1, MFS, K70FX, eMMC, DDR

I'm writing a small ascii file to MFS installed over the SD card driver.  When I try to display the contents of the file (using the "type" shell command) I can see corrupted data sometimes.  Not all the time.  I have noticed that if I create multiple files and then "type" them from the shell, sometimes the data printed to the shell is good and other times the data is corrupted.  I have tracked the corruption to the esdhc driver.  I am seeing data corruption when the ADMA engine transfers data to DDR.  After the transfer is complete the buffer in DDR contains some new data mixed with old data.  For example, if I "type" file1.txt and then "type" file2.txt, the data printed to the screen contains file1.txt data intermixed with file2.txt data.

I don't understand the ESDHC_IS_HANDLING_CACHE code.  What is the purpose of head, body, and tail?  It looks like ESDHC_IS_HANDLING_CACHE is not meant to be optional.  It's forced true in esdhc_prv.h.

I'm also wondering if the problem may be related to the clock domains between the eMMC and DDR.  I've run pattern tests, walking ones/zeros over the address range of DDR with no errors.  My eMMC clock is running at approximately 750kHz and the DDR clock is 120MHz.  I think the ADMA is sitting in the middle transferring data from SDHC_DATPORT to DDR.

Has anyone seen any issues like this before?

Thanks. 

Labels (1)
Tags (5)
12 Replies

787 Views
pavel_chromy
NXP Employee
NXP Employee

Dear pbanta,

ESDHC_IS_HANDLING_CACHE defaults to 1 for platforms which feature data cache. This macro is not a user option - it has to correspond with cache setting (enabled/disabled). Please do not change it unless you are absolutely sure that you know what you are doing (e.g. you have the data cache intentionally disabled or so).

K70 features data cache and I suppose that you have it enabled so PSP_HAS_DATA_CACHE should be 1. Could you, please, verify that it is so?

Best regards, Pavel

0 Kudos

787 Views
pbanta
Contributor IV

HI Pavel,

Yes, I can verify that PSP_HAS_DATA_CACHE is set to 1 in kinetis.h.  And from esdhc_prv.h:

#ifndef ESDHC_IS_HANDLING_CACHE

  #define ESDHC_IS_HANDLING_CACHE PSP_HAS_DATA_CACHE

#endif

Thanks for the help,

Paul

0 Kudos

787 Views
KenOverly
Contributor I

I've been looking at the sdcard driver in more detail and stepping through the code in the debugger.  @pbanta asked about the usage of the head, body, and tail dma transfer buffers.  This section of code looks unusual to me as well.

When executed in the debugger the number of bytes to read (variable n) passed into _eshdc_read() is always 512.  The 'head' buffer descriptor always ends up being 32 bytes, the 'body' descriptor is 480 bytes, and the 'tail' descriptor is not used.  Also interesting to note is that the head buffer descriptor transfers data from a different area of memory than the body buffer descriptor.  The head uses 32 bytes of memory allocated during initialization of the sdcard driver in _eshdc_install(), whereas the body buffer descriptor uses memory passed into _eshdc_read() via the data_ptr variable.

I've also referenced the SD host controller spec PDF document located on the sdcard.org website.  It provides specific details of the ADMA transfer process, but did not shed any light on why the MQX driver is designed the way that it is.

Does anyone understand why the adma buffer transfer was designed this way?

0 Kudos

787 Views
pbanta
Contributor IV

Hi Ken,

Sorry for the delay in replying.  I got busy with other portions of the firmware and forgot about this because I worked around the problem.  I got rid of DMA in the driver.  Yes, it's slower, but it is reliable and my application doesn't need high speed access to the eMMC and I have "bigger fish to fry".  I would like to see this issue addressed and fixed because I would prefer not to have custom modifications in my peripheral IO drivers.  I ended up using the Cloning Wizard to export an MQX tree and I made all my changes in the exported tree.

Paul

0 Kudos

787 Views
akobyl
Contributor I

I know this is dredging up an old thread, but how exactly were you able to get rid of the DMA?  Looking at the reference manual (VFxxx Controller Reference Manual Rev 0 figure 10-41) it appears the only way to output data from the SDHC peripheral is via DMA.  Thanks

0 Kudos

787 Views
tobiasmaurer
Contributor I

Hi everyone,

I don't understand the head, body, tail ADMA handling in the driver either. Maybe someone could give us some hints?

I am working with MQX 4.1.2 on the Vybrid M4. I also see problems with with SD-card driver (_esdhc_read) in combination with active caches and cached memory. (but I think in my case it has nothing to do with DDR3 or interrupts) 

I think it is problem regarding the cache handling in the driver and the cache controller.

In my case I found a workaround in my application to have data consistency after a read access:

flush the data after buffer_read re-init -> then start the read access

(open file in filesystem, loop: write access, CRC handling, etc.)

...

     memset(buffer_read, 0, accessSize );

     //workaround to to fix problem in case of application uses cached memory

     _DCACHE_FLUSH_MBYTES(buffer_read, accessSize );    

     returnSize = read(fd, buffer_read, accessSize );

...

Could anyone try or approve this?

BR Tobi

0 Kudos

787 Views
KenOverly
Contributor I

Hi pbanta,

Have you had any success in resolving your issue with the sdcard?  I ask because I've had a similar problem which I reported in another forum post (see here).

I observed that corruption seems to occur when interrupts occur while data is being copied to/from the sdcard dma buffer.  As a test I modified the sdcard driver to disable interrupts while the data is copied and it has significantly improved my problem.  I provided details on what I changed in the other post hoping that Freescale will comment.

Perhaps you could try making the same change and report whether it helps your particular issue?

Thanks,

-Ken

0 Kudos

787 Views
RadekS
NXP Employee
NXP Employee

We know about sporadic problem with DDR under MQX4.1.

TWR-K70F120M BSP configures incorrect DDR2 clock frequency. By default it is 120 MHz. JEDEC specifications minimum requires 125 MHz. Maximum allowed by K70 chip is 150 MHz.

There is Freescale MQX RTOS 4.1.0.1 Patch which apply fix for this issue – increase DDR clock.

https://www.freescale.com/webapp/sps/download/license.jsp?colCode=FSLMQXOS_4_1_0_1_PATCH

Could you please try applying this patch and testing it again?

If this doesn’t help, could you please share here code which you use for writing your files – that we can reproduce it on our side under the same conditions?


Have a great day,
RadekS

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

0 Kudos

787 Views
sohamd
Contributor I

can you resend the patch again

0 Kudos

786 Views
pbanta
Contributor IV

I set PLL1 to 125MHz and I see the same result.  Data in DDR is corrupted after ADMA from SDHC controller.  I will share the code but it's not ready yet.

Thanks,

Paul

0 Kudos

786 Views
pbanta
Contributor IV

I had PLL1 set to 150MHz when I discovered the problem.  According to the K70 reference manual PLL1 is used to provide clock to the DDR controller.  I lowered PLL1 to 120MHz and I still saw the problem.  I will try 125MHz and let you know the results.

Thanks,

Paul

0 Kudos

787 Views
pbanta
Contributor IV

Can anyone at Freescale confirm that the K70 SDHC errata is accounted for in the MQX 4.1 esdhc driver?

0 Kudos