Часто виникає плутанина між форксуванням процесу та виконанням.
Коли ви робите підказки bashоболонки.
$ sh -c 'exec env ps'
Процес P1 видачі цього $підказка в даний час працює bashкодом. Цей bashкод розщеплює новий процес P2, який виконує, /bin/shякий потім виконує /usr/bin/env, який потім виконує /bin/ps.
Таким чином , P2 , в свою чергу виконується код bash, sh, envі ps.
ps(або будь-яка інша команда, як скрипт, яку ми б замість цього використали тут) не може знати, що вона виконується envкомандою.
Все, що він може зробити, - це з’ясувати, що таке його ідентифікатор батьківського процесу, який у цьому випадку буде P1 або 1якщо P1 загинув в інтервалі, або в Linux інший процес, який був призначений як підреактор замість 1.
Потім він може запитувати систему для того, яку команду цей процес виконує в даний момент (як, наприклад, readlink /proc/<pid>/exeв Linux) або які аргументи, де передано останню команду, яку вона виконувала (наприклад, з ps -o args= -p <pid>).
Якщо ви хочете, щоб ваш скрипт знав, на що він викликав, надійним способом було б дозволити заявнику сказати це. Це можна зробити, наприклад, за допомогою змінної середовища. Наприклад, script1можна записати так:
#! /bin/sh -
INVOKER=$0 script2 &
І script2:
#! /bin/sh -
printf '%s\n' "I was invoked by $INVOKER"
# and in this case, we'll probably find the parent process is 1
# (if not now, at least one second later) as script1 exited just after
# invoking script2:
ps -fp "$$"
sleep 1
ps -fp "$$"
exit
$INVOKER( як правило ) міститиме шлях до script1. У деяких випадках це може бути відносний шлях, і шлях буде відносно поточного робочого каталогу на початок часу script1. Тож якщо script1змінити поточний робочий каталог перед викликом script2, script2отримає неправильну інформацію щодо того, що його викликало. Тому може бути бажано переконатися, що він $INVOKERмістить абсолютний шлях (бажано збереження базового імені), наприклад, написавши script1:
#! /bin/sh -
mypath=$(
mydir=$(dirname -- "$0") &&
cd -P -- "$mydir" &&
pwd -P) && mypath=$mypath/$(basename -- "$0") || mypath=$0
... some code possibly changing the current working directory
INVOKER=$mypath script2
В оболонках POSIX $PPIDміститиметься під батьківського процесу, який виконував оболонку під час ініціалізації цієї оболонки. Після цього, як видно вище, батьківський процес може змінитися, якщо процес ідентифікації $PPIDзагине.
zshв zsh/systemмодулі, може запитувати поточний батьківський під поточної (під-) оболонки за допомогою $sysparams[ppid]. В оболонках POSIX ви можете отримати поточний ppid процесу, який виконував інтерпретатор (якщо припустити, що він все ще працює) ps -o ppid= -p "$$". З bash, ви можете отримати ppid поточної (під-) оболонки за допомогою ps -o ppid= -p "$BASHPID".