Перенаправление stdout и stderr из фонового процесса

У меня есть сценарий под названием foo, который запускает программу a.exe и отправляет статистику времени в файл time.log

#!/bin/bash
date 1>> time.log
(time ./a.exe) 2>> time.log

Это работает, если я запускаю скрипт в фоновом режиме своего терминала и держу свою оболочку открытой до завершения работы a.exe, но если я запускаю скрипт в фоновом режиме и выхожу из терминала (запуск a.exe занимает много времени)

foo & 
exit

когда я возвращаюсь, a.exe выполняется, но статистика времени не отображается в моем файле журнала. Кто-нибудь знает, почему это? Есть ли способ получить статистику времени после закрытия родительской оболочки?

Благодарность


person frankscup    schedule 28.11.2010    source источник


Ответы (5)


nohup foo &

Когда вы выходите из оболочки, она отправляет сигнал SIGHUP всем дочерним процессам, который по умолчанию их уничтожает. Если вы хотите, чтобы процесс продолжал выполняться даже после выхода из родительской оболочки, вам нужно, чтобы он игнорировал SIGHUP.

НАЗВАНИЕ

nohup - вызвать команду, невосприимчивую к зависаниям

ОБЗОР

nohup utility [arg ...]

ОПИСАНИЕ

Утилита nohup вызывает команду со своими аргументами и в это время устанавливает игнорирование сигнала SIGHUP. Если стандартный вывод - это терминал, стандартный вывод добавляется к файлу nohup.out в текущем каталоге. Если стандартная ошибка - это терминал, она направляется в то же место, что и стандартный вывод.

person John Kugelman    schedule 28.11.2010

Поскольку вопрос также помечен как bash, я цитирую man bash

disown [-ar] [-h] [jobspec ...]
          Without  options,  each  jobspec  is  removed  from the table of
          active jobs.  If jobspec is not present, and neither -a  nor  -r
          is  supplied, the shell's notion of the current job is used.  If
          the -h option is given, each jobspec is not removed from the ta‐
          ble,  but is marked so that SIGHUP is not sent to the job if the
          shell receives a SIGHUP.  If no jobspec is present, and  neither
          the  -a  nor the -r option is supplied, the current job is used.
          If no jobspec is supplied, the -a option means to remove or mark
          all  jobs;  the  -r  option without a jobspec argument restricts
          operation to running jobs.  The return value is 0 unless a  job‐
          spec does not specify a valid job.

Это пригодится, когда вы начали работу, но забыли поставить перед ней префикс nohup. Просто сделать

disown -ah
disown -a
person dennycrane    schedule 28.11.2010

Не забудьте удалить все ссылки на tty / pts, 0 ‹/ dev / null удаляет ссылку на стандартный ввод.

person Rahly    schedule 28.11.2010

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

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

Джон дал гораздо лучший ответ - используйте nohup.

person harithski    schedule 10.12.2010
comment
Точно. Если вы заранее знаете, что запускаете длительный процесс или используете нестабильное соединение, вам следует использовать screen или tmux. Эти программы дают вам гораздо больше гибкости в управлении заданиями и окнами. - person Martijn Heemels; 25.05.2011

Пытаться:

nohup <your_command> &
person khachik    schedule 28.11.2010