假设我从线程转储中得到了这一行:
waiting to lock <0x0000000301cf21a8> (a foo.bar.MyClass)我怎么能找到这个东西?我以为调用System.identityHashCode并将其转换为十六进制就可以了,但它似乎不匹配。
发布于 2015-10-06 12:16:43
我使用了@guillaumegirod vitouch基纳建议-我创建了一个小代码,它使用不安全的方式打印内存地址,然后我可以将它与我在线程转储中看到的进行比较。谢谢!
发布于 2015-10-04 10:45:26
请注意,线程转储行中的数字是虚拟内存地址,而不是哈希代码。
您可以通过使用像月食垫这样的内存分析器来检查JVM。
我使用了一个Oracle演示死锁情况的示例,使用jstack创建了一个线程转储,使用Mat创建了一个堆转储。
"Thread-1" prio=10 tid=0x00007fb0a00bc000 nid=0x5cc4 waiting for monitor entry [0x00007fb098b25000]
java.lang.Thread.State: BLOCKED (on object monitor)
at net.noorg.playground.Deadlock$Friend.bowBack(Deadlock.java:19)
- waiting to lock <0x00000000ebd9f320> (a net.noorg.playground.Deadlock$Friend)
at net.noorg.playground.Deadlock$Friend.bow(Deadlock.java:16)
- locked <0x00000000ebd9f368> (a net.noorg.playground.Deadlock$Friend)
at net.noorg.playground.Deadlock$2.run(Deadlock.java:34)
at java.lang.Thread.run(Thread.java:745)双方都是
和
在Mat中创建堆转储:文件> Aquire堆转储> ,选择一个进程 > Finish
打开直方图:

在直方图视图中,可以使用正则表达式筛选类名。然后可以显示该类的传出对象引用:

在引用列表中,可以找到引用该类的对象:

在这个例子中,我们可以看到name引用(String对象)及其各自的值Alphonse和Gaston。因此,“阿方斯”和“加斯顿”是这一僵局的相关方。
注:
在服务器上,您可以使用jmap (作为根用户或运行进程的用户)创建堆转储:
$ jmap -dump:file=heapdump.hprof <PID>https://stackoverflow.com/questions/32930564
复制相似问题