分析本地方法上的卡住线程
Analyzing stuck threads on a native method
我正在使用 tomcat 和 java 1.7.0_80。该产品是使用流口水的规则引擎。
加载系统后我的速度变慢了。我进行了线程转储,看到许多线程看起来像:
http-bio-9980-exec-48" daemon prio=10 tid=0x00007fa8b43a3000 nid=0x10299 runnable [0x00007fa9522c5000]
java.lang.Thread.State: RUNNABLE
at java.lang.Class.getDeclaredConstructors0(Native Method)
at java.lang.Class.privateGetDeclaredConstructors(Class.java:2595)
at java.lang.Class.getConstructor0(Class.java:2895)
at java.lang.Class.newInstance(Class.java:354)
at sun.reflect.MethodAccessorGenerator.run(MethodAccessorGenerator.java:399)
at sun.reflect.MethodAccessorGenerator.run(MethodAccessorGenerator.java:396)
at java.security.AccessController.doPrivileged(Native Method)
at sun.reflect.MethodAccessorGenerator.generate(MethodAccessorGenerator.java:395)
at sun.reflect.MethodAccessorGenerator.generateMethod(MethodAccessorGenerator.java:77)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:46)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
.
.
.
我认为这些线程被卡住了,所以我做了另一个线程转储(以查看本机方法上发生了什么):
00007faa1dabf6d5 __pthread_cond_wait + 0xc5
0x00007faa1cb638ad _ZN15JvmtiRawMonitor9raw_enterEP6Thread + 0x25d
0x00007faa1cb3f63d _ZN8JvmtiEnv15RawMonitorEnterEP15JvmtiRawMonitor + 0xad
0x00007faa1b7089a8 debugMonitorEnter + 0x38
0x00007faa1b6f5205 event_callback + 0xe5
0x00007faa1b6f5e3e cbClassPrepare + 0x8e
0x00007faa1cb548c4 _ZN11JvmtiExport18post_class_prepareEP10JavaThreadP12klassOopDesc + 0x1b4
0x00007faa1ca1de8e _ZN13instanceKlass15link_class_implE19instanceKlassHandlebP6Thread + 0x45e
0x00007faa1cae55c7 JVM_GetClassDeclaredConstructors + 0x1b7
0x00007faa180cac39 * java.lang.Class.getDeclaredConstructors0(boolean) bci:0 (Interpreted frame)
谁能告诉我为什么这里有争用?
好吧,让我试着回答你。我将做一个假设,最上面的条目是最里面的调用。
在reflect,调用了一些方法,具体是什么不好说,但是
这需要创建一个或多个方法和 运行 它们,并且
这需要创建 java.lang.Class 的新实例,并且
这需要获得 class 的构造函数,并且
进入 JVM,
命中一个事件,将其放入 debugMonitor,这
很可能在线程等待中
在调试器中等待用户输入。
所以也许您需要查看另一个线程?
或者这可能是正确的,您只需要忽略事件回调之后的级别。
无论如何,我会查看 reflect 看它是否指的是 your 代码。
这就是你需要找到的。
深入研究您认为工作正常的系统代码没有任何好处。
问题是我在调试模式(jpda 启动)下启动了 tomcat。即使我没有附加调试器,它也会导致问题。
当我在没有调试的情况下启动 tomcat 时,我没有注意到卡住的方法。
我正在使用 tomcat 和 java 1.7.0_80。该产品是使用流口水的规则引擎。 加载系统后我的速度变慢了。我进行了线程转储,看到许多线程看起来像:
http-bio-9980-exec-48" daemon prio=10 tid=0x00007fa8b43a3000 nid=0x10299 runnable [0x00007fa9522c5000]
java.lang.Thread.State: RUNNABLE
at java.lang.Class.getDeclaredConstructors0(Native Method)
at java.lang.Class.privateGetDeclaredConstructors(Class.java:2595)
at java.lang.Class.getConstructor0(Class.java:2895)
at java.lang.Class.newInstance(Class.java:354)
at sun.reflect.MethodAccessorGenerator.run(MethodAccessorGenerator.java:399)
at sun.reflect.MethodAccessorGenerator.run(MethodAccessorGenerator.java:396)
at java.security.AccessController.doPrivileged(Native Method)
at sun.reflect.MethodAccessorGenerator.generate(MethodAccessorGenerator.java:395)
at sun.reflect.MethodAccessorGenerator.generateMethod(MethodAccessorGenerator.java:77)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:46)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
.
.
.
我认为这些线程被卡住了,所以我做了另一个线程转储(以查看本机方法上发生了什么):
00007faa1dabf6d5 __pthread_cond_wait + 0xc5
0x00007faa1cb638ad _ZN15JvmtiRawMonitor9raw_enterEP6Thread + 0x25d
0x00007faa1cb3f63d _ZN8JvmtiEnv15RawMonitorEnterEP15JvmtiRawMonitor + 0xad
0x00007faa1b7089a8 debugMonitorEnter + 0x38
0x00007faa1b6f5205 event_callback + 0xe5
0x00007faa1b6f5e3e cbClassPrepare + 0x8e
0x00007faa1cb548c4 _ZN11JvmtiExport18post_class_prepareEP10JavaThreadP12klassOopDesc + 0x1b4
0x00007faa1ca1de8e _ZN13instanceKlass15link_class_implE19instanceKlassHandlebP6Thread + 0x45e
0x00007faa1cae55c7 JVM_GetClassDeclaredConstructors + 0x1b7
0x00007faa180cac39 * java.lang.Class.getDeclaredConstructors0(boolean) bci:0 (Interpreted frame)
谁能告诉我为什么这里有争用?
好吧,让我试着回答你。我将做一个假设,最上面的条目是最里面的调用。
在reflect,调用了一些方法,具体是什么不好说,但是 这需要创建一个或多个方法和 运行 它们,并且 这需要创建 java.lang.Class 的新实例,并且 这需要获得 class 的构造函数,并且 进入 JVM, 命中一个事件,将其放入 debugMonitor,这 很可能在线程等待中 在调试器中等待用户输入。
所以也许您需要查看另一个线程? 或者这可能是正确的,您只需要忽略事件回调之后的级别。 无论如何,我会查看 reflect 看它是否指的是 your 代码。 这就是你需要找到的。 深入研究您认为工作正常的系统代码没有任何好处。
问题是我在调试模式(jpda 启动)下启动了 tomcat。即使我没有附加调试器,它也会导致问题。 当我在没有调试的情况下启动 tomcat 时,我没有注意到卡住的方法。