Netduino home hardware projects downloads community

Jump to content


The Netduino forums have been replaced by new forums at community.wildernesslabs.co. This site has been preserved for archival purposes only and the ability to make new accounts or posts has been turned off.
Photo

OutOfMemoryException, but I still have free memory!


  • Please log in to reply
14 replies to this topic

#1 Valkyrie-MT

Valkyrie-MT

    Advanced Member

  • Members
  • PipPipPip
  • 315 posts
  • LocationIndiana, USA

Posted 24 December 2010 - 03:38 PM

I am getting the exception below. I am playing with that NetduinoPlusWebServer app from this thread. It seems to keep throwing an exception, usually on the substring command. I figured I was probably carelessly leaking memory, so I used the following command to watch the memory run out:

Debug.Print("Memory: " + Microsoft.SPOT.Debug.GC(false).ToString());
It looks like I have plenty of memory before the command. So am I missing something? What Memory is it talking about here?

Memory: 13680
    #### Exception System.OutOfMemoryException - CLR_E_OUT_OF_MEMORY (5) ####
    #### Message: 
    #### System.String::Substring [IP: 0000] ####
    #### NetduinoPlusWebServer.Request::ProcessRequest [IP: 0025] ####
    #### NetduinoPlusWebServer.Request::.ctor [IP: 0010] ####
    #### NetduinoPlusWebServer.Listener::StartListening [IP: 00de] ####
A first chance exception of type 'System.OutOfMemoryException' occurred in mscorlib.dll
An unhandled exception of type 'System.OutOfMemoryException' occurred in mscorlib.dll

Also, here are the assemblies being loaded:
Assembly: mscorlib (4.1.2821.0) (3880 RAM - 33236 ROM - 19134 METADATA)
Assembly: Microsoft.SPOT.Native (4.1.2821.0) (1144 RAM - 6516 ROM - 4479 METADATA)
Assembly: Microsoft.SPOT.Hardware (4.1.2821.0) (1752 RAM - 11440 ROM - 7371 METADATA)
Assembly: Microsoft.SPOT.Net (4.1.2821.0) (704 RAM - 5060 ROM - 2452 METADATA)
Assembly: System (4.1.2821.0) (872 RAM - 5992 ROM - 3206 METADATA)
Assembly: Microsoft.SPOT.IO (4.1.2821.0) (740 RAM - 4620 ROM - 2522 METADATA)
Assembly: System.IO (4.1.2821.0) (1548 RAM - 13292 ROM - 5862 METADATA)
Assembly: Microsoft.SPOT.Hardware.SerialPort (4.1.2821.0) (508 RAM - 3440 ROM - 1527 METADATA)
Assembly: Microsoft.SPOT.Hardware.Usb (4.1.2821.0) (580 RAM - 3740 ROM - 1844 METADATA)
Assembly: SecretLabs.NETMF.Hardware (4.1.0.0) (256 RAM - 1108 ROM - 491 METADATA)
Assembly: SecretLabs.NETMF.Diagnostics (4.1.0.0) (180 RAM - 440 ROM - 166 METADATA)
Assembly: NetduinoPlusWebServer (1.0.0.0) (1284 RAM - 19852 ROM - 12230 METADATA)
Assembly: SecretLabs.NETMF.Hardware.Netduino (4.1.0.0) (268 RAM - 796 ROM - 423 METADATA)
Resolving.

-Valkyrie-MT

#2 Corey Kosak

Corey Kosak

    Advanced Member

  • Members
  • PipPipPip
  • 276 posts
  • LocationHoboken, NJ

Posted 24 December 2010 - 03:52 PM

I don't know, but one trick that might help is to put this line near the start of your program:

Debug.EnableGCMessages(true);

And then watch the memory statistics in your debug output window. Hopefully you'll see a pattern as they dwindle down to nothing...

#3 Valkyrie-MT

Valkyrie-MT

    Advanced Member

  • Members
  • PipPipPip
  • 315 posts
  • LocationIndiana, USA

Posted 24 December 2010 - 05:31 PM

... put this line near the start of your program:

Debug.EnableGCMessages(true);


Great idea. Here is the output. I still don't see how it runs out of memory...

