Не удается отладить Java-службы Windows с помощью jhat, jps, jstack

Я часто показываю jhat, jps, а инструмент jstack - для разработчиков на Linux и Mac. Однако недавно разработчик указал, что они непригодны для использования в Windows, если рассматриваемое приложение Java работает как служба Windows.

A Исправлена ​​ошибка с ошибкой Sun, но она была закрыта из-за бездействия.

Я проверил это для себя, и действительно это кажется правдой, хотя я с трудом могу в это поверить. Вот настройка:

  • Tomcat или аналогичный запуск в качестве службы Windows с функцией "Вход в систему" ​​== "Локальная система"
  • Пользователь с правами администратора, зарегистрированными на той же машине Windows.
  • Администратор открывает Диспетчер задач Windows, может видеть, как работает java.exe
  • Администратор открывает консоль, набирает "jps", возвращает список процессов, которые не включают в себя сервисный процесс Tomcat java.
  • Как попытка грубой силы получить PID tomcat как службу из диспетчера задач Windows. Тип jstack <pid> . Получите ответ: <pid> нет такого процесса

Это выглядит воспроизводимым в Windows XP, Windows 2003 Server и Windows 7. Версии Java 1.5 и 1.6 дают тот же результат.

Есть ли способ от терминала, даже если он входит в систему как Admin, для "sudo up", чтобы получить JPS и другие инструменты для просмотра java-сервиса?

Ответ 1

Чтобы запустить утилиту, вы можете подключиться к сеансу консоли с помощью "mstsc/admin", используя учетную запись (не обязательно точные разрешения, которые должны быть у нее есть, моя была в группе "Администраторы" ) и использовать инструмент sysinternals psexec для запуска в качестве системы. Ниже приведен пример использования jstack.exe:

psexec -s "%JAVA_HOME%\bin\jstack.exe" PID >stack.txt
Где PID - это идентификатор процесса вашего процесса. Возможно, вам также придется подставить реальный путь к вашему JDK в зависимости от вашей конкретной среды.

Кроме того, каталог TEMP должен быть установлен правильно или еще раз инструменты не будут работать.

Ответ 2

У меня были удаленные процессы отладки, выполняемые пользователем SYSTEM, запустив это из командной строки:

c:> time/t
11:18 AM
c:> at 11:19 /interactive cmd.exe
Added a new job with job ID = 1

Используйте время 1 минута в будущем. Когда задание "at" запускает командную строку Windows, она будет запускаться как пользовательская система. Оттуда вы сможете увидеть java-процессы.

Если служба запущена как локальный пользователь (проверьте данные с "mmc% windir%\system32\SERVICES.MSC", дважды щелкнув по этой услуге и выбрав вкладку "Вход" ), вы можете сделать то же самое используя "runas":

runas /user:USERNAME cmd.exe

Ответ 3

Вы получаете только те процессы, которые "принадлежат" вам - тот же идентификатор пользователя.

Можете ли вы подключиться к нему с помощью jvisualvm?

Ответ 5

Это мой пакетный файл для записи дампа потока

    :: Creates a thread dump for the tomcat6.exe process saved in a timestamped filename and views it!
:: Jim Birch 20111128 rev 2015-10-12

::Note this required the following files to be placed in the confluence jre/bin folder:
:: 
:: attach.dll  - From the Java JDK  (must be the same version)
:: tools.jar   - ditto
:: psexec.exe  - from Windows sysinternals
:: Also, the TEMP directory must be set (stack overflow)
set TEMP=c:\windows\temp

::go to run location
d:
cd \confluence.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%

::tomcat PID   
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 (won't work without psexec)
psexec -s "D:\confluence.application\jre\bin\jstack.exe" -l %PID%  >>  %ff%

:: view output txt file
start %ff%

::pause to review script operation, or use ping to wait a few secs 
::ping localhost -n 20 >nul
pause

Ответ 6

Вот решение, которое в конечном итоге помогло мне получить стековые трассировки из неподготовленного Java-процесса, запущенного под другим пользователем в терминальной сессии или в качестве службы Windows.

jstack.cmd:

@for /f "usebackq tokens=2" %%I in ('tasklist /NH /FI "imagename eq tomcat.exe" /FI "username eq SYSTEM"') DO set PID=%%I
@for /f "tokens=2 delims==." %%G in ('wmic os get localdatetime /value') do @set datetime=%%G
@set date_time=%datetime:~0,4%_%datetime:~4,2%_%datetime:~6,2%__%datetime:~8,2%_%datetime:~10,2%_%datetime:~12,2%
PsExec.exe /accepteula -h -s -d cmd /c "%JAVA_HOME%\jstack.exe" -l %PID% ^>%~dp0jstack_%date_time%.txt

Первая строка определяет PID по имени процесса и пользователю.

Затем PsExec с принятым EULA помогает вызывать jstack в режиме повышенных прав с правильно экранированным перенаправлением вывода в jstack*.txt каталоге dir с отметкой времени, включенной в имя файла.

Возможно, вам придется добавить каталоги PsExec и JDK в PATH заранее.

Ранее я пытался принудительно создать поток потоков с помощью SendSignal, но он никогда не работал надежно с процессами службы Windows.