2016-05-21 5 views
1

Я запускаю команду в фоновом режиме в моем сценарии bash. Мне нужно восстановить stderr этого в var и не знаю, как это сделать. Помогите! : DBash. восстановить stderr команды фона

#!/bin/bash 
existingdestiny="8.8.8.8" #this is google dns for the example 
ping -c 1 $existingdestiny -W 1 > /dev/null 2>&1 
exitvar=$? 
echo "exitvar: $exitvar" 

nonexistingdestiny="172.16.0.234" #this is a non accesible ip example 
ping -c 1 $nonexistingdestiny -W 1 > /dev/null 2>&1 
exitvar=$? 
echo "exitvar: $exitvar" 

Это работает, оно возвращает 0, а затем 1, что правильно, приятно! но если я положу команду в фоновом режиме, я не могу взять stdout. Давайте посмотрим:

#!/bin/bash 
existingdestiny="8.8.8.8" #this is google dns for the example 
ping -c 1 $existingdestiny -W 1 > /dev/null 2>&1 & 
exitvar=$? 
echo "exitvar: $exitvar" 

nonexistingdestiny="172.16.0.234" #this is a non accesible ip example 
ping -c 1 $nonexistingdestiny -W 1 > /dev/null 2>&1 & 
exitvar=$? 
echo "exitvar: $exitvar" 

Он возвращает 0 и 0, что является неправильным. Как я могу получить правильные ответы?

ответ

1

Код выхода и стандартный вывод ошибки (также известный как «stderr») - это две разные вещи. Стандартный вывод ошибки - это выходной поток, который любая программа может писать независимо от того, что она хочет. Код выхода (также известный как статус выхода) представляет собой целое число, возвращаемое процессом.

Из фрагмента в вопросе, я предполагаю, что вы хотите получить код выхода.

Специальный символ оболочки $? действительно вернет код выхода последней запущенной команды. Однако это не работает с командами, запущенными в фоновом режиме, через &. Это связано с тем, что, поскольку команда запускается в фоновом режиме, она еще не закончена. И даже если бы это закончилось, оболочка не узнала бы.

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

Чтобы использовать команду wait, вам необходимо знать идентификатор процесса фонового процесса. Вы можете получить идентификатор процесса команды, запущенной в фоновом режиме, с помощью $! специальный символ. Таким образом, следующий код будет делать то, что вы хотите:

COMMAND & 
pid="$!" 
# Optional: Do something else while ping runs 
wait "$pid" 
exitcode="$?" 
echo "exitcode=$exitcode" 

Однако обратите внимание, что сама команда пинг не остановится, поэтому только начинается пинг в фоновом режиме и ждать его будет просто висеть.

Я рекомендую не запускать ping в фоновом режиме. Вы уже правильно используете опции -c и -W, чтобы убедиться, что ping не будет висеть.

+0

О да, мне нужен код выхода. И еще вопрос ... как отправить команду на задний план и в то же время получить stdout? У меня есть команда 'iface = $ (airmon-ng start wlan0 2>/dev/null | grep monitor)' и i wan, чтобы отправить ее на задний план, но когда я помещаю & где угодно, grep перестает работать и iface var пустой. Есть идеи? – OscarAkaElvis

1

Вам необходимо записать ПИД-код фонового процесса, затем позвонить wait, чтобы получить статус возврата.

ping -c 1 $nonexistingdestiny -W 1 > /dev/null 2>&1 & 
ping_pid=$! 
wait $ping_pid 
exitvar=$? 
echo "exitvar: $exitvar" 

(я думаю, что вы хотите, возвращение статуса, а не stderr, который находится на файловый дескриптор 2).