Я не понимаю команду bash exec. Я видел, как он использовался внутри скриптов для перенаправления всех выходных данных в файл (как показано в этот). Но я не понимаю, как это работает или что он делает в целом. Я прочитал справочные страницы, но я их не понимаю.
man bash говорит:
exec [-cl] [-a name] [command [arguments]] If command is specified, it replaces the shell. No new process is created. The arguments become the arguments to command. If the -l option is supplied, the shell places a dash at the beginning of the zeroth argument passed to command. This is what login(1) does. The -c option causes command to be executed with an empty environment. If -a is supplied, the shell passes name as the zeroth argument to the executed command. If command cannot be executed for some reason, a non-interactive shell exits, unless the execfail shell option is enabled. In that case, it returns failure. An interactive shell returns failure if the file cannot be executed. If command is not specified, any redirections take effect in the current shell, and the return status is 0. If there is a redirection error, the return status is 1.Последние две строки - это то, что важно: если вы запустите exec сам по себе, без команды, он просто заставит перенаправления применяться к текущей оболочке. Вы, вероятно, знаете, что, когда вы бежите command > file, выход из command записывается в file вместо того, чтобы на ваш терминал (это называется перенаправление). Если вы запустите exec > file вместо этого перенаправление применяется ко всей оболочке: любой вывод, созданный оболочкой, записывается в file вместо того, чтобы обращаться к вашему терминалу. Например, здесь
bash-3.2$ bashbash-3.2$ exec > filebash-3.2$ datebash-3.2$ exitbash-3.2$ cat fileThu 18 Sep 2014 23:56:25 CESTЯ впервые начинаю новую bash ракушка. Затем в этой новой оболочке я запускаю exec > file, так что все выходные данные перенаправляются на file. Действительно, после этого я бегу date но я не получаю никаких выходных данных, потому что выходные данные перенаправляются на file. Затем я выхожу из своей оболочки (так что перенаправление больше не применяется), и я вижу, что file действительно содержит выходные данные date команда, которую я запустил ранее.
exec это команда с двумя очень разными поведениями, в зависимости от того, используется ли с ней хотя бы один аргумент или вообще не используется ни один аргумент.
Если передается хотя бы один аргумент, первый из них принимается в качестве имени команды и
execпопробуйте выполнить его как команду, передав оставшиеся аргументы, если таковые имеются, этой команде и управляя перенаправлениями, если таковые имеются.Если команда, переданная в качестве первого аргумента, не существует, текущая оболочка, а не только
execкоманда завершается с ошибкой, если только оболочка не является интерактивной или опция bashexecfailустановлен (shopt -s execfail). См. также https://superuser.com/questions/992204/why-does-exec-non-existent-file-exits-the-shell-when-in-a-script-that-is-sourcЕсли команда существует и является исполняемой, она заменяет текущую оболочку. Это означает, что если
execпоявляется в скрипте, инструкции, следующие за вызовом exec никогда не будет казнен (если толькоexecсам находится в подоболочке). Успешныйexecникогда не возвращается. Ловушки оболочки, такие как "ВЫХОД", также не будут срабатывать.Если аргумент не передается,
execиспользуется только для переопределения текущих файловых дескрипторов оболочки. Оболочка продолжается после того, какexec, в отличие от предыдущего случая, но стандартный ввод, вывод, ошибка или любой другой дескриптор файла, который был перенаправлен, вступают в силу.Если некоторые из перенаправлений используют
/dev/null, любой ввод из него вернет EOF, а любой вывод на него будет отброшен.Вы можете закрыть файловые дескрипторы с помощью
-как источник или пункт назначения, напримерexec <&-. Последующее чтение или запись в этом случае завершатся неудачей.
Вот два примера:
echo foo > /tmp/barexec < /tmp/bar # exec has no arguments, will only affect current shell descriptors, here stdincat # simple command that read stdin and write it to stdoutЭтот скрипт выведет "foo" в качестве команды cat, вместо того, чтобы ждать ввода пользователя, как это было бы в обычном случае, будет принимать свои входные данные из файла /tmp/bar, который содержит foo.
echo foo > /tmp/barexec wc -c < /tmp/bar # exec has two arguments, the control flow will switch to the wc commandcatЭтот скрипт отобразит 4 (количество байт в /tmp/bar) и немедленно завершается. То cat команда не будет выполнена.
Чтобы понять exec вам нужно сначала понять fork Я стараюсь быть кратким.
Когда вы подходите к развилке дорог, у вас обычно есть два варианта. Программы Linux достигают этой развилки на дороге, когда они попадают в
fork()системный вызов.Обычные программы - это системные команды, которые существуют в скомпилированной форме в вашей системе. Когда такая программа выполняется, создается новый процесс. Этот дочерний процесс имеет ту же среду, что и его родительский, отличается только идентификационный номер процесса. Эта процедура называетсяраздвоение.
- Разветвление предоставляет способ для существующего процесса запустить новый. Однако могут возникнуть ситуации, когда дочерний процесс не является частью той же программы, что и родительский процесс. В этом случае
execиспользуется.execзаменит содержимое текущего запущенного процесса информацией из двоичного файла программы. - После процесса разветвления адресное пространство дочернего процесса перезаписывается новыми данными процесса. Это делается с помощью execcall к системе.
В bash, если вы это сделаете help exec:
$ help execexec: exec [-cl] [-a name] [command [arguments ...]] [redirection ...] Replace the shell with the given command. Execute COMMAND, replacing this shell with the specified program. ARGUMENTS become the arguments to COMMAND. If COMMAND is not specified, any redirections take effect in the current shell. Options: -a name pass NAME as the zeroth argument to COMMAND -c execute COMMAND with an empty environment -l place a dash in the zeroth argument to COMMAND If the command cannot be executed, a non-interactive shell exits, unless the shell option `execfail' is set. Exit Status: Returns success unless COMMAND is not found or a redirection error occurs.Соответствующий бит:
If COMMAND is not specified, any redirections take effect in the current shell.exec это встроенная оболочка, который является оболочечным эквивалентом exec семья из системные вызовы тот G_P говорит о (и чьи справочные страницы вы, по-видимому, прочитали). У него просто есть Предписанный POSIX функциональность воздействия на текущую оболочку, если не указана команда.
@fkraiem что ты имеешь в виду?
Извини, я имел в виду “что”.
Но ответ, похоже, отрицательный.
Но на самом деле ваш скрипт использует exec особым образом, что можно объяснить гораздо проще, я напишу ответ.
@becko `exec" - это не про процессы. Он не создает процесс.
Пожалуйста, включите код в вопрос, чтобы нам не приходилось нажимать на него, чтобы прочитать, и потому что веб-сайты меняются. Также я не могу найти использование exec на веб-странице, связанной с веб-страницей.