Из того, что Linux kernel/libc версия является Java Runtime.exec () безопасный относительно памяти?

Исключение нулевого указателя - это индикатор того, что вы используете объект, не инициализируя его.

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

public class Student {

    private int id;

    public int getId() {
        return this.id;
    }

    public setId(int newId) {
        this.id = newId;
    }
}

Приведенный ниже код дает вам исключение с нулевым указателем.

public class School {

    Student obj_Student;

    public School() {
        try {
            obj_Student.getId();
        }
        catch(Exception e) {
            System.out.println("Null Pointer ");
        }
    }
}

Поскольку вы используете Obj_Student, но вы забыли инициализировать его, как в правильном коде, показанном ниже:

public class School {

    Student obj_Student;

    public School() {
        try {
            obj_Student = new Student();
            obj_Student.setId(12);
            obj_Student.getId();
        }
        catch(Exception e) {
            System.out.println("Null Pointer ");
        }
    }
}
23
задан Kara 1 February 2014 в 20:28
поделиться

4 ответа

Это в значительной степени способ, которым * nix (и linux) работали с незапамятных времен (или на заре mmus).

Чтобы создать новый процесс в * nixes, вы вызываете fork (). fork () создает копию вызывающего процесса со всеми его отображениями памяти, файловыми дескрипторами и т. д. Отображения памяти выполняются с копированием при записи, поэтому (в оптимальных случаях) фактически не копируется никакая память, только отображения. Следующий вызов exec () заменяет текущее отображение памяти на отображение нового исполняемого файла. Итак, fork () / exec () - это способ создания нового процесса, и это то, что использует JVM.

Предостережение - с огромными процессами в загруженной системе, родительский элемент может продолжать работать некоторое время, прежде чем child exec () вызывает копирование огромного объема памяти из-за копирования при записи. В виртуальных машинах память можно много перемещать, чтобы упростить сборщик мусора, который производит еще больше копирования.

«Обходной путь» - сделать то, что вы уже сделали, создать внешний облегченный процесс, который позаботится о порождении новых процессов - или использовать более легкий подход, чем fork / exec для порождения процессов (чего в Linux нет - и в любом случае потребуется изменение самого jvm). Posix определяет функцию posix_spawn (), которая теоретически может быть реализована без копирования отображения памяти вызывающего процесса, но в Linux это не так.

создать внешний облегченный процесс, который заботится о порождении новых процессов - или использовать более легкий подход, чем fork / exec, для порождения процессов (чего нет в Linux - и в любом случае потребует изменения в самом jvm). Posix определяет функцию posix_spawn (), которая теоретически может быть реализована без копирования отображения памяти вызывающего процесса, но в Linux это не так.

создать внешний облегченный процесс, который заботится о порождении новых процессов - или использовать более легкий подход, чем fork / exec, для порождения процессов (чего нет в Linux - и в любом случае потребует изменения в самом jvm). Posix определяет функцию posix_spawn (), которая теоретически может быть реализована без копирования отображения памяти вызывающего процесса, но в Linux это не так.

11
ответ дан 29 November 2019 в 03:00
поделиться

1: Да. 2: Это разделено на два шага: Любой системный вызов как ветвление () обертывается glibc к ядру. Часть ядра системного вызова находится в kernel/fork.c 3: Я не знаю. Но я держал бы пари, что Ваше ядро имеет его.

уничтожитель OOM умирает, когда Низкой памяти угрожают на полях на 32 бита. У меня никогда не было проблемы с этим, но существуют способы держать OOM в страхе. Этой проблемой могла быть некоторая проблема конфигурации OOM.

, Так как Вы используете JAVA-приложение, необходимо рассмотреть перемещение в Linux на 64 бита. Это должно определенно зафиксировать его. Большая часть приложений на 32 бита может работать на ядре на 64 бита без проблем, пока соответствующие библиотеки установлены.

Вы могли также попробовать ядро PAE за мягкую фетровую шляпу на 32 бита.

1
ответ дан Bash 29 November 2019 в 03:00
поделиться

Ну, я лично сомневаюсь, что это верно, так как ветвление Linux () сделано с помощью копии на записи, так как Бог знает, когда (по крайней мере, 2.2.x ядра имели его, и это было где-нибудь в 199x).

, Так как уничтожитель OOM, как полагают, является довольно сырым инструментом, который, как известно, дает осечку (f.e., это не делает необходимых уничтожений процесс, который на самом деле выделил большую часть памяти), и который должен использоваться только в качестве последнего переспорта, мне не ясно, почему Вам настроили его для стрельбы 160M.

, Если Вы хотите наложить ограничение на выделение памяти, тогда ulimit является Вашим другом, не OOM.

Мой совет состоит в том, чтобы оставить OOM в покое (или отключить его в целом), настройте ulimits и забудьте об этой проблеме.

5
ответ дан ADEpt 29 November 2019 в 03:00
поделиться

Да, это верно даже для новых версий Linux (мы используем 64-битную Red Hat 5.2). У меня была проблема с медленно работающими подпроцессами около 18 месяцев, и я никогда не мог понять проблему, пока не прочитал ваш вопрос и не проверил тест, чтобы проверить его.

У нас есть 32-гигабайтный блок с 16 ядрами, и если мы запускаем JVM с такими настройками, как -Xms4g и -Xmx8g, и запускаем подпроцессы с помощью Runtime.exec () с 16 потоками, мы не можем запускать наш процесс быстрее, чем примерно 20 вызовов процессов в секунду.

Попробуйте это с помощью простой команды «date» в Linux примерно 10 000 раз. Если вы добавляете код профилирования, чтобы наблюдать, что происходит, он запускается быстро, но со временем замедляется.

Прочитав ваш вопрос, я решил попробовать снизить настройки памяти до -Xms128m и -Xmx128m. Теперь наш процесс выполняется со скоростью около 80 вызовов в секунду. Все, что я изменил, - это настройки памяти JVM.

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

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

2
ответ дан 29 November 2019 в 03:00
поделиться
Другие вопросы по тегам:

Похожие вопросы: