-9

I have a server that handles requests via a socket and spawns a thread to handle each request.

Why do I get a java.lang.OutOfMemoryError and what can I do to fix it?

codeDr
  • 1,535
  • 17
  • 20
  • 3
    Maybe it is the infinite loop on lines 33-40 where you create a byte array of size 2**29 and add it to an ArrayList. – President James K. Polk Apr 20 '13 at 02:43
  • https://www.google.co.in/search?q=reasons+for+java+outofmemoryexception+&ie=utf-8&oe=utf-8&aq=t&rls=org.mozilla:en-US:official&client=firefox-a – Jayan Apr 20 '13 at 02:45
  • 1
    Please make sure that if you're answering your own question, the question is suitable to stand on its own. As-is, this question falls under `not a real question`. –  Apr 20 '13 at 02:49
  • No where in java can I find that the garbage collector **does not run** when in native or jni code. All references to java.lang.OutOfMemoryError direct users to count objects or other similar solutions. This is my attempt to document the solution to having a server process running out of memory -- namely the garbage collector is always blocked from running. – codeDr May 13 '13 at 14:41

2 Answers2

2

Type I: Out of heap space.

This is the most common error. It can be hard to track down because it involves understanding what objects are 'normal' and which objects should be released.

Creating unbounded amount of referenced objects. Creating objects that are thread specific but are referenced by one more global objects.

If you can reproduce the issue, running jmap -dump:format=b,file=output.bin

Then analyze the heap file with jhat.

Type II: Out of process memory

If you have implemented JNI calls, or have objects created on your behalf by the JVM, which creates JNI objects, you can run out of process memory, which for a 32-bit process is 4 gig.

The process space of your running java process consists of:

  • jvm memory
  • loaded libraries
  • native created objects

of which -Xmx only controls the sizing of the JVM memory.

Type III: The garbage collector does not run

I have not found any reference to this situation in any web search. I think I have read every posting for solving java.lang.OutOfMemoryErrors.

If you have a java program making JNI calls to native code, the garbage collector does not run while any thread is in a JNI call. Given a sufficient busy system, with two or more threads in a JNI call, it possible for the garbage collector to not run, ever.

The first instance was a long running JNI call which made a callback into java code to release the current object and fetch a new one. At each iteration, the amount of memory used grew and the unused objects did not get garbage collected.

The second instance was a test in which every spawned thread caused a JNI call. The code would run for a very long time, about an hour or so, but die with a java.lang.OutOfMemoryError. The -Xloggc option showed periodic garbage collection for the first 4000 seconds until the number of concurrent threads running increased.

4055.330: [GC 4055.330: [ParNew: 147424K->12220K(147456K), 0.0073372 secs] 769563K->637289K(1294336K) icms_dc=0 , 0.0073809 secs] [Times: user=0.00 sys=0.00, real=0.01 secs]  
18668.710: [GC 18668.710: [ParNew: 143289K->16384K(147456K), 0.0297121 secs] 768358K->651851K(1294336K) icms_dc=0 , 0.0297604 secs]

[Update 7 Jun 2014] In one instance I found this answer Memory leak when calling java code from C using JNI fixed the issue. The local java memory is assigned to the C stack even if it's allocated in java, because it's made from inside a JNI call. Specifically, I wrapped the back call to java with PushLocalFrame()/PopLocalFrame() to fix the issue.

Community
  • 1
  • 1
codeDr
  • 1,535
  • 17
  • 20
2

Force a heapdump when the out of memory happens. See Can I force generation of a JVM crash log file?. Then use the tools listed there to narrow down the memory leak: Tool for analyzing large Java heap dumps

Community
  • 1
  • 1
Jayan
  • 18,003
  • 15
  • 89
  • 143