GC: 2msec 37308 bytes used, 13668 bytes available
Type 0F (STRING              ):    456 bytes
Type 11 (CLASS               ):   3468 bytes
Type 12 (VALUETYPE           ):     60 bytes
Type 13 (SZARRAY             ):  10416 bytes
Type 15 (FREEBLOCK           ):  13668 bytes
Type 17 (ASSEMBLY            ):  13788 bytes
Type 18 (WEAKCLASS           ):     48 bytes
Type 19 (REFLECTION          ):     24 bytes
Type 1B (DELEGATE_HEAD       ):    252 bytes
Type 1D (OBJECT_TO_EVENT     ):    168 bytes
Type 1E (BINARY_BLOB_HEAD    ):   1884 bytes
Type 1F (THREAD              ):   2304 bytes
Type 20 (SUBTHREAD           ):    288 bytes
Type 21 (STACK_FRAME         ):   2352 bytes
Type 27 (FINALIZER_HEAD      ):    336 bytes
Type 31 (IO_PORT             ):    252 bytes
Type 34 (APPDOMAIN_HEAD      ):     72 bytes
Type 36 (APPDOMAIN_ASSEMBLY  ):   1140 bytes
Memory: 13668
GC: 2msec 37740 bytes used, 13236 bytes available
Type 0F (STRING              ):    888 bytes
Type 11 (CLASS               ):   3468 bytes
Type 12 (VALUETYPE           ):     60 bytes
Type 13 (SZARRAY             ):  10416 bytes
Type 15 (FREEBLOCK           ):  13236 bytes
Type 17 (ASSEMBLY            ):  13788 bytes
Type 18 (WEAKCLASS           ):     48 bytes
Type 19 (REFLECTION          ):     24 bytes
Type 1B (DELEGATE_HEAD       ):    252 bytes
Type 1D (OBJECT_TO_EVENT     ):    168 bytes
Type 1E (BINARY_BLOB_HEAD    ):   1884 bytes
Type 1F (THREAD              ):   2304 bytes
Type 20 (SUBTHREAD           ):    288 bytes
Type 21 (STACK_FRAME         ):   2352 bytes
Type 27 (FINALIZER_HEAD      ):    336 bytes
Type 31 (IO_PORT             ):    252 bytes
Type 34 (APPDOMAIN_HEAD      ):     72 bytes
Type 36 (APPDOMAIN_ASSEMBLY  ):   1140 bytes
Could not allocate 74 blocks, 888 bytes. Compacting memory.

    #### Exception System.OutOfMemoryException - CLR_E_OUT_OF_MEMORY (5) ####
    #### Message: 
    #### System.String::Substring [IP: 0000] ####
    #### NetduinoPlusWebServer.Request::ProcessRequest [IP: 0025] ####
    #### NetduinoPlusWebServer.Request::.ctor [IP: 0010] ####
    #### NetduinoPlusWebServer.Listener::StartListening [IP: 00de] ####
A first chance exception of type 'System.OutOfMemoryException' occurred in mscorlib.dll
An unhandled exception of type 'System.OutOfMemoryException' occurred in mscorlib.dll


#4 Corey Kosak

Corey Kosak

    Advanced Member

  • Members
  • PipPipPip
  • 276 posts
  • LocationHoboken, NJ

Posted 24 December 2010 - 05:51 PM

It's a little puzzling. I think the program does a couple of needless copies, but even so I don't see why it's running out of memory. Would you be willing to try something just to satisfy my curiosity?

in Request.cs, substitute this routine for ProcessRequest() and then tell me what the output is.

        private void ProcessRequest(char[] data)
        {
            Debug.Print("data length is "+data.Length);
            string content = new string(data);
            var indexOf=content.IndexOf('\n');
            Debug.Print("indexOf is "+indexOf);
            string firstLine = content.Substring(0, indexOf);

            // Parse the first line of the request: "GET /path/ HTTP/1.1"
            string[] words = firstLine.Split(' ');
            method = words[0];
            url = words[1];

            // Could look for any further headers in other lines of the request if required (e.g. User-Agent, Cookie)
        }


#5 Corey Kosak

Corey Kosak

    Advanced Member

  • Members
  • PipPipPip
  • 276 posts
  • LocationHoboken, NJ

Posted 24 December 2010 - 05:57 PM

Oh yeah, and add a Debug.GC(true) to the first line of that routine so we can get one more GC status message just before the s*** hits the fan.

#6 Chris Walker

Chris Walker

    Secret Labs Staff

  • Moderators
  • 7767 posts
  • LocationNew York, NY

Posted 24 December 2010 - 06:31 PM

Valkyrie-MT,

Really interesting. Could you try something in your code right before the function which causes the "compacting memory" message?

