Windows 上的 Java 堆栈跟踪
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/659650/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Java stack trace on Windows
提问by richs
I need to get a stack trace for a JVM process running on a client machine that uses windows.
我需要获取在使用 Windows 的客户端计算机上运行的 JVM 进程的堆栈跟踪。
The client has the JRE installed but not the JDK.
客户端安装了 JRE,但没有安装 JDK。
I want to use JStack but it is not installed and we can't install a JDK on the client's machine. I also tried using AdaptJ stack trace product from a Java Webstart Session but that didn't work because we remote in and get an error about not being the session that started the application at a specified PID.
我想使用 JStack 但它没有安装,我们无法在客户端的机器上安装 JDK。我还尝试使用来自 Java Webstart 会话的 AdaptJ 堆栈跟踪产品,但这没有用,因为我们远程进入并收到错误,提示不是在指定的 PID 上启动应用程序的会话。
Essentially I want a way to install JStack without installing the JDK.
本质上,我想要一种无需安装 JDK 即可安装 JStack 的方法。
采纳答案by Eddie
You probably want to use SendSignal, which was designed for exactly this purpose.
您可能想要使用专为此目的而设计的SendSignal。
回答by Joshua McKinnon
The JDK and associated tools work fine whether "installed" or not, if you just zip up and extract it to a temporary directory, you should be able to run jstack. (No PATH or JAVA_HOME modifications necessary). Just make sure you use the same version that corresponds to the JRE your client has the application running with. At least in the case of JConsole, it seems to fuss if the versions are different. I'm not sure if jstack behaves the same way.
JDK 和相关工具无论是否“安装”都可以正常工作,如果您只是将其压缩并解压缩到一个临时目录,您应该能够运行 jstack。(不需要 PATH 或 JAVA_HOME 修改)。只需确保您使用与客户端运行应用程序的 JRE 对应的相同版本。至少在 JConsole 的情况下,如果版本不同似乎会大惊小怪。我不确定 jstack 的行为是否相同。
I'm not saying this is the ideal solution, just that it would work. I think jdigital and Eddie's suggestions are better first bets, and even though this shouldn't interfere with an existing java installation the same way running the installer would, the customer may disagree regardless.
我并不是说这是理想的解决方案,只是它会起作用。我认为 jdigital 和 Eddie 的建议是更好的第一选择,即使这不应该像运行安装程序一样干扰现有的 java 安装,但无论如何客户可能不同意。
回答by Senthil Kumar Sekar
jstack and jps are part of tools.jar of the JDK. Also attach.dll is required to attach jstack to a process.
jstack 和 jps 是 JDK 的 tools.jar 的一部分。还需要 attach.dll 将 jstack 附加到进程。
Ofcourse the tools.jar and attach.dll are not part of JRE.
当然,tools.jar 和 attach.dll 不是 JRE 的一部分。
To make jstack work on a systems which has no JDK (mostly Windows), I usually do the following.
为了使 jstack 在没有 JDK(主要是 Windows)的系统上工作,我通常会执行以下操作。
- Copy tools.jar and attach.dll from JDK and put in to some location on the target system. Example: to c:\temp\jstack
- Write a bat script to manually invoke it using JRE.
- 从 JDK 复制 tools.jar 和 attach.dll 并放入目标系统上的某个位置。示例:到 c:\temp\jstack
- 编写一个 bat 脚本以使用 JRE 手动调用它。
For example, create a bat file jstack.bat:
比如创建一个bat文件jstack.bat:
set JRE=c:\jrefolder
"%JRE%\bin\java" -classpath "c:\temp\jstack\tools.jar" -Djava.library.path="c:\temp\jstack" sun.tools.jstack.JStack %*
Similarly for jps, create a jps.bat with following content.
同样对于 jps,创建一个具有以下内容的 jps.bat。
set JRE=c:\jrefolder
设置 JRE=c:\jrefolder
"%JRE%\bin\java" -classpath "c:\temp\jstack\tools.jar" -Djava.library.path="c:\temp\jstack" sun.tools.jps.Jps %*
Usage:
用法:
jstack.bat -l <pid>
Hope this helps.
希望这可以帮助。
回答by jim birch
To get a thread dump with only a JRE you need tools.jar and attach.dll from the JDK of the same Java version. Install this somewhere and copy these into the jre. Must be identical version!
要获得仅包含 JRE 的线程转储,您需要来自相同 Java 版本的 JDK 的 tools.jar 和 attach.dll。在某处安装它并将它们复制到 jre 中。必须是同版本!
If you need a dump of a process running under the system account you can use the Windows sysinternals psexec.exe to gain access to the process. Copy this into the JRE bin or somewhere in the path.
如果您需要在系统帐户下运行的进程的转储,您可以使用 Windows sysinternals psexec.exe 来访问该进程。将其复制到 JRE bin 或路径中的某个位置。
This batch file writes the stack dump to a file with a datetime filename so multiple traces can be taken and compared easily.
此批处理文件将堆栈转储写入具有日期时间文件名的文件,以便可以轻松获取和比较多个跟踪。
Threads.bat
线程.bat
:: Creates a thread dump for the tomcat6.exe process
:: saved in a timestamped filename and views it!
:: Jim Birch 20111128 rev 2015-10-12
::Required the following files to be placed in the jre/bin folder:
:: attach.dll - From the Java JDK (must be the same version)
:: tools.jar - ditto
:: psexec.exe - from Windows sysinternals
::cd to jre/bin
d:
cd \application\jre\bin
::build datetime filename
rem datetime from wmi.exe
for /f "tokens=2 delims==" %%I in ('wmic os get localdatetime /format:list') do set dt0=%%I
rem datetime string as YYYY-MM-DD-hhmmss
set dt=%dt0:~0,4%-%dt0:~4,2%-%dt0:~6,2%-%dt0:~8,6%
set ff=td-%dt%.txt
echo filename: %ff%
::PID of the process by named exe, eg, tomcat6
for /F "tokens=2" %%I in ('TASKLIST /NH /FI "IMAGENAME eq tomcat6.exe"' ) DO SET PID=%%I
echo pid: %PID%
::combine above with jstack command
psexec -s jstack.exe -l %PID% >> %ff%
:: view result
start %ff%
::insert pause to debug or timer to review script operation
::ping localhost -n 20 >nul
::pause
回答by Stefan Winkler
If you want to use the on-board tools of the JDK and also want to both have a minimal (i.e., not including copying the whole JDK) and convenient (i.e. not invoking with a custom .bat) solution, this works for me (tried on Java 1.8):
如果您想使用 JDK 的板载工具,并且还想同时拥有最小(即,不包括复制整个 JDK)和方便(即不使用自定义调用.bat)的解决方案,这对我有用(试过Java 1.8):
Create an empty folder ($DESTbelow) and copy the following files (from the JDK $JDK_HOME) into binand libfolders as follows:
创建一个空文件夹($DEST如下)并将以下文件(从 JDK $JDK_HOME)复制到bin和lib文件夹中,如下所示:
Source -> Destination
$JDK_HOME/bin/jps.exe -> $DEST/bin/jps.exe
$JDK_HOME/bin/jstack.exe -> $DEST/bin/jstack.exe
$JDK_HOME/bin/jli.dll -> $DEST/bin/jli.dll
$JDK_HOME/jre/bin/attach.dll -> $DEST/bin/attach.dll
$JDK_HOME/lib/tools.jar -> $DEST/lib/tools.jar
Then ZIP and copy this over to the destination machine running a compatible JRE.
然后 ZIP 并将其复制到运行兼容 JRE 的目标机器上。
You should be able to run jpsand jstackfrom the binfolder now as you would run them from the original JDK.
您应该能够运行jps,并jstack从bin文件夹现在,你会从原来的JDK运行它们。

