cancel
Showing results for 
Search instead for 
Did you mean: 

stm32f405 random hard, usage, bus ore memory-fault

s239955_stm1
Associate II
Posted on December 05, 2013 at 12:17

Hey there,

Our problem is that we get random faults (memory, bus or usage)!

The handlers are calling sporadically between 10s to some hours! But we have also pcb�s without any issues!

We are using a custom environment with a STM32F405ZGT and an external PSRAM!

From software side we have the Keil os without micro lib (due to usage of a cpp library)

We are using excessive dynamic memory but only in external RAM! All other RAM access goes to internal one.

A further interface we are using in a high priority is the SPI2 interface with DMA functionality!

If we stop in an error handler, we recognize invalid addresses in pc (like: 0xE0C001E0; 0x804AED2; 0xFFFFFFFE; 0x46604630 or 0x00000000)

Does anybody have an idea?

#stm32f4 #stm32 #fault
30 REPLIES 30
s239955_stm1
Associate II
Posted on December 16, 2013 at 10:03

The code for the memory-test, we are using every start-up, was implemented to detect wrong solder or defect RAM-cells. And it looks like as followed:

bool bl_test_ext_ram(void) {

    bool error = false;

    static unsigned int data = 1;

    static unsigned long *address = (unsigned long*)0x60000000;

    static unsigned int offset;

    for (offset = 1; offset <= (size_ext_ram / sizeof(bitsize_ext_databus)); offset = offset << 1) {

        *address = data;

        *(address + offset) = ~data;

        if (*address != data)

            error = true;

        if (*(address + offset) != ~data)

            error = true;

        data = (data << 1) | (data >> (8 * sizeof(int) - 1));

    }

    address = (unsigned long*)0x60000000;

    while ((unsigned long) address < (0x60000000 + size_ext_ram)) {

        *address = 0xAAAA5555;

        if (*address != 0xAAAA5555)

            error = true;

        *address = 0x5555AAAA;

        if (*address != 0x5555AAAA)

            error = true;

        address += 1;

    }

    return error;

}

Posted on December 16, 2013 at 16:55

FSMC_NORSRAMInitStructure.FSMC_WaitSignal = FSMC_WaitSignal_Enable; //???

This might a little more aggressive, I didn't understand the purpose of statics, the memory array should probably be defined as volatile to force the compiler to actually read memory instead of optimize it out.

// MemTest(0x60000000, (4 * 1024 * 1024)); // 4MB device at 0x60000000
int MemTest(unsigned long Address, unsigned long Size) // Size in bytes
{
volatile unsigned long *addr;
unsigned long length = Size / sizeof(unsigned long); // length in 32-bit words
unsigned long offset;
unsigned long data;
// Stepping Address bus test
addr = (volatile unsigned long *)Address;
offset = 1;
data = 0xFFFE0001;
while(offset < 
length
)
{
addr[0] = data;
addr[offset] = ~data;
if ((addr[0] != data) || (addr[offset] != ~data))
return(0); // Failed
data = (data << 1) | (data >> (8 * sizeof(data) - 1)); // rotate
offset <<= 1;
}
// Stuck at test for data lines/cells 
addr = (volatile unsigned long *)Address;
offset = length;
while(offset--)
{
*addr = 0xAAAA5555;
if (*addr != 0xAAAA5555)
return(0); // Failed
*addr = 0x5555AAAA;
if (*addr != 0x5555AAAA)
return(0); // Failed
addr++;
}
// Fill entire specified array with unique data, rapidly
addr = (volatile unsigned long *)Address;
offset = length;
while(offset--)
*addr++ = (unsigned long)addr;
// Revisit and compare
addr = (volatile unsigned long *)Address;
offset = length;
while(offset--)
{
if (*addr != (unsigned long)addr)
return(0); // Failed
addr++;
}
return(1); // Memory Test Passed
}

A more aggressive approach still would be STM/LDM in assembler. The failure of the memory should be demonstrable outside of application execution.
Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
d2399
Associate II
Posted on December 17, 2013 at 09:11

FSMC_NORSRAMInitStructure.FSMC_WaitSignal = FSMC_WaitSignal_Enable;

This should have no influence, but I put it to disable, the NWAIT is not used in our application! Thanks for this hint!

Actual we are testing your code and we are waiting for an issue! Thanks for that...

I attach some screenshots of data communication between MCU and PSRAM! Maybe you can see anything!?!?

Thanks...

________________

Attachments :

SCR07.PNG : https://st--c.eu10.content.force.com/sfc/dist/version/download/?oid=00Db0000000YtG6&ids=0680X000006I0ld&d=%2Fa%2F0X0000000bdR%2FbpWsdR6nsyw5EESxQl7cPQOU71QHStQmVgGF8lhwbcA&asPdf=false

