I recently helped investigate an apparent "hang" in using ScheduledThreadPoolExecutor that turned out to be caused by the main thread encountering an OutOfMemoryError and terminating without producing any sign that an exception had occurred.
The problem is that ThreadGroup.uncaughtException relies on being able to allocate memory to produce any output:
} else if (!(e instanceof ThreadDeath)) {
System.err.print("Exception in thread \""
+ t.getName() + "\" ");
e.printStackTrace(System.err);
}
When memory is exhausted the string concatenation above will trigger a secondary OutOfMemoryError and so the thread will terminate silently.
There are a number of simple things that can be done to alleviate this problem:
- don't use String concatenation in the above
- check for OOME explicitly and report it directly rather than relying on printStackTrace
More sophisticated checking would place the printStackTrace in a try/catch and report if printing the stacktrace failed due to an exception.