Java JVMTI не работает вместе с -Xdebug -Xrunjdwp
Последние 4 часа я потратил на настройку профилирования памяти Eclipse TPTP на экземпляре Tomcat, который должен запускаться удаленно (т.е. не в Eclipse). Это должно быть возможно в соответствии с документами TPTP и Agent Controller.
Я установил компоненты TPTP (4.6.0) в свою рабочую среду Eclipse (Galileo) вместе с контроллером агентов в соответствии с инструкциями на веб-сайте. Чтобы включить агент, я добавил следующие опции в командную строку, которая запускает экземпляр Tomcat:
-agentlib:JPIBootLoader=JPIAgent:server=enabled;HeapProf:allocsites=true
и добавил следующие каталоги в начало PATH:
D:\dev\tools\ac\plugins\org.eclipse.tptp.javaprofiler
D:\dev\tools\ac\bin
При попытке запустить Tomcat я постоянно получал следующее сообщение об ошибке:
ERROR: JDWP unable to get necessary JVMTI capabilities. ["debugInit.c",L279]
Я много гуглял, но ничего не нашел; Я попытался переустановить TPTP и различные версии контроллера агентов.
В итоге проблема оказалась в том, что я запускал Tomcat с опцией "jpda", которую catalina.bat переводит в
-Xdebug -Xrunjdwp:transport=.....
Удаление аргумента команды "jpda" заставило JVMTI начать работать.
Итак, вопрос в том, что во время поисков я ничего не обнаружил, чтобы указать, что агент JVMTI несовместим с отладкой. Может кто-нибудь объяснить, что происходит и почему JVMTI + JDWP не является допустимой установкой?
3 ответа
Пока что ни один из ответов не является правильным, и это первый случай, который появится в Google, если вы запросите указанную ошибку, поэтому я чувствую, что некоторые пояснения необходимы.
JVMTI и JDWP работают вместе, фактически они обычно должны использоваться вместе. Ты получишь ERROR: JDWP unable to get necessary JVMTI capabilities
если -Xrunjdwp
(и / или возможно -agentlib:jdwp
) указывается более одного раза в командной строке. Чтобы исправить это, убедитесь, что у вас есть только один из -Xrunjdwp
или же -agentlib:jdwp
в вашей командной строке.
Для более подробной информации читайте дальше...
JVMTI (интерфейс инструмента виртуальной машины Java) является преемником JVMDI (интерфейс отладки виртуальной машины Java) и JVMPI (интерфейс профилирования виртуальной машины Java). Он включает в себя функциональные возможности как JVMDI, так и JVMPI, которые устарели в Java 5 и удалены в Java 6. Это API, который предоставляет внутреннюю часть JVM для целей отладки и профилирования.
JDWP (Java Debug Wire Protocol) - это протокол, который описывает простой механизм передачи команд и ответов. Насколько я знаю, это единственный способ для отладчика, сидящего вне JVM, общаться с ним и взаимодействовать с JVMTI.
JDI (Java Debugger Interface) - это API на стороне клиента (на стороне отладчика), который предоставляет некоторые функции JVMTI, в то же время используя JDWP более или менее прозрачно.
Ошибка, упомянутая в ответе Боба Доббса, касается вводящего в заблуждение сообщения об ошибке и того факта, что JVM будет пытаться загрузить JDWP один раз за каждый раз, когда он указан в командной строке. Нигде не говорится, что JDWP и JVMTI нельзя использовать вместе.
Более подробная информация здесь: http://publib.boulder.ibm.com/infocenter/iseries/v5r4/topic/rzaha/jpdebuga.htm
Я столкнулся с той же проблемой, что и вы, но я подготовил отчет об ошибке JVM ( http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6354345), который пролил некоторый свет на эту проблему. Это в основном сводится к тому, что библиотека агента Java никогда не предназначена для двойной загрузки в одну и ту же виртуальную машину. Отстой, но, похоже, это основное ограничение системы агентов, которое нельзя делать обоим одновременно.
Для меня это была та же проблема, что и в посте Code Bling, они были повторены -Xrunjdwp
не понял, что был второй -Xrunjdwp
как это было спрятано в переменной %JAVA_OPTIONS%
проверьте скрипт запуска сервера приложений.