我得到了我的一个进程的线程转储。它有一堆这样的线程。我猜他们保留了一堆记忆,所以我得到了OOM。
"Thread-8264" prio=6 tid=0x4c94ac00 nid=0xf3c runnable [0x4fe7f000]
java.lang.Thread.State: RUNNABLE
at java.util.zip.Inflater.inflateBytes(Native Method)
at java.util.zip.Inflater.inflate(Inflater.java:223)
- locked <0x0c9bc640> (a java.util.zip.Inflater)
at org.apache.commons.compress.archivers.zip.ZipArchiveInputStream.read(ZipArchiveInputStream.java:235)
at com.my.ZipExtractorCommonsCompress.extract(ZipExtractorCommonsCompress.java:48)
at com.my.CustomThreadedExtractorWrapper$ExtractionThread.run(CustomThreadedExtractorWrapper.java:151)
Locked ownable synchronizers:
- None
"Thread-8241" prio=6 tid=0x4c94a400 nid=0xb8c runnable [0x4faef000]
java.lang.Thread.State: RUNNABLE
at java.util.zip.Inflater.inflateBytes(Native Method)
at java.util.zip.Inflater.inflate(Inflater.java:223)
- locked <0x0c36b808> (a java.util.zip.Inflater)
at org.apache.commons.compress.archivers.zip.ZipArchiveInputStream.read(ZipArchiveInputStream.java:235)
at com.my.ZipExtractorCommonsCompress.extract(ZipExtractorCommonsCompress.java:48)
at com.my.CustomThreadedExtractorWrapper$ExtractionThread.run(CustomThreadedExtractorWrapper.java:151)
Locked ownable synchronizers:
- None
我试图找出它是如何达到这种情况的。CustomThreadedExtractorWrapper 是一个包装类,它触发一个线程来完成一些工作(ExtractionThread,它使用 ZipExtractorCommonsCompress 从压缩流中提取 zip 内容)。如果任务耗时过长,ExtractionThread.interrupt()
则调用取消操作。
我可以在我的日志中看到取消发生了 25 次。我在我的转储中看到了其中的 21 个线程。我的问题:
- 这些线程的状态是什么?活着还跑?以某种方式被阻止?
- 他们显然没有死于 .interrupt() 吗?有没有确定的方法可以真正杀死一个线程?
- 堆栈跟踪中“锁定”的真正含义是什么?
Inflater.java 中的第 223 行是:
public synchronized int inflate(byte[] b, int off, int len) {
...
//return is line 223
return inflateBytes(b, off, len);
}