System.Outofmemoryexception' Was Thrown When There Is Still Plenty of Memory Free

System.OutOfMemoryException' was thrown when there is still plenty of memory free

You may want to read this: "“Out Of Memory” Does Not Refer to Physical Memory" by Eric Lippert.

In short, and very simplified, "Out of memory" does not really mean that the amount of available memory is too small. The most common reason is that within the current address space, there is no contiguous portion of memory that is large enough to serve the wanted allocation. If you have 100 blocks, each 4 MB large, that is not going to help you when you need one 5 MB block.

Key Points:

  • the data storage that we call “process memory” is in my opinion best visualized as a massive file on disk.
  • RAM can be seen as merely a performance optimization
  • Total amount of virtual memory your program consumes is really not hugely relevant to its performance
  • "running out of RAM" seldom results in an “out of memory” error. Instead of an error, it results in bad performance because the full cost of the fact that storage is actually on disk suddenly becomes relevant.

System.OutOfMemoryException is thrown while still having free VM space

there were chunks up to 14Mb free. The operation which was failing was creating an object less than 1KB total

14 MB is definitely close to the danger-zone. The way the GC allocates VM has nothing to do with the object size. The GC heap is created from chunks of VM called "segments". The segment size is 2 MB when a program starts out but the GC dynamically grows the allocation of new segments when the program uses a lot of memory. Clearly you use a lot of memory. There isn't anything you can do to affect the VM allocation or avoid VM address space fragmentation.

Clearly you are way too close to the VM limit of a 32-bit process. You'll need to either drastically revise your code so you can make do with less. Or you need to put a 64-bit operating system on your list of prerequisites. Which can provide 4 gigabytes of VM address space to a 32-bit process. You'll need an extra build step to take advantage of it, described in this answer.

C# : Out of Memory exception

Two points:

  1. If you are running a 32 bit Windows, you won't have all the 4GB accessible, only 2GB.
  2. Don't forget that the underlying implementation of List is an array. If your memory is heavily fragmented, there may not be enough contiguous space to allocate your List, even though in total you have plenty of free memory.

System.OutOfMemoryException in Azure but not locally

What Azure Service offering are you using?

Most App Service based offerings, including Azure Functions in consumption plan maxxes out at 1.5GB memory per process/app regardless of the app service pricing plan you choose. Azure functions in consumption plan have a max memory limit of 1.5GB per function app instance (scaling can allow multiple instances) and other offerings also have limits to prevent you from gobbling up all the memory of the underlying machines. (Your local environment does not have these limits)

It is hard to solve without actual metrics. Run your code, then give it a few minutes after the crash and see metrics for the app, especially under Working Memory and private bytes. These are found in the metrics section in the App Service.

If these hit around the limits before your crash, this is likely the reason. If this is the case, your options in Azure are

  • Reduce your memory footprint
    • Optimize the current work so it uses less memory
    • Or split the work into multiple jobs which each uses less memory and use Azure Functions or similar
  • use an App Service Environment (lot of memory, isolated networking, but not cheap)
  • use a VM (Azure got memory optimized VMs for practically any size)

Why am I getting OutOfMemory exceptions when I have plenty of memory?

First of all, is your OS 32 or 64bit? If it's the former, you won't actually have access to all of the installed memory.

Additionally, (and I'm assuming you're using the .Net framework, correct me if I'm wrong) you'll need to set your platform target to x64 inside your build configuration. On top of this, you can add the following config to your app.config file:

<runtime>
<gcAllowVeryLargeObjects enabled="true" />
</runtime>

This will allow traversal of objects greater than 2GB.

OutOfMemoryException combined with another exception

I think that during creation of ArgumentException object there was OutOfMemoryException, hence AggregateException



Related Topics



Leave a reply



Submit