Debug.GC(true);

We identified an issue in .NET MF a while ago where the garbage collector was not collecting/compacting properly. Basically, if there were huge chunks of memory available...but not contiguously, the automatic garbage collector was not compacting fully (and the memory allocator couldn't allocate a contiguous block of memory because the memory in use wasn't leaving a big enough contiguous block of RAM)... Interestingly, a manual garbage collection request seemed to fix the issue...

...but we need a good repro case to fix it (or as is more likely in the case of GC, assist Microsoft in fixing it in the core).

If Debug.GC(true) fixes it, that gives us both a good short-term fix and hopefully a repro case so the root cause can be remedied.

Chris

#7 Valkyrie-MT

Valkyrie-MT

    Advanced Member

  • Members
  • PipPipPip
  • 315 posts
  • LocationIndiana, USA

Posted 24 December 2010 - 08:47 PM

Valkyrie-MT,

Really interesting. Could you try something...

Debug.GC(true);


Well, that's exactly what I did about 3 hours ago and I have not been able to reproduce the Memory exception since. I was serving pages continuously for 2 hours straight to 3 different computers and did not get even one exception. I switched that setting back to false ( Debug.GC(false); ) and within 10 seconds had another Memory exception. It reproduces 50-60% of the time and the stack shows different sources from time to time. The second run set to false did not throw an exception. The third time did again and here is that exception:

GC: 3msec 37464 bytes used, 13512 bytes available
Type 0F (STRING              ):    576 bytes
Type 11 (CLASS               ):   3576 bytes
Type 12 (VALUETYPE           ):     60 bytes
Type 13 (SZARRAY             ):   9516 bytes
Type 15 (FREEBLOCK           ):  13512 bytes
Type 17 (ASSEMBLY            ):  13788 bytes
Type 18 (WEAKCLASS           ):     48 bytes
Type 19 (REFLECTION          ):     24 bytes
Type 1B (DELEGATE_HEAD       ):    252 bytes
Type 1D (OBJECT_TO_EVENT     ):    168 bytes
Type 1E (BINARY_BLOB_HEAD    ):   1884 bytes
Type 1F (THREAD              ):   2304 bytes
Type 20 (SUBTHREAD           ):    288 bytes
Type 21 (STACK_FRAME         ):   3156 bytes
Type 27 (FINALIZER_HEAD      ):    360 bytes
Type 31 (IO_PORT             ):    252 bytes
Type 34 (APPDOMAIN_HEAD      ):     72 bytes
Type 36 (APPDOMAIN_ASSEMBLY  ):   1140 bytes
Could not allocate 89 blocks, 1068 bytes. Compacting memory.

    #### Exception System.OutOfMemoryException - CLR_E_OUT_OF_MEMORY (5) ####
    #### Message: 
    #### Microsoft.SPOT.IO.NativeFileStream::.ctor [IP: 0000] ####
    #### System.IO.FileStream::.ctor [IP: 00fd] ####
    #### System.IO.FileStream::.ctor [IP: 0010] ####
    #### NetduinoPlusWebServer.Request::SendFile [IP: 00aa] ####
    #### NetduinoPlusWebServer.Program::TrySendFile [IP: 00ba] ####
    #### NetduinoPlusWebServer.Program::RequestReceived [IP: 0020] ####
    #### NetduinoPlusWebServer.Listener::StartListening [IP: 0114] ####
A first chance exception of type 'System.OutOfMemoryException' occurred in Microsoft.SPOT.IO.dll
A first chance exception of type 'System.OutOfMemoryException' occurred in System.IO.dll
An unhandled exception of type 'System.OutOfMemoryException' occurred in System.IO.dll

You can see that this time it happened in another part of the code. I have this version checked in to my SVN server so I can get it back for testing in the future.

P.S. Corey, I could see what you were getting at with the extra debug statement, but when the exception happened I could see that the IndexOf('\n') was NOT some huge number, creating some huge string. Also, the input was always less than 600 characters... I'll revisit this IF I get any more Memory Exceptions with the Debug.GC(true).

-Valkyrie-MT

#8 Corey Kosak

Corey Kosak

    Advanced Member

  • Members
  • PipPipPip
  • 276 posts
  • LocationHoboken, NJ

Posted 24 December 2010 - 11:24 PM

P.S. Corey, I could see what you were getting at with the extra debug statement, but


That's trippy. I wonder if this GC bug Chris referred to is what was happening to me earlier as well.

