views:

213

answers:

7

Hi Guys

I would like to run a Java program with garbage collection switched off. Managing memory in my own code is not so difficult. However the program needs quite a lot of I/O. Is there any way (short of using JNI for all I/O operations) that I could achieve this using pure Java?

Thanks Daniel

A: 

GarbageCollection is automated memory management in java.So you can not disable GC

giri
I thought there was some strategy of flags that could be set to ensure that nothing was garbage collected - maybe I'm wrong.
Dan
@Dan - You *are* wrong.
Stephen C
+7  A: 

Managing memory in my own code is not so difficult.

It's not difficult - It's impossible. For example:

public void foo() {
  Object o = new Object();

  // free(o); // Doh! No "free" keyword in Java.
}

Without the aid of the garbage collector how can the memory consumed by o be reclaimed?

I'm assuming from your question that you might want to avoid the sporadic pauses caused by garbage collection due to the high level of I/O being performed by your app. If this is the case there are techniques for minimising the number of objects created (e.g. re-using objects from a pool). You could also consider enabling the Concurrent Mark Sweep Collector.

The concurrent mark sweep collector, also known as the concurrent collector or CMS, is targeted at applications that are sensitive to garbage collection pauses.

Adamski
No I would always use a cache to reuse objects.
Dan
What about temporary objects that you don't see or control? There's a lot going on inside the various libraries that aren't going to know squat about your memory scheme.
Joe
That may be the case but the library code you'll be using for I/O will be probably be creating objects somewhere. Also, have you actually established this is a problem? Avoiding object creation for the sake of speed is a "code smell" IMO. Most of the time your app will be I/O bound anyway, not CPU bound.
Adamski
Agreed but my main issue is that I don't want any GC at all - its all about predictability not straight line speed.
Dan
In which case you should look into using the concurrent mark sweep collector.
Adamski
But even that will stop the program running for a brief period of time.
Dan
Have you actually established that this would be a problem for your app? It sounds like you're trying to optimise something which may not even be an issue. Realtime Java introduces the notion of immortal memory and scoped memory which bypass the GC but I really think this is overkill from what you've mentioned.
Adamski
@Dan, you just need to be using a different language. Sounds like C or C++ are the obvious choices here, although you could probably hack enough of a solution in .NET with unmanaged code. With modern JVMs you can minimize the "program stops responding" situation, but you cannot eliminate it - and you cannot not use the GC.
Yishai
+1  A: 

The only way you are going to be able to turn off garbage collection is to modify the JVM. This is should be feasible with OpenJDK 6 codebase.

However, the what you will get at the end is a JVM that leaks memory like crazy, with no reasonable hope of fixing the leaks. The Java class library APIs are designed and implemented on the assumption that there is a GC taking care of memory management. This is so fundamental that any serious attempt to "fix" it would lead to a language / library that is not recognizable as Java.

If you want a non-garbage collected language, use C or C++.

Stephen C
+1  A: 

Modern JVM's are so good at handling short-lived objects that any scheme you devise on your own will be slower.

This is because the objects you handle yourself will become long-lived and receive extra deluxe treatment from the JVM in terms of being moved around etc. Of course, this is by the garbage collector, which you want to turn off, but you can do very little without any gc.

So, before you start considering what optimization to use, then establish a baseline where you have a large unoptimized, program and profile it. Then do your tweaks, and see if it helps, but you will never know if you do not have a baseline.

Thorbjørn Ravn Andersen
+4  A: 

It's very hard (but not impossible) to disable GC in a JVM.

Look at the JNI "critical" functions for hints.

You can also essentially ensure you don't GC by not allocating any more objects (write a JVMTI agent that slaps you if you do, and instrument your code).

Finally, you can force a fatal OutOfMemoryError by ensuring that every object you allocate is never freed, thus when you hit -Xmx memory used, you'll fall over as GC won't be able to reclaim anything (mind you, you'll GC one or more times at this point before you fall over in a heap).

The real question is why you'd want to? What upside do you see in doing it? Is it for realtime? If so, I'd consider looking at one of the several realtime JVMs available on the market (Oracle, IBM, & others all sell them). I can't honestly think of another reason to do this while still using Java.

Trent Gray-Donald
+1  A: 

Since you say, "its all about predictability not straight line speed," you should look at using a realtime Java system with deterministic garbage collection.

Matthew Flaschen
+1  A: 

What you are trying to achieve is frequently done in investment banking to develop low-latency real-time systems.

To avoid GC you simply need to make sure not to allocate memory after the startup and warm-up phase of your application. As you seem to have noticed Java NIO internally does unwanted memory allocation. Unfortunately, you have no choice but write JNI replacements for the problematic calls. You need at least to write a replacement for the NIO Selector.

You will have to avoid using most of the Java libraries due to similar unwanted memory allocations. For example you will have to avoid using immutable object like String, avoid Boxing, re-implement Collections that preallocate enough entries for the whole lifetime of your program.

Writing Java code this way is not easy, but certainly possible. I am developing a platform to do just so.

macgarden