Como posso obter o pid de um subshell?
Por exemplo:
$ echo $$
16808
Isso não funciona, porque o shell original se expande $$
:
$ ( echo $$ )
16808
Por que as aspas simples não funcionam? Depois que o shell original remove as aspas simples, o subshell não se expande $$
por si só?
$ ( echo '$$' )
$$
Por que também eval
não funciona? É eval
executado pelo subshell? Por que isso me fornece o PID do shell original?
$ ( eval echo '$$' )
16808
Obrigado.
$$
expansão" vs. "pid diferente no subshell").Respostas:
Além do
bash
's$BASHPID
, você pode fazê-lo de forma portável com:Exemplo:
Você pode transformá-lo em uma função:
Observe que alguns shells (por exemplo,
zsh
ouksh93
) NÃO iniciam um subprocesso para cada subshell criado com(...)
; nesse caso,$pid
pode acabar sendo o mesmo que$$
, o que é certo, porque esse foi o nome do PID do processogetpid
.fonte
ksh93
, por exemplo.(...)
exemplo que pode não gerar um processo separado, como ocorre embash
.zsh
ouyash
otimizam umfork()
para o último comando em um subshell. Eles podem até otimizar a bifurcação para o subshell se esse for o último comando de um script para que vocêgetpid
possa até relatar o pai$$
. Você pode definirgetpid
como:getpid(){ sh -c 'echo "$PPID"'; return; }
para desativar evitar o problema.exec
ou sem essa otimização, osh -c ...
processo será um neto, em vez de um filho do processo em que uma$(...)
substituição de comando é usada, e$PPID
será o pid do$(...)
subshell. É exatamente o que acontece no exemploset -E
+trap ERR
bash acima.test "$1"
testa se$1
é uma string vazia ou não - uma maneira rápida e suja de testar se essa função recebeu umvarname
argumento para atribuir o pid ou não; usar uma função não era a idéia mais brilhante em primeiro lugar.Do manual:
Relacionado:
fonte
$$
em subcascas.$BASHPID
em uma variável e usá-lo no subshell. Existe$PPID
, mas esse é o PID pai do shell no mesmo sentido que$$
o PID do shell (não é redefinido em um subshell). Não há$BASHPPID
variável.