Tom Marthenal
Tom Marthenal

Reputation: 3146

Grails application taking more memory than possible?

I'm currently running a Grails application in Jetty. It's working fine, but taking more memory than I'd like.

htop shows that Jetty is being run like so: java -server -Xmx256m -Xms256m -Xmn96m -XX:MaxPermSize=64m -Djetty.home=/home/...

It seems to me, then, that the maximum memory that Jetty could possibly use should be about 256 + 64 = 320 MB. Instead, it looks like this:

  PID USER      PRI  NI  VIRT   RES   SHR S CPU% MEM%   TIME+  Command
 6256 jetty      20   0 2747M  623M 13732 S  0.0 31.3  1:28.06 /usr/lib/jvm/java-7-openjdk-amd64/jre/bin/java -server -Xmx256m -Xms256m -Xmn96m -XX:MaxPermSize=64m -Djetty.home=...

Obviously I wouldn't expect the memory usage to be exactly 320 MB, but shouldn't it be close? Why would it be double the expected memory? If anything, shouldn't Java refuse to allocate more space when the heap fills up?

I tried to see exaftly what's going on with jmap, but everything looks right to me:

# jmap -heap 6256
Attaching to process ID 6256, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 23.7-b01

using thread-local object allocation.
Parallel GC with 4 thread(s)

Heap Configuration:
   MinHeapFreeRatio = 40
   MaxHeapFreeRatio = 70
   MaxHeapSize      = 268435456 (256.0MB)
   NewSize          = 100663296 (96.0MB)
   MaxNewSize       = 100663296 (96.0MB)
   OldSize          = 5439488 (5.1875MB)
   NewRatio         = 2
   SurvivorRatio    = 8
   PermSize         = 21757952 (20.75MB)
   MaxPermSize      = 67108864 (64.0MB)
   G1HeapRegionSize = 0 (0.0MB)

Heap Usage:
PS Young Generation
Eden Space:
   capacity = 65208320 (62.1875MB)
   used     = 33343488 (31.798828125MB)
   free     = 31864832 (30.388671875MB)
   51.13379396984924% used
From Space:
   capacity = 17170432 (16.375MB)
   used     = 0 (0.0MB)
   free     = 17170432 (16.375MB)
   0.0% used
To Space:
   capacity = 18284544 (17.4375MB)
   used     = 0 (0.0MB)
   free     = 18284544 (17.4375MB)
   0.0% used
PS Old Generation
   capacity = 167772160 (160.0MB)
   used     = 132604224 (126.46124267578125MB)
   free     = 35167936 (33.53875732421875MB)
   79.03827667236328% used
PS Perm Generation
   capacity = 67108864 (64.0MB)
   used     = 55899320 (53.30974578857422MB)
   free     = 11209544 (10.690254211425781MB)
   83.29647779464722% used

26872 interned Strings occupying 2932096 bytes.

As far as I can tell, neither the perm gen space nor the heap space are full. So what's all that ~400 MB of memory being used for? Is there something I can change in my Grails application or in Jetty to reduce it?

I've run Grails apps on Jetty in the past with low memory usage. Just checked one right now and it's sitting at 220 MB of memory used, so I'm not really sure what I'm doing wrong.

Upvotes: 1

Views: 710

Answers (1)

Dror Bereznitsky
Dror Bereznitsky

Reputation: 20376

The JVM is a native program which consumes native resources, including native memory. Native memory is the memory available to the runtime process, as distinguished from the Java heap memory that a Java application uses. Every virtualized resource — including the Java heap and Java threads — must be stored in native memory, along with the data used by the virtual machine as it runs.
You can also take a look at this answer which explains this subject very nicely.
This thread show some nice examples of how to leak native memory with Java.
The Jetty documentation also refers to this subject.
If you are using JDK7 you can use the VisualVM buffer monitor plugin for monitoring direct buffers that are allocated outside of the garbage-collected heap.

Upvotes: 2

Related Questions