Memory issue either RPC or my eeprom class

03 Oct 2010 . Edited: 03 Oct 2010

Hey Guys,

I seem to have a memory problem, I look at the graph provided by the online compiler below and this shows me ive use 1.4k(5%) in memory.

And I also have used show memory function posted in another thread. And call the below whilst the program is running, it would seem that I only have 1.2k left.

Checking memory with blocksize 256 char ...

256 @ 0x10006540
512 @ 0x10006540
768 @ 0x10006540
1024 @ 0x10006540
1280 @ 0x00000000
Ok for 1024 char

 

 

So the program was crashing in all time, in different spots. So this lead me to memory issue, ive noticed on multiple write the device will hard fault like its not releasing memory. Here is my write code

 

int eeprom::write(int address, char *str) {

    string s(str);

    wp = 0; // disable write protect

    int size = (strlen(str)/2) + 2;
    char data[size];

    data[0] = address >> 8;
    data[1] = address ;//& 0xFF; // address is 0x0000, data is 0x5A


    for (int i=2; i<size; i++) {
        string sub = s.substr(((i-2)*2),2);

        const char* pszConstString = sub.c_str ();
        int value = (int) strtol (pszConstString,NULL,16);

        data[i]=value;
    }

    if (i2c.write(0xA0, data, size)) {
        printf("Write failed\n\r");
    }


    int poll = 0;
    while (i2c.write(0xA0, NULL, 0)) { // wait until we get an acknowledge
        poll++;
    }

    //  printf("OK\n\r", poll);
    printf("%d %d %d\n\rOK\n\r",data[0],data[1],size);
    return 0;
}

 

 

I write in 0x2 hex value to get around the RPC class not being able to handle all characters.

 

I use this method with a static function call exposed as RPC function, for example (BOLD is output)

 

mcu:rcp /eeprom/write 0  01FD090000000000002A00005365747570566950454328313135323030293B0D53657443414E537065656428362C353030303030290001FD08140000000000AB

0 64 42

OK

mcu:rcp /eeprom/write 64  0000673D727063414E53656E6428362C30783238302C382C307834392C302C302C52536869667428

0 128 66

OK

mcu:rcp /eeprom/write 128  672C38292C52536869667428672C30292C302C302C30293B0D43414E53656E6428362C30783238382C382C307834322C31302C302C302C39352C37372C302C30

 

Hard Fault!

Jason


03 Oct 2010

ps this is how I am calling a static function.

in eeprom.cpp

rpc_class *eeprom::get_rpc_class() {
    static const rpc_function funcs[] = {
        { "read", rpc_function_caller },
        { "write", rpc_function_caller },
        RPC_METHOD_END
    };
    static rpc_class c = { "eeprom", funcs, NULL };
    return &c;
}

 

in eeprom.h

static int write(int address, char *str);
static char* read(int address, int size);

03 Oct 2010

and how I get a serial command to call the rpc

in main.cpp

 if (s.find_first_of("mcu:rpc ")==0) {
        rpc(s.substr(8,s.size()-8).c_str(), outbuf);
        console_port.printf("\n\r%s",outbuf);
}

03 Oct 2010
user Jason Engelman wrote:
I seem to have a memory problem

Hi Jason

Are you using the beta compiler (memory usage is just reported for the main 32K with the beta)?