#9 Chris Walker

Chris Walker

    Secret Labs Staff

  • Moderators
  • 7767 posts
  • LocationNew York, NY

Posted 25 December 2010 - 05:06 AM

Thanks, Valkyrie-MT. I'll see if I can create a good repro for Microsoft and see if we can take care of this in a an out-of-band patch after the holidays... Chris

#10 Fred

Fred

    Advanced Member

  • Members
  • PipPipPip
  • 302 posts
  • LocationUK

Posted 25 December 2010 - 09:12 AM

I was reading this very nervously expecting that you'd find a horrendous memory leak in my code. I intentionally kept it simple rather than optimized, but glad I didn't do anything too bad!

#11 Christopher Gilmore

Christopher Gilmore

    Member

  • Members
  • PipPip
  • 12 posts
  • LocationBurlington, MA

Posted 14 August 2011 - 01:40 PM

Hey guys, I had the same issue but the Debug.GC(true) did not work (it helped but didnt fix) for me. My application is a webserver that sends output to a sound board via netduino plus (firmware v4.1.0 update 6). that will turn on/off channels. Anyways, i run into problems when i compile my html string to send as a response. I then load that string into an array and send it. I put Debug.GC(true) all over the place, but after a few requests (about 19) it bombs. Granted for each request I log an event, so i understand that these events will take up more and more memory as they get added, but like others mentioned above, the system says i have plenty of memory left, before i get the error. Attached is the code for my application. It is based off of the multi-threaded webserver found here: http://forums.netdui...h__1#entry11770 but my HTML responses are pretty big (about 4-6KB) Here is where I run into problems: // Send HTML Response to web user. Debug.Print("About to load string into bytes. No significant memory drop should have occured."); Debug.GC(true); string htmlResponse = getHomepageHTML(activeChannel, turnOn, e.Command.ClientIP); Debug.Print("String loaded."); Debug.GC(true); e.ReturnString = Encoding.UTF8.GetBytes(htmlResponse); Debug.Print("Loaded Byte array."); Debug.GC(true); Can anyone help? What am i doing wrong?

Attached Files



#12 Chris Walker

Chris Walker

    Secret Labs Staff

  • Moderators
  • 7767 posts
  • LocationNew York, NY

Posted 14 August 2011 - 06:07 PM

Hi Christopher,

Can anyone help? What am i doing wrong?

There are two GC issues to be aware of.

In .NET MF 4.1, the garbage collector sometimes doesn't sweep memory completely. This has been fixed in .NET MF 4.2 RC1. If you haven't tried it yet, I'd recommend updating your board to the newest .NET MF 4.2 beta and see if this problem is fixed for you :)

Also, some objects are pinned in memory. This is necessary for a few things like native code interop, hardware interrupt code, etc. A few items are pinned early in the memory space (which is why you might be able to allocate small--but not large objects when memory starts getting tight...not enough consecutive memory).

All that said, I'm guessing that .NET MF 4.2 will clear the issue up for you right away.

Chris

#13 Earthed

Earthed

    Member

  • Members
  • PipPip
  • 20 posts
  • LocationAustralia

Posted 25 August 2011 - 01:01 AM

