JVM без сбора мусора

Я читал во многих потоках, что невозможно отключить сбор мусора на Sun JVM. Однако для целей нашего исследовательского проекта нам нужна эта функция. Может ли кто-нибудь рекомендовать реализацию JVM, которая не содержит сборку мусора или которая позволяет отключить ее? Спасибо.

Ответы

Ответ 1

  Я хотел найти быстрый способ сохранить все объекты в памяти для простого начального доказательства концепции.

Простой способ сделать это - запустить JVM с кучей, которая настолько велика, что GC никогда не должен запускаться. Установите для параметров -Xmx и -Xms большое значение и включите ведение журнала GC, чтобы убедиться, что GC не работает в течение всего теста.

Это будет быстрее и проще, чем изменение JVM.


(In hindsight, this may not work. I vaguely recall seeing evidence that implied that the JVM does not always respect the [TG42] setting, especially if it was really big. Still, this approach is worth trying before trying some much more difficult approach ... like modifying the JVM.)

Also, this whole thing strikes me as unnecessary (even counter-productive) for what you are actually trying to achieve. The GC won't throw away objects unless they are garbage. And if they are garbage, you won't be able to use them. And the performance of a system with GC disabled / negated is not going to indicative of how a real application will perform.


ОБНОВЛЕНИЕ - Начиная с Java 11, у вас есть гораздо более простой вариант использования сборщика мусора Epsilon (no-op); см

При запуске JVM добавляются следующие параметры:

-XX:+UnlockExperimentalVMOptions -XX:+UseEpsilonGC

Когда куча заполнена, никакие попытки собрать мусор не предпринимаются. Вместо этого Epsilon GC завершает JVM.

Ответ 2

В зависимости от ваших потребностей это может работать:

Используя параметр -Xbootclasspath, вы можете указать собственную реализацию классов API. Затем вы могли бы, например, переопределить реализацию Object и добавить к конструктору globalList.add(this), чтобы предотвратить сбор мусора. Это взломать наверняка, но для простого изучения ситуации это, возможно, достаточно.

Другой вариант - принять jvm с открытым исходным кодом и закомментировать части, которые инициируют сбор мусора. Я бы предположил, что это не так сложно.

Ответ 3

Sun JVM не имеет такой возможности. AFAIK, никакой другой JVM не имеет этого варианта.

Вы не указали, что именно вы пытаетесь достичь, но у вас есть один из двух вариантов: либо используйте профилировщик, либо посмотрите, что делает GC, таким образом вы можете принять во внимание его последствия. Другой - скомпилировать один из JVM из источника и отключить GC оттуда.

Ответ 4

Возможно, вы могли бы попытаться сделать доступную память вашей виртуальной машины достаточной для того, чтобы GC никогда не запускался.

Мой (allbeit limited) опыт заставляет меня предположить, что виртуальная машина по умолчанию чрезвычайно ленива и крайне неохотно запускает GC.

давая -Xmx 16384M (или некоторые из таких) и следя за тем, чтобы ваш исследовательский объект оставался значительно ниже этого предела, может дать вам среду, которую вы хотите получить, хотя даже тогда она, очевидно, не будет гарантирована.

Ответ 5

Можете ли вы получить JVM с открытым исходным кодом и отключить его GC, например Sun Hotspot?

Если бы не было Garbage Collection, что бы вы ожидали быть семантикой кода, подобной этому?

public myClass {

      public void aMethod() {

            String text = new String("xyz");

      }

}

В отсутствие GC любой новый элемент и ссылка с привязкой к стеку никогда не могут быть восстановлены. Даже если ваши собственные классы могут решить не использовать локальные переменные, подобные этому, или использовать только примитивные типы, я не вижу, как вы могли бы безопасно использовать любую стандартную библиотеку Java.

Мне было бы интересно узнать больше о вашем сценарии использования.

Ответ 6

Взгляните на JRKD JVM для Oracle. Я видел очень хорошую почти детерминированную производительность на оборудовании Intel с помощью этой JVM, и вы можете создавать и вызывать время выполнения с помощью утилиты Mission Control посмотрите, насколько хорошо он работает.

Хотя вы не можете полностью отключить GC, я считаю, что вы можете использовать параметр - Xnoclassgc, чтобы отключить коллекцию классов. GC может быть настроен на свести к минимуму латентность за счет увеличения потребления памяти. Возможно, вам понадобится лицензия на то, чтобы отбросить задержку настолько низко, насколько вам нужно, если вы идете по этому маршруту.

Существует также версия JVM JRKT в реальном времени, но я не думаю, что есть свободная версия для разработчиков.

Ответ 7

Вы можете отключить GC, если он не нужен (в противном случае у вашего приложения будет нехватка памяти), и если вам не нужен GC, он не должен работать в любом случае.

Самый простой вариант - не отбрасывать какие-либо объекты, это позволит избежать выполнения GC (и установите максимальную память очень высоко, чтобы вы не закончили).

Вы можете обнаружить, что вы запускаете GC при запуске, и вы можете рассматривать no-GC при нормальной работе.

Ответ 8

На самом деле существует грязный взломать временную паузу GC. Сначала создайте фиктивный массив в Java. Затем в JNI используйте функцию GetPrimitiveArrayCritical, чтобы получить указатель на массив. Sun JVM отключит GC, чтобы гарантировать, что массив никогда не перемещается, и указатель остается действительным. Чтобы снова включить GC, вы можете вызвать функцию ReleasePrimitiveArrayCritical на указателе. Но это очень специфично для реализации, поскольку другой VM impl может привязать объект, а не полностью отключить GC. (Протестировано для работы с Oracle Jdk 7 и 8)

Ответ 9

вопрос старый, но для тех, кто может быть заинтересован, есть предложение

Создайте GC, который обрабатывает только распределение памяти, но не реализует никакого реального механизма восстановления памяти. Когда доступная куча Java исчерпана, выполните упорядоченное выключение JVM.

JEP draft: Epsilon GC: произвольно низкий сборщик мусора (Non-) Collector

Ответ 10

Если бы у меня была эта проблема, я бы получил IBM Jikes Research Virtual Machine, потому что:

  • Система времени выполнения написана на самой Java (со специальными расширениями)
  • Все это было разработано как исследовательский автомобиль и относительно легко подстраивается.

Вы не можете отключить GC навсегда, потому что Java-программы действительно выделяют, и в конечном итоге вы исчерпаете память, но вполне возможно, что вы можете отсрочить GC на время вашего эксперимента, сообщив JVM не начинать сбор пока куча не станет действительно большой. (Этот трюк может работать и на других JVM, но я не знаю, где найти ручки, чтобы начать крутить.)