Захват SIGINT в Java - PullRequest
       25

Захват SIGINT в Java

38 голосов
/ 30 марта 2010

Каков наилучший способ захвата сигнала уничтожения в Java без использования JNI. Я обнаружил sun.misc.Signal и sun.misc.SignalHandler и предупреждение о возможности удаления в будущих версиях.

Будет ли использование JNI для вызова c lib единственным вариантом, который у меня есть?

Ответы [ 3 ]

54 голосов
/ 30 марта 2010

Способ справиться с этим - зарегистрировать shutdown hook. Если вы используете ( SIGINT ) kill -2, из-за этого программа изящно выйдет и запустит блокировку отключения.

Регистрирует новую виртуальную машину отключающий крюк.

Виртуальная машина Java отключается в ответ на два вида событий:

  • Программа завершается нормально, когда завершается последний поток, не являющийся демоном, или когда вызывается метод выхода (эквивалентно System.exit), или

  • Виртуальная машина завершает работу в ответ на пользовательское прерывание, такое как ввод ^ C, или общесистемное событие, такое как выход пользователя из системы или завершение работы системы.

Я попробовал следующую тестовую программу на OSX 10.6.3, а на kill -9 он NOT запустил ловушку завершения работы, не думал, что так будет. На kill -15 it DOES каждый раз запускается отключающий крюк.

public class TestShutdownHook
{
    public static void main(final String[] args) throws InterruptedException
    {
        Runtime.getRuntime().addShutdownHook(new Thread()
        {
            @Override
            public void run()
            {
                System.out.println("Shutdown hook ran!");
            }
        });

        while (true)
        {
            Thread.sleep(1000);
        }
    }
}

Это документированный способ написания ваших собственных обработчиков сигналов , которые не являются перехватчиками завершения работы в Java. Будьте предупрежденными , что пакеты com.sun.misc не поддерживаются и могут быть изменены или удалены в любое время и, вероятно, существуют только в Sun JVM.

4 голосов
/ 02 декабря 2014

Поскольку, по крайней мере, в Java 6 команда HotSpot java имеет флаг -Xrs для отключения обработчиков сигналов JVM.

Если вы используете его, вам нужно реализовать свой собственный SIGINT,Обработчики SIGTERM, SIGHUP и SIGQUIT, включая один для явного вызова System.exit().

Примечание. Это означает, что функция дампа потока SIGQUIT отключена, если присутствует флаг -Xrs.

См. https://docs.oracle.com/javase/8/docs/technotes/tools/unix/java.html#BABHDABI (также доступно в аналогах Windows и Solaris java).

4 голосов
/ 30 марта 2010

Взгляните на Интегрирование обработки сигналов и исключений , описывающее способность HotSpot JVM действительно связывать сигналы. Тем не менее, он включает в себя некоторую хитрость уровня C.

Разве java.lang.Runtime.addShutdownHook(Thread) не будет достаточно для вашей цели? Эти перехваты запускаются JVM после завершения, включая прием SIGINT, если JVM может их выполнить.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...