When you say you are using 1.4 kB, you are ignoring the 12 kB of RAM (not flash) used by your library code. So your statically allocated RAM usage is 14 kB (nearly half of your main RAM bank). Then you need space for a stack and a heap (which you can't see on the RAM usage graph).

Are you using the network stack? A few memory issues there as well.

Regards
Daniel

03 Oct 2010

user avatar Daniel Peter wrote:
e beta compiler

Daniel,

No, not using beta atm. Not using the the network stack. My program is pretty big as it has few other components aswell. But this is just with the above the write command just doesnt seem to let go of the memory.

If I start it up and just show memory I have this

Checking memory with blocksize 256 char ...

256 @ 0x10005E68

512 @ 0x10005E68

768 @ 0x10005E68

1024 @ 0x10005E68

1280 @ 0x10005E68

1536 @ 0x10005E68

1792 @ 0x10005E68

2048 @ 0x10005E68

2304 @ 0x10005E68

2560 @ 0x10005E68

2816 @ 0x10005E68

3072 @ 0x10005E68

3328 @ 0x10005E68

3584 @ 0x00000000

Ok for 3328 char


But when I call my eeprom write RPC command, it just doesnt let go. I few write commands succeeds, with show mem afterwards ( see below)

Checking memory with blocksize 256 char ...

256 @ 0x100067D8

512 @ 0x100067D8

768 @ 0x100067D8

1024 @ 0x100067D8

1280 @ 0x00000000

Ok for 1024 char

 

But the next time I run a few write RPC commands it. It hangs.

 

 

 

 

 

 

03 Oct 2010

Hi Jason

I've never dabbled with the rpc code so I can't be too much help. If you think the problem is due to running out of memory, can you cut your code right back to isolate the classes of interest and prove that they work when they have enough memory? Then start adding things back in until something breaks. Then optimise your code, and think about using the AHBSRAM0 and AHBSRAM1 banks of RAM as well. It's always possible there is a memory leak somewhere ie. dynamic memory allocation that is never being cleaned up. Are you creating objects where you should be calling explicit destructors?

I think the mbed is not too good on dynamic memory management; there is no easy way to see how much stack or heap you have used. I'm playing now with scmRTOS (thanks to Igor) and at least there you can set a fixed size for the stack of each process and monitor how much is being used. Whether that turns out to be a good idea ...

Regards
Daniel

11 Oct 2010 . Edited: 11 Oct 2010

 

user Daniel Peter wrote:

Hi Jason

I've never dabbled with the rpc code so I can't be too much help. If you think the problem is due to running out of memory, can you cut your code right back to isolate the classes of interest and prove that they work when they have enough memory? Then start adding things back in until something breaks. Then optimise your code, and think about using the AHBSRAM0 and AHBSRAM1 banks of RAM as well. It's always possible there is a memory leak somewhere ie. dynamic memory allocation that is never being cleaned up. Are you creating objects where you should be calling explicit destructors?

I think the mbed is not too good on dynamic memory management; there is no easy way to see how much stack or heap you have used. I'm playing now with scmRTOS (thanks to Igor) and at least there you can set a fixed size for the stack of each process and monitor how much is being used. Whether that turns out to be a good idea ...

Regards
Daniel

 

 

Thanks Daniel for the reply,

how do you address the AHBSRAM0 and AHBSRAM1 banks? Are there any example around to use this space.

 

 

11 Oct 2010

Hi Jason

You add an attribute when declaring a variable eg. the following code creates buffers in both RAM banks:

unsigned char buf0[0x4000] __attribute((section("AHBSRAM0"),aligned));
unsigned char buf1[0x2465] __attribute((section("AHBSRAM1"),aligned));

You'll get a warning from the compiler if you declare too much, but I think there is a process whereby main RAM will be used instead of the RAM bank if you go to large and there is space available in the main RAM. Best to play around ...

Regards
Daniel

 

12 Oct 2010 . Edited: 12 Oct 2010

Daniel,

I take it you can only do this on global static types, you cannot say do it on a object. Like

myobject test("something") __attribute((section("AHBSRAM0"),aligned));


What about this method below in myobject.h, I have tried but seems the map still get alloc'ed in the main 32k

#pragma arm section zidata = "AHBSRAM0", rwdata = "AHBSRAM0"

class myobject
  {

   std::map<std::string, double> maymap_;

}

#pragma arm section

 

 



12 Oct 2010

Hi Jason

I think you're right that you can only use the attribute on global static types. With regards to dynamic types, they should be allocated from the heap (of which there is only one in main memory).

If you look into the code for the networking stack, lwip uses its own alloc functions to provide dynamic memory allocation in the AHB RAM area, so that might be helpful. It's C rather than C++ types though.

Regards
Daniel