2016-05-18 2 views
6

Чтобы поддерживать лучшие данные профилирования, я хотел бы, чтобы мой агент JVMTI включил пару флагов JVM. Агент, о котором идет речь, является Honest-Profiler, и его можно загрузить только при запуске.Как агент JVMTI может установить флаг JVM при запуске?

Я хотел бы включить флаги: -XX:+UnlockDiagnosticVMOptions -XX:+DebugNonSafepoints

По вопросу документален here если флаги не на мы получаем необъективный профиль. Было бы неплохо выйти за пределы предупреждения пользователя и просто включить флаг.

+2

Если вы не нашли юридического решения, существует gory-подход от @apangin: https://github.com/odnoklassniki/one-elf/blob/master/test/one/jvm/HotspotFlags.java он находит адрес загруженный libjvm.so и вычисляет адрес флага с .so адресом + .symtab постоянным смещением (но он не всегда работает, зависит от использования конкретного флага в коде VM) – qwwdfsad

ответ

8

Что касается DebugNonSafepoints, вам не нужно устанавливать этот флаг. Посмотрите на debugInfoRec.cpp:

static inline bool compute_recording_non_safepoints() { 
    if (JvmtiExport::should_post_compiled_method_load() 
     && FLAG_IS_DEFAULT(DebugNonSafepoints)) { 
    // The default value of this flag is taken to be true, 
    // if JVMTI is looking at nmethod codes. 
    // We anticipate that JVMTI may wish to participate in profiling. 
    return true; 
    } 

    // If the flag is set manually, use it, whether true or false. 
    // Otherwise, if JVMTI is not in the picture, use the default setting. 
    // (This is true in debug, just for the exercise, false in product mode.) 
    return DebugNonSafepoints; 
} 

Если флаг не установлен, то отладочная информация по-прежнему записывается при JVMTI CompiledMethodLoad уведомления включены. Вам просто нужно запросить can_generate_compiled_method_load_events и включить JVMTI_EVENT_COMPILED_METHOD_LOAD.

Именно так я справляюсь с этим в своем проекте async-profiler.


Безопасный способ изменения неуправляемых флагов JVM во время выполнения. Однако в Linux есть уродливый взлом.

  1. Прочитать /proc/self/maps, чтобы найти базовый адрес libjvm.so.
  2. Используйте ELF format reader, чтобы обнаружить смещение нужного символа в динамической библиотеке.
  3. Напишите прямо на адрес этого символа.

Это a sample code для этого.

+0

Я справился с ним через Helfy (а также с Hotspot SA). Я покажу его с образцом кода, когда я его подготовил –

+1

вот он https://github.com/serkan-ozal/jvm-playground/blob/master/src/main/java/tr/com/serkanozal/jvm/ детская площадка/ChangeImmutableVmFlagDemo.java –

+0

@ SerkanÖzal Cool! Не думал, что для этого можно использовать Хелфи. Не могли бы вы добавить этот пример в Helfy repo на github? – apangin

1

Хорошо, это не точный ответ, но больше толчка в определенном направлении ....

В services/writeableFlags.hpp есть статические методы для установки VM флагов. Успех будет зависеть от того, действительно ли эти флаги являются изменяемыми, но это было бы хорошее место, чтобы начать ковырять. Я не пробовал называть эти методы у агента JVMTI, но, теоретически, он должен работать.

1

Существует несколько флагов JVM, которые можно записать во время выполнения, используя com.sun.management.HotSpotDiagnosticMXBean.setVMOption.

(список см. http://hg.openjdk.java.net/jdk7/jdk7/hotspot/file/b92c45f2bc75/src/share/vm/runtime/globals.hpp и поиск manageable).

К сожалению, для вашего варианта использования опция UnlockDiagnosticVMOptions не доступна для записи.

 Смежные вопросы

  • Нет связанных вопросов^_^