SCR08.PNG : https://st--c.eu10.content.force.com/sfc/dist/version/download/?oid=00Db0000000YtG6&ids=0680X000006I0hO&d=%2Fa%2F0X0000000bdQ%2Fi1bmMIROwtCYsjiJeamIyYfbypYWiOrUoeBk5IYLaWg&asPdf=false

SCR09.PNG : https://st--c.eu10.content.force.com/sfc/dist/version/download/?oid=00Db0000000YtG6&ids=0680X000006I0lY&d=%2Fa%2F0X0000000bdP%2Frvk.EbeLImFH1kml.sMiBaqvQMUBWUDh3zoxFjG6l_M&asPdf=false
Posted on December 17, 2013 at 11:16

The /CS and /WR high duration is surprisingly short, and may violate the required tCPH/tWPH - hard to say from this screenshot. However, according to the diagram for mode A write in UM (fig.436), /WR high should be determined by ADDSET cycles. In the code snippets you gave above it appears you set ADDSET (address setup time) to nonzero - can you please confirm what is actually written in the respective FSMC registers?

JW

s239955_stm1
Associate II
Posted on December 17, 2013 at 13:31

We confirm that the configuration is set to the right FSMC-registers. I double-check this and the configuration is also not overwritten after the initialisation-phase.

The Min-Values for tCPH and tWPH are 5 and 10 ns. I also quite sure that we do not fall below that values, but I will check this...

d2399
Associate II
Posted on December 17, 2013 at 16:07

Clive's testcode is running since 8 hours at -20 deg. with no issues!

In parallel we test a software with the heap in internal RAM and only some unimportant buffers in external RAM and this SW is also running without issues! Because this fact we think the application sw has no illegal pointer operations or something else!

Posted on December 18, 2013 at 08:20

And what did you change since the last failing case?

I am somewhat reluctant to admit that *disabling* waitstates could increase stability.

Could you please post the complete initialization code used when the above waveforms were taken? I assume you are running the tests with the very same settings.

JW

d2399
Associate II
Posted on December 18, 2013 at 10:18

Thats the latest configuration:

        p.FSMC_AddressSetupTime = 0xF;// (1/168MHz) * 15 -> 88,5ns

        p.FSMC_AddressHoldTime = 0xF;// (1/168MHz) * 15 -> 88,5ns

        p.FSMC_DataSetupTime = 0x0F;// (1/168MHz) * 15 -> 88,5ns

        p.FSMC_BusTurnAroundDuration = 0x0;// no HCLK cycles added

        p.FSMC_CLKDivision = 0x1;// clock divided by 2

        p.FSMC_DataLatency = 0x0;//due to ''note'' ref. man.(DM00031020) page 1555/1705

                                                            //''with PSRAMs the DATLAT field must be set to 0''

        p.FSMC_AccessMode = FSMC_AccessMode_A;

        FSMC_NORSRAMInitStructure.FSMC_Bank = FSMC_Bank1_NORSRAM1;

        FSMC_NORSRAMInitStructure.FSMC_DataAddressMux = FSMC_DataAddressMux_Disable;

        FSMC_NORSRAMInitStructure.FSMC_MemoryType = FSMC_MemoryType_PSRAM;

        FSMC_NORSRAMInitStructure.FSMC_MemoryDataWidth = FSMC_MemoryDataWidth_16b;

        FSMC_NORSRAMInitStructure.FSMC_BurstAccessMode = FSMC_BurstAccessMode_Disable;

        FSMC_NORSRAMInitStructure.FSMC_AsynchronousWait = FSMC_AsynchronousWait_Disable;

        FSMC_NORSRAMInitStructure.FSMC_WaitSignalPolarity = FSMC_WaitSignalPolarity_Low;

        FSMC_NORSRAMInitStructure.FSMC_WrapMode = FSMC_WrapMode_Disable;

        FSMC_NORSRAMInitStructure.FSMC_WaitSignalActive = FSMC_WaitSignalActive_BeforeWaitState;

        FSMC_NORSRAMInitStructure.FSMC_WriteOperation = FSMC_WriteOperation_Enable;

        FSMC_NORSRAMInitStructure.FSMC_WaitSignal = FSMC_WaitSignal_Disable;

        FSMC_NORSRAMInitStructure.FSMC_ExtendedMode = FSMC_ExtendedMode_Disable;

        FSMC_NORSRAMInitStructure.FSMC_WriteBurst = FSMC_WriteBurst_Disable;

        FSMC_NORSRAMInitStructure.FSMC_ReadWriteTimingStruct = &p;

        FSMC_NORSRAMInitStructure.FSMC_WriteTimingStruct = &p;

Posted on December 18, 2013 at 14:05

All I say is, that the waveforms given above don't appear to reflect these settings. /WE should be shorter than /CE by ADDSET cycles, see Fig.436 on page 1530.

JW

d2399
Associate II