Які можливості використання команди exec?


10

Я навчаюсь execкоманді. Я знаю, що execкоманда замінює процес, який її запустив. Тож повернутися до процесу, який замінюється execкомандою, неможливо .

Можна сказати, що його мета - унеможливити повернення до процесу, який його розпочав.

Але які ще є можливості мати щось на зразок команди, execдоступного як команда?



1
із статті вікіпедії: "Сценарії Wrapper часто використовують цю команду для запуску програми (безпосередньо або через інтерпретатор або віртуальну машину) після встановлення змінних середовища або іншої конфігурації."
кнб

1
більше підходить для інформатики
Анвар

2
Особисто мені здається, що мені exec ssh server-that-does-byobu-on-login.example.comдуже подобається, що ^ A ^ D повністю закриває термінал. (Більш загально, exec byobu(або exec screen, exec tmux).
Вілліхам Тотланд

Відповіді:


9

У сценарії обгортки

exec використовується в основному в сценарії обгортки.

Якщо ви хочете змінити середовище для програми перед виконанням основної програми, ви часто пишете сценарій і в кінці його запускаєте основну програму. Але немає необхідності, щоб сценарій залишався в пам’яті на той час. Отже, execвикористовується в цих випадках так, що основна програма може замінити материнський скрипт.

Ось практичний приклад цього. Це mate-terminal.wrapperсценарій поставляється з мате-терміналом. Він починається mate-terminalз додаткових аргументів, перевіряючи оточення користувача.

#!/usr/bin/perl -w

my $login=0;

while ($opt = shift(@ARGV))
{
    if ($opt eq '-display')
    {
        $ENV{'DISPLAY'} = shift(@ARGV);
    }
    elsif ($opt eq '-name')
    {
        $arg = shift(@ARGV);
        push(@args, "--window-with-profile=$arg");
    }
    elsif ($opt eq '-n')
    {
        # Accept but ignore
        print STDERR "$0: to set an icon, please use -name <profile> and set a profile icon\n"
    }
    elsif ($opt eq '-T' || $opt eq '-title')
    {
        push(@args, '-t', shift(@ARGV));
    }
    elsif ($opt eq '-ls')
    {
        $login = 1;
    }
    elsif ($opt eq '+ls')
    {
        $login = 0;
    }
    elsif ($opt eq '-geometry')
    {
        $arg = shift(@ARGV);
        push(@args, "--geometry=$arg");
    }
    elsif ($opt eq '-fn')
    {
        $arg = shift(@ARGV);
        push(@args, "--font=$arg");
    }
    elsif ($opt eq '-fg')
    {
        $arg = shift(@ARGV);
        push(@args, "--foreground=$arg");
    }
    elsif ($opt eq '-bg')
    {
        $arg = shift(@ARGV);
        push(@args, "--background=$arg");
    }
    elsif ($opt eq '-tn')
    {
       $arg = shift(@ARGV);
       push(@args, "--termname=$arg");
    }
    elsif ($opt eq '-e')
    {
        $arg = shift(@ARGV);
        if (@ARGV)
        {
            push(@args, '-x', $arg, @ARGV);
            last;
        }
        else
        {
            push(@args, '-e', $arg);
        }
        last;
    }
    elsif ($opt eq '-h' || $opt eq '--help')
    {
        push(@args, '--help');
    }
}
if ($login == 1)
{
    @args = ('--login', @args);
}
exec('mate-terminal',@args);

Сенс, що тут слід помітити, є execдзвінок, який замінює цей скрипт у пам'яті.

Ось подібне запитання, на яке відповіли на сайті Unix & Linux StackExchange - https://unix.stackexchange.com/q/270929/19288

Для перенаправлення дескрипторів файлів

Ще одне поширене використання exec- перенаправлення файлових дескрипторів. stdin, stdout, stderrМожуть бути перенаправлені на файли з допомогою EXEC.

  1. Перенаправлення stdout- exec 1>fileпризведе до того, що стандартним висновком буде файл, названий fileна кінець поточного сеансу оболонки. Все, що виводиться на дисплей, буде у файлі.

  2. Перенаправлення stdin- також може використовуватися для переадресації stdinфайлу. Наприклад, якщо ви хочете виконати файл сценарію script.sh, ви можете просто перенаправити stdinфайл на файл, використовуючи exec 0<script.sh.


Добре. Згодом у "mate-terminal" з'явиться PID, який має скрипт обгортки? І чи буде використовувати пам'ять, яку використовував обгортковий скрипт? Тож обгортковий сценарій зник. Інакше два сценарії існуватимуть як окремі процеси в системі (з двома різними PID)?
mizech

@mizech так. вони використовують той самий PID
Anwar

@mizech Радий знати, що це допомогло :)
Anwar

