我想对 Windows 上运行的 Java 程序进行一些调试:回溯、打印一些变量、设置断点、单步执行关键函数。
我尝试的第一件事是
jdb -attach 5312
。此操作失败,并显示“shmemBase_attach 失败:系统找不到指定的文件”。我发现了一些关于该错误消息的相关问题,但他们似乎在谈论一个更复杂的场景,涉及不同主机上的调试器和目标。
我正在做的是本地进程附加,所以我认为它应该更容易。但有一些事情让它变得更困难。
目标进程不以
java -jar foo.jar
或任何类似的正常方式运行。它是一个包装了 java 代码的特定于应用程序的 EXE 文件。它在进程列表中将自己标识为“Commons Daemon Service Runner”,查看其中的字符串,它似乎是来自 Apache Commons Daemon 的 prunsrv
程序。
Process Explorer 告诉我没有命令行参数,并且该进程是 services.exe 的子进程。我能够从 Windows 服务启动和停止它,但我不知道如何用它做其他事情。
jps
命令没有显示这个过程,但我知道它是一个Java程序......轻度包装。有什么办法可以调试吗?
尝试将 _JAVA_OPTIONS 变量设置为如下所示:
_JAVA_OPTIONS "-agentlib:jdwp=transport=dt_socket,server=y,suspend=y,address=32887"
JVM 启动时应获取该变量。
然后,您可以尝试通过调用来附加到该 JVM
jdb -attach 32887
其中 32887 是调试器使用的任意端口号(数字必须匹配)。
更新:
您可以使用不同的连接方式。由你决定。我给您提供的只是许多不同设置方法的一个示例。请看这里了解更多详细信息:
https://docs.oracle.com/javase/8/docs/technotes/guides/jpda/conninv.html
您还可以使用 VisualVM。在这种情况下,您需要让运行 VisualVM 的用户看到 JVM 进程。