how many Java Garbage Collector objects? - java

Can anyone please tell me if we call garbage collector in parallel executing two threads, how many gc objects are created?

There's always only one garbage collector, that runs in it own Thread

There's one garbage collector as others pointed out.
You should not care about the count of the garbage collector objects
or about any details about the garbage collector. This is something
on JVM/system level. All you care about is when to call the garbage
collection explicitly (if you want to do that).

(This is responding to the OP's comments which reveal the nature of the misunderstanding that is at the root of his Question. See the quoted text ...)
yes Runtime is a singleton but when we are calling Runtime.gc(), ...
Correct
... the jvm internally it will created one thread that is garbage colletor(daemon thread).
Incorrect. It does not create a new GC thread. Rather it causes the existing GC thread to wake up and do a garbage collection. Furthermore:
the thread that calls gc() will not return until the garbage collector has completed.
depending on the garbage collector that has been configured, the garbage collector may freeze all other application threads before starting the collection.
... but in this case when we call gc in two different threads at a time, how many GC objects will be created?
None. If two methods call gc() at the same time, the GC will run once on the existing GC thread. Think of the GC as an "engine" that is either running or sleeping at any point in time. Calling gc() will typically cause the GC to start running if it is currently sleeping.
(Actually, I'm simplifying things a bit. CMS and G1 have the complication that the gc() will typically run in parallel with application threads. Another possibility is that the gc() call will be simply ignored. Finally, the GC typical has a variety of modes; e.g. a young generation collection, and a full collection. Calling gc() will start a full collection.)
... but we are saying that GC is daemon thread
Yes (sort of),
The GC may have multiple threads. There is typically a main GC thread, and another thread for handling finalization. And for some kinds of GC, some tasks are performed in parallel using a pool of threads.
and also gc() has native implementation
For mainstream JVMs, yes. (But as a counter-example, in JNode is implemented in Java, albeit using Unsafe methods, etc.)
then what is GC?
It is the "stuff" that does garbage collection. What actually goes on under the hood is JVM specific, and depends on JVM options, etcetera.

Related

Do Finalizer thread can cause Out of Memory?

Finalizer thread are responsible clearing objects in the finalization queue. Ironically does the same finalizer thread can responsible for OOM?
Short answer: theoretically yes.
More specifically it depeneds on how your finalizer thread is constructed and what he does. In general any new object creation can lead to OOM if no free memory left.
The short answer is yes.
Some classes implement the Object.finalize() method. Objects which override this method need to called by a background thread call
finalizer, and they can't be cleaned up until this happens. If these tasks are short and you don't discard many of these
it all works well. However if you are creating lots of these objects and/or their finalisers take a long time,
the queue of objects to be finalised builds up. It is possible for this queue to use up all the memory.
If many objects with finalizers are created, it is likely that there will be performance issues,
even if the underlying native resources are explicitly freed using try-finalize blocks.
Code to try and outpace java garbage collector with finalizers showed the following result.
It is surprisingly easy to outpace the Java garbage collector if lots of objects with finalizers are created,
leading to spurious out-of-memory errors with lots of objects which could theoretically be reclaimed.More on this can be found on
the link http://www.enyo.de/fw/notes/java-gc-finalizers.html
There are some apps that have hit this finalizer queue build up problem in the past, so it is worth considering
how to deal with it. One obvious way is to increase the priority of the "Finalizer" daemon thread - there is no API for this,
so you have to run through all the threads to find it by name, then increase it's priority.
You could also take explicit control over finalization by removing the finalize() method and using your own explicit queue
using your own Reference objects in a very similar way that the Finalizer class processes the objects and their finalize()
methods . That way you control your finalization processing thread's priority and schedule.
Note that neither of these techniques reduce the overheads in having finalizable objects,
they just avoid the queue building up because of the lower priority thread.
How finalization works is shown in the link below for the curious
http://www.fasterj.com/articles/finalizer2.shtml

Garbage collector don't run when object is referenced.Which object?

As there are so many objects being created for a particular class some of which could be referenced and some can be anonymously lying in the heap and hence elgible for garbage collection . So is the presence of even one non referenced object in the heap is enough for garbage collector to run or is there any other criteria to assure the garbage collector is executed.
Thanks
Jayendra
we don't know when GC get executed, it depend on lots of things e.g. Type of GC. Also you can recommend to VM to launch GC by doing System.gc(). But again it is just a recommendation
GC on an object is, for typical reference implementations of the JVM, completely non-deterministic. There is no way to guarantee when, or even if, the GC will be run, never mind if it will result in a particular object reference being released (and its corresponding finalizer called.) This is regardless of the state of this particular object.
As pointed out in comments, System.gc() is merely a hint or request. In a great many cases it will result in a full GC. But consider gathering a heap dump usually results in 2-3 calls to System.gc() before the dump is generated, mostly as a way to improve the chances it actually happens.
There are experimental VMs that offer various implementations of real-time guarantees where some of this is not true.

When does garbage collection work in java?

I knew that there are a lot of articles about java garbage collection but after searching I don't know exactly "when dose the garbage collection run in a java application?(when the application restart or while it still running)".
Garbage Collector is a dameon thread. A dameon thread runs behind the application. It is started by JVM. The
thread stops when all non-dameon threads stop.
The JVM controls the Garbage Collector; it decides when to run the Garbage Collector. JVM runs
the Garbage Collector when it realizes that the memory is running low. The behavior of GC can
be tuned by passing parameters to JVM.
One can request the Garbage Collection to happen from
within the java program but there is no guarantee that this request will be taken care of by
jvm.Check How to force garbage collection in Java?
Learn More ..
Garbage collection runs regularly alongside the program. It is part of the JVM.
When exactly does it run though? Well, that's unpredictable, version-dependent, and should be treated as if it could run at any time.
When a variable goes out of scope, the application tells the JVM it's done with that piece of memory. Then, when the garbage collector runs it will free those resources for the OS to use.
For example
String capitalizeAll(String s) {
char[] chars = s.toCharArray();
for(int i = 0; i < chars.length; i++)
chars[i] -= 32;
return new String(chars);
}
As soon as the method returns, the char[] chars allocated within the method will go out of scope. The program tells the JVM it's done with those resources and next time GC runs they will be freed.
Interesting stuff though, the JVM takes into account how much the app has told it is ready to be collected. That means that if your app does a lot of unnecessary copying or boxing, JVM will run often and cause your app to take a performance hit.
This is mostly implementation-specific.
The most primitive type of garbage collector, the serial GC will be triggered when it fails to find sufficient free space during an allocation (with generational GCs this usually means the young generation is full). It then suspends the entire JVM by triggering a safepoint on mutator threads and does its work on a single thread, this is called a "stop the world pause"
In this case you can say that GCs can be caused by any allocation.
On top of that some GCs may also do background work concurrently to mutators, such as Hotspot's CMS. But it still needs stop the world pauses for some work, they just tend to be shorter than in the serial GC.
For CMS it's still triggered by allocations but also does some of its work on background thread(s).
Azul Zing's concurrent compacting collector also does - as its name says - concurrent collecting on dedicated threads more or less all the time. It still needs cooperation from the mutator threads but does so without STW pauses.
So this case one could say that the GC is running all the time in the background and does a little work in the foreground.
There are other collectors out there, so this isn't a comprehensive overview. But in general it's an implementation detail, subject to change and not something one should rely on. Some GCs even ignore System.gc() by default because it would mess up their heuristics.
This is from Kathy Sierra and Bert Bates' book SCJP Study Guide:
"The garbage collector is under the control of the JVM. The JVM decides when to
run the garbage collector. From within your Java program, you can ask the JVM to
run the garbage collector, but there are no guarantees, under any circumstances, that the JVM will comply. Left to its own devices, the JVM will typically run the garbage collector when it senses that memory is running low. Experience indicates that when your Java program makes a request for garbage collection, the JVM will usually grant your request in short order, but there are no guarantees. Just when you think you can count on it, the JVM will decide to ignore your request."

Java not releasing objects with finalize() override

My application makes use of a third-party library (the JTDS driver) that has some objects that override the finalize() method. I think they obey all the rules about when not to use finalize() - it doesn't depend on them running in a timely manner or at all.
The problem is that they objects are never being released. They seem to get stuck in the Finalizer queue and never removed. They build up slowly over a couple of weeks and run the JVM out of heap space. Thread dumps show the Finalizer thread just waiting for something to call finalize() on. If I call System.runFinalization(), the objects are finalized and are properly removed from the finalizer queue (and don't show up in heap dumps anymore).
Why will System.runFinalization() remove objects properly, but the Finalizer thread won't do it on its own?
Had the same issue today. You are not specifying what JVM you are using but just in case it is OpenJDK - there is a bug https://lists.launchpad.net/openjdk/msg10021.html
They say it is already fixed so you just need to upgrade.
This means your finalize() methods are taking too long resulting in objects building up in the queue waiting to be called.
Objects are removed from the queue as they are being called and wont be in the queue after being called.
Why won't the Finalizer thread remove these objects?
The simple answer is, something in side the finalizer has caused a deadlock. Finalizers are the worst way to do clean-up. It is called by the garbage collector.
Called by the garbage collector on an object when garbage collection
determines that there are no more references to the object.
What happens when the object to be garbage collector has a strong reference? The object never gets garbage collector. I strongly doubt this is what is happening in your case.
Joshua Bloch says in Effective Java:
In summary don't use finalizers except as a safety net or to terminate
noncritical native resources
Avoid finalizers - Finalizers are unpredictable, often dangerous, and generally unnecessary
http://www.informit.com/articles/article.aspx?p=1216151&seqNum=7

Is it possible to change the priority of garbage Collector thread?

Java garbage collector runs with priority 1, due to which it is not guaranteed that System.gc() will actually execute if called.
Is there any way to change its priority? This shall enable me to run if I want.
Garbage Collector is an independent thread (as reminded by Tom Hawtin in a comment, not even necessarily a single thread) and is on a priority which is decided by the Java Virtual Machine. This means you can't force garbage collection. Calling System.gc() tells the runtime environment that "now" might be a good time to run the GC but garbage collection is actually not guaranteed to be done immediately.
Even if you upped the thread priority to 11 System.gc will not guarantee anything. All you can be sure of is that if Java needs to GC it will before it throws an out of memory exception.
The GC will run as required. You shouldn't need to call it manually. If you don't like when it is run you can control it with command line arguments.
If you believe you have a problem with the behaviour of the GC you should try to fix the cause rather than trying to write your own work around.
In summary, you should tell us what is the real cause of your concern so we can address that.
When a thread is created it inherits the priority of the thread that created it. The priority of a thread can be adjusted by using
public final void setPriority(int newPriority)
The problem is a thread doesn't "run" the garbage collector.
The garbage collector is run by the VM (when Java wants or is in "good mood .. :)" ).
EDIT:
The GC is not a thread but a method of the Runtime thread. You can change the priority of the Runtime thread but this will have no effect on the GC. The thread that calls the GC is a thread of the VM and is out side the scope of the API so you can't change its priority.
So, I don't really think you can set its priority.

Categories