Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is there a way to schedule a Full Garbage Collection in Java? [duplicate]

I have an application that's running on a 24x6 schedule. Currently, after running for a few days, a Full GC is performed automatically - and usually during a busy part of the day, which negatively impacts user response times.

What I'd like to do is force a Full GC - perhaps at midnight each night, during very low usage times - to prevent it from happening during the day. I've tried System.gc(), but it doesn't seem to guarantee when a Full GC will happen, or even if it will. Is there some means of doing this?

Version info:

Java(TM) SE Runtime Environment (build 1.6.0_11-b03)
Java HotSpot(TM) Server VM (build 11.0-b16, mixed mode)

Additionally -

  • Minor GCs are running, about every 10-15 seconds. But these are are not freeing up enough RAM to get the app through a full week. When a Full GC does happen, nearly 50% of the heap is freed.
  • In relation to the above, calling System.gc() doesn't seem to mean that any of the next GCs, will be of the Full form needed to free those large chucks of memory. Yes, it is enabled (or not disabled, depending on how you read the -XX option).
  • I've already played around with several of the CMS GC settings, which has helped greatly, but not solved the problem. Originally it was throwing OOMs, two to three times a week.
  • I want to stop the endless loops of:
    • constantly adding to heap space - which can only go on for so long
    • constant tuning and testing of GC settings - it is long past the point of diminishing return
  • I don't want to treat this like an NT machine and bounce it nightly. There are active user sessions throughout the night, and bouncing the app would mean loosing session data.

To be more specific, I'm looking more for a technique to use to ensure that a Full GC is going to happen, rather than a simple method/function to call to run it.

At the moment I'm looking at the modification of the percentage threshold used by CMS to determine when a Full GC is required.

Thanks for any help.

like image 643
Jim Black Avatar asked Jan 02 '14 22:01

Jim Black


2 Answers

jmap -histo:live <PID> will force Full GC as "side effect" of finding all live objects. You can schedule it to recycle your JVM processes on off-working hours.

Your JVM build 1.6.0_11-b03 is pretty ancient, but jmap should be supported on all 1.6 HotSpot JVMs.

like image 64
Alexey Ragozin Avatar answered Oct 11 '22 14:10

Alexey Ragozin


No.

System.gc() suggests to the GC that you would like a collection.

Further, there is probably very little garbage generated during the quiet period and that is why calling System.gc() doesn't do much.

During peak time there is, presumably, more activity and therefore more garbage being generated - hence the need for a collection.

It should be obvious that you cannot defer collection in that simplistic manner. The JVM will collect when it needs to.

You need to look into tuning your GC - if you have stop the world collection happening then you have some issue. This shouldn't really happen on a modern server JVM.

You should look into tuning the CMS collector - this is a pretty good article on the basics of the GC system in Java. In Java 7 there is the new G1GC which may or may not be better.

You should find a way to simulate load conditions and try different GC parameters, the CMS GC has many tuning parameters and configuring it is somewhat of a dark art...

This is a somewhat more involved article on GC tuning and benchmarking.

like image 29
Boris the Spider Avatar answered Oct 11 '22 13:10

Boris the Spider