1
Чудовий приклад, який дає зрозуміти
Zanna

Ця відповідь є частковою і пропускає одне з важливих (і типових) способів використання exec- це використання в перенаправлення дескрипторів файлів.
heemayl

9

exec Команда замінює поточний процес оболонки з вказаною командою. Зазвичай при запуску команди новий процес створюється (роздвояється). exec Команда не породжує новий процес. Натомість поточний процес перекривається новою командою. Іншими словами execкоманда виконується замість поточної оболонки без створення нового процесу.

Існує три найпоширеніших використання команди exec:

1. Заміна процесу

Приклад-1: Якщо ви відкриєте новуbashоболонку як

$ bash 

в pstreeній схоже

├─gnome-термінал
        ├─bash────bash───pstree

Попередня bashоболонка все ще є, і ви отримали нову bashоболонку. Враховуючи, що якщо ви відкриєте нову оболонку bash як,

$ exec bash

на pstreeшоу

├─gnome-термінал
        ├─bash───pstree

Тут старе bashзамінено новим. Особливо корисно вийти з декількох логінів в одній команді. Це більш безпечно і усуває шанс залишити відкритий термінал помилково. Див. Вихід із кореня та користувача за допомогою однієї команди

Приклад-2: ви можете відкрити файл як

$ exec vi filename.txt

Після завершення роботи viнемає необхідності закривати термінал окремо, оскільки оболонка вже замінена. Як тільки ви закриєте, термінал також закривається.

2. Метод перенаправлення дескрипторів файлів у скриптах оболонки

exec Команда також може бути використана в скриптах динамічно відкривати, закривати і копіювання файлових дескрипторів. Це дозволяє виконувати перенаправлення STDIN, STDERR, STDOUT та інших дескрипторів файлів до різних файлів всередині скрипту оболонки, а не рядка виклику команд. Якщо ви не вказали команду чи аргументи, ви можете вказати символи перенаправлення та дескриптори файлів для виконання цих функцій.

Скажімо, у вас є сценарій оболонки, для script.shякого потрібно мати файл журналу script.log, який ви можете використовувати execяк

LOG=/path/to/script.log
exec 1>>$LOG
exec 2>&1

що еквівалентно

./script &>> /path/to/script.log
./script >>  /path/to/script.log 2>&1

3. Створення етапів процесу за допомогою команди exec

Ви також можете скористатися командою exec для створення набору скриптів оболонки, які виконують один одного послідовно, як етапи процесу. Замість нерестування нових процесів кожен раз, коли вам потрібно перенести керування в наступний скрипт, який ви виконуєте команду exec.

У цьому випадку останнім висловом кожного етапу має бути execкоманда, яка викликає наступний етап.

Докладніше див. Про використання execкоманди в скриптах оболонки .

Примітка: Частина вище взята з цього.


1
Тільки повна відповідь (поки що).
heemayl

Я завжди використовував exec для ефективності. Якщо ви запускаєте демон з exec, вам потрібно мати лише один активний процес замість двох. Залишаючи процес збивання навколо відходів, серед іншого, пару МБ барабану.
gmatht

2

Наскільки я знаю, він також використовується для перенаправлення дескрипторів файлів (наприклад, STDOUT, STDERR, STDIN) bash-скрипту.

Так, наприклад, ви можете читати з файлу замість клавіатури, використовуючи перенаправлення STDIN і записувати у файл замість терміналу шляхом перенаправлення STDOUT (або може бути STDERR залежно від програми).


1
Ця відповідь часткова і лише доповнює цю відповідь .
heemayl
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.