I'm experiencing a similar issue to the above, on 4.1.2821.0, but with string concatenation can someone elaborate on the significance of the '*' in the exception debug CLR_E_OUT_OF_MEMORY (*) - in the example above * = 5, I however am getting a 1 as below: GC: 3msec 37008 bytes used, 13968 bytes available Type 0F (STRING ): 2388 bytes Type 11 (CLASS ): 4164 bytes Type 12 (VALUETYPE ): 60 bytes Type 13 (SZARRAY ): 1788 bytes Type 15 (FREEBLOCK ): 13968 bytes Type 17 (ASSEMBLY ): 16164 bytes Type 18 (WEAKCLASS ): 48 bytes Type 19 (REFLECTION ): 24 bytes Type 1B (DELEGATE_HEAD ): 360 bytes Type 1D (OBJECT_TO_EVENT ): 288 bytes Type 1E (BINARY_BLOB_HEAD ): 4116 bytes Type 1F (THREAD ): 1920 bytes Type 20 (SUBTHREAD ): 240 bytes Type 21 (STACK_FRAME ): 3300 bytes Type 23 (LOCK_HEAD ): 60 bytes Type 24 (LOCK_OWNER_HEAD ): 24 bytes Type 25 (LOCK_REQUEST_HEAD ): 36 bytes Type 27 (FINALIZER_HEAD ): 216 bytes Type 31 (IO_PORT ): 288 bytes Type 34 (APPDOMAIN_HEAD ): 72 bytes Type 36 (APPDOMAIN_ASSEMBLY ): 1452 bytes Could not allocate 141 blocks, 1692 bytes. Compacting memory. #### Exception System.OutOfMemoryException - CLR_E_OUT_OF_MEMORY (1) #### #### Message: #### System.String::Concat [IP: 0000] #### #### namespace_Lib_SERIAL.SerialPortHardware::Read [IP: 005f] #### #### namespace_Lib_TELIT_GM862.Lib_TELIT_GM862_HTTP::ReceivePage [IP: 0045] #### #### namespace_Lib_TELIT_GM862.Lib_TELIT_GM862_HTTP::Request [IP: 0151] #### #### NetduinoPlusLibrary.Program::Program_Loop_TEST_TW_EVENT_TRACKER [IP: 00b9] #### #### NetduinoPlusLibrary.Program::Program_Loop [IP: 0031] #### #### NetduinoPlusLibrary.Program::Main [IP: 0020] #### A first chance exception of type 'System.OutOfMemoryException' occurred in mscorlib.dll 2009-01-01 01:24:41.823> [Lib_SERIAL.Read(5)][COM2]Exception: System.OutOfMemoryException GC: 3msec 38796 bytes used, 12180 bytes available Type 0F (STRING ): 804 bytes Type 11 (CLASS ): 4224 bytes Type 12 (VALUETYPE ): 60 bytes Type 13 (SZARRAY ): 1968 bytes Type 15 (FREEBLOCK ): 12180 bytes Type 17 (ASSEMBLY ): 16164 bytes Type 18 (WEAKCLASS ): 48 bytes Type 19 (REFLECTION ): 24 bytes Type 1B (DELEGATE_HEAD ): 360 bytes Type 1D (OBJECT_TO_EVENT ): 288 bytes Type 1E (BINARY_BLOB_HEAD ): 7656 bytes Type 1F (THREAD ): 1920 bytes Type 20 (SUBTHREAD ): 240 bytes Type 21 (STACK_FRAME ): 2892 bytes Type 23 (LOCK_HEAD ): 60 bytes Type 24 (LOCK_OWNER_HEAD ): 24 bytes Type 25 (LOCK_REQUEST_HEAD ): 36 bytes Type 27 (FINALIZER_HEAD ): 216 bytes Type 31 (IO_PORT ): 288 bytes Type 34 (APPDOMAIN_HEAD ): 72 bytes Type 36 (APPDOMAIN_ASSEMBLY ): 1452 bytes

#14 Chris Walker

Chris Walker

    Secret Labs Staff

  • Moderators
  • 7767 posts
  • LocationNew York, NY

Posted 25 August 2011 - 01:36 AM

Hi Earthed, There was a significant GC-related glitch in .NET MF 4.1. Can you try this on .NET MF 4.2 RC1 and let us know if it works for you? Chris

#15 Earthed

Earthed

    Member

  • Members
  • PipPip
  • 20 posts
  • LocationAustralia

Posted 31 August 2011 - 06:17 AM

Hi Chris, Just got 4.2 RC1 installed everywhere. I'm not at present getting the OUT_OF_MEMORY exception (But not at a point to thrash out things just yet, given the new exception that's crept in with 4.2 RC1: My Serial Library is attached. History: under 4.1.0.6 I never had this type of Exception inside serialPort_DataReceived() at all, and its nearly occurring every time something is received (even 3-5 chars) Under 4.1.0.6 I used to get an exception when inside Read() as not enough memory was allocated for Chars[] to copy from mBuffer[]. Code: attached Implementation: COM2 on NetduinoPlus Note: My Original Exception entry point seems to persist, however the exception it raises is different: 4.1.0.6 Exception: OUT OF MEMORY 4.2. RC1: A first chance exception of type 'System.ArgumentOutOfRangeException' occurred in mscorlib.dll Exception seems to occur on Line: sChars = new string(chars, 0, mBufferPtr);

Attached Files






0 user(s) are reading this topic

0 members, 0 guests, 0 anonymous users

home    hardware    projects    downloads    community    where to buy    contact Copyright © 2016 Wilderness Labs Inc.  |  Legal   |   CC BY-SA
This webpage is licensed under a Creative Commons Attribution-ShareAlike License.