3

Do you know any way to and log all exceptions that are ever thrown (whether catched and handled or not) in java?

Here is my issue: There is an application, that I cannot change, and sometimes it has issues creating a lockfile (relevant code below). When it calls the tryLock() method , freezes for 30 seconds (despite the fact that tryLock is nonblocking), and returns with failure (CANT_CREATE_LOCK). As you see, all the catch tiers mask away the real problem, without even logging it.

final File lockFile = new File(fooHomeDir, ".foo-home.lock");
try
{
    FileOutputStream stream = new FileOutputStream(lockFile);
    try
    {
        if (stream.getChannel().tryLock() == null)
        {
            return LockResult.HELD_BY_OTHERS;
        }
        this.fileOutputStream = stream;
        this.lockFile = lockFile;
        return LockResult.OK;
    }
    catch (OverlappingFileLockException overlappingFileLockException)
    {
        return LockResult.HELD_BY_OTHERS;
    }
    catch (IOException ie)
    {
        return LockResult.CANT_CREATE_LOCK;
    }
}
catch (FileNotFoundException fnfe)
{
    return LockResult.CANT_CREATE_LOCK;
}

What I wish: Able to see what was the details of the exceptions.

Other info:

  • The environment is Linux, Java 1.7, Tomcat 7.
  • The fooHomeDir points to an NFS-backed mount point.
  • The fooHomeDir's permissions did not change.
  • The fooHomeDir's owner did not change.
  • The fooHomeDir's filesystem is not full.
  • There is no SELinux, or other thing that may interfere.

Basically, it worked before, and stopped "suddenly" and "without cause". So right now I'm investigating.

I'm commencing a remote debug of the application, but until then, suggestions are welcome :-)

Thanks, joe

UPDATE

For the record, the root cause of the issue was that the rpc.statd daemon died. Hence, the native locking mechanism failed over NFS. The symptom was an IOException with the message: "No locks available".

Kudos to Hans Maes

4

1 回答 1

2

您可以创建自己的异常实现,它将记录创建的每个错误。然后使用-Xbootclasspath:bootclasspath标志将其添加到类路径中。我不建议将其作为“最佳实践”,但至少您可以找到问题的根源。

一个非常简单的例子(有改进的余地)

package java.lang;

public class Exception extends Throwable {

public Exception() {
    super();
    String exception = "Exception";
    logWithStack(exception);

}

public Exception(String message) {
    super(message);
    logWithStack(message);
}

public Exception(String message, Throwable cause) {
    super(message, cause);
    logWithStack(message);
}

public Exception(Throwable cause) {
    super(cause);
    logWithStack(cause.getMessage());
}

protected Exception(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
    super(message, cause, enableSuppression, writableStackTrace);
    logWithStack(message);
}

private void logWithStack(String exception) {
    System.out.println(exception);
    for (StackTraceElement ste : Thread.currentThread().getStackTrace()) {
        System.out.println(ste);
    }
}

}

编译成类文件,然后将 -Xbootclasspath:/directoryWhereClassFileIsLocated/ 添加到 tomcat 选项中。

于 2013-10-30T13:19:21.213 回答