Eu me aproximei disso mascarando o comando exit
com uma função; a função verifica se você está na tela e se você é o único processo filho que resta desse processo de tela.
exit() {
if [[ "$(ps -o pid= --ppid "$(ps -o ppid= -p "$$")" | wc -l)" -eq 1 ]]
then
read -p "Warning: you are in the last screen window; do you really want to exit? (y/n) "
case $REPLY in
(y*) command exit "$@" ;;
esac
else
# not within screen at all, or not within the last screen window
command exit "$@"
fi
}
Você teria que incluir essa função como parte do seu perfil (bash), por exemplo %código%. Ao iniciar a tela, (a menos que seja dito o contrário), inicie uma instância de seu $ SHELL. Esse shell será filho de um processo de tela. Ao sair de um shell filho, o código acima verifica quantos processos são filhos do processo pai do shell atual. De dentro para fora:
-
~/.bash_profile
- pede o PID pai (adicionando o$(ps -o ppid= -p "$$")
suprime a linha de cabeçalho) do processo atual (=
) -
$$
- pede a lista de PIDs (novamente sem o cabeçalho) cujo pai PID é nosso pai, então conta o número de linhas de saída
Se parece que somos o último processo filho de uma sessão de tela, ele solicita confirmação; se a resposta começar com a letra $(ps -o pid= --ppid ... | wc -l)
, a função chamará o comando "real" y
para sair do shell; caso contrário, a função termina sem sair do shell.
Se não formos o último processo filho, a função continua e sai normalmente.
Algumas notas foram desenvolvidas:
-
Inicialmente tive mais testes na linha
exit
para ver se estamos em uma sessão de tela, inclusive ver seif
está preenchida e seSTY
é maior que 1. a tela define STY e O bash irá incrementar o SHLVL, mas nenhuma dessas variáveis é somente leitura, então o teste não é strong o suficiente para ser útil.
A tela -
também define uma variável
SHLVL
, mas a verificação deWINDOW
não é confiável; você pode abrir duas janelas e fechar a janela0
, deixando a janela0
como a última janela. -
Digitar EOF (normalmente Controle + D ) fará com que o shell saia imediatamente, ignorando esta função do invólucro. A melhor solução que eu sei seria definir a variável
1
para algum valor diferente de zero; Isso só vai atrasar a inevitável saída da Shell.
Como eu usei muitos recursos específicos bash- (e GNU procutils-) acima, eu também quis fornecer uma solução em conformidade com POSIX. A linha IGNOREEOF
muda para um esquema ps
para capturar o número de processos com um PID pai específico. A outra mudança é re-trabalhar o ps ... | grep -c
em um prompt separado e read -p
.
exit() {
parent="$(ps -o ppid= -p $$)"
if [ "$( ps -eo ppid= | grep -c "^ *${parent}\$" )" -eq 1 ]
then
printf "Warning: you are in the last screen window; do you really want to exit? (y/n) "
read REPLY
case $REPLY in
(y*) command exit "$@" ;;
esac
else
# not within screen at all, or not within the last screen window
command exit "$@"
fi
}