Java multithreading - detect automatically locked thread
I have a j开发者_Go百科ava program, with multi threading. My problem is that from time to time, I have a timeout. Because I have some unix stuff I cannot see where is the timeout or/and lock. The problem is that this does not happens every night, only from time to time. Actually, an unix component (lsf) kill the thread (if timeout more that 15 minutes). So because I cannot see where is the problem, I was wondering if anyone has any idea. Is there any chance to launch another java something and when I have a lock, to write a log file ? If, yes, what would be ?
If you have to leave the app running and it gets deadlocked at the wrong time of day, you might get some benefit from JCarder, which is an agent you tell Java to use. When the program has finished running, it outputs various diagnostic files which can then be converted into a graph to show the deadlock(s).
Also, run your code through things like Findbugs, which may point out a subtle deadlock scenario that you otherwise haven't noticed.
jstack is a command line program you can use to introspect running java programs. It will print out a stack trace for every thread, tell you if it's locked and even detect deadlocks. That can help you debug the problem interactively.
If you want to get this data inside your program you can call Thread.getAllStackTraces() which will get you a list of all threads and their stack traces, so you can see where the threads are and their state, if you want to 'do something' if a thread is locked, like write to a log file.
In addition to jstack you could check out JConsole, which is a GUI application that allows you to detect deadlocks, monitor thread / memory / CPU usage, etc. It ships with the JDK.
Internally, JConsole makes use of the ThreadMXBean
, which you can also use to programmatically detect deadlocks; e.g. I typically arrange for a daemon thread in my server applications to periodically call the following code:
private void detectDeadlocks() {
logger.info("Checking for deadlocks.");
ThreadMXBean threadMXBean = ManagementFactory.getThreadMXBean();
long[] threadIds = threadMXBean.findDeadlockedThreads();
if (threadIds == null || threadIds.length == 0) {
logger.info("No deadlocks found.");
} else {
StringBuilder sb = new StringBuilder();
for (long threadId : threadIds) {
ThreadInfo threadInfo = threadMXBean.getThreadInfo(threadId);
if (sb.length() > 0) {
sb.append(", ");
}
sb.append(threadInfo.getThreadName()).append(" (ID: ").append(threadId).append(')');
}
logger.severe("Blocked Threads: " + sb);
// Raise alert here, etc.
}
}
精彩评论