Processos em background sem “&”

24

Digamos que você tenha iniciado um novo aplicativo no Linux (como um editor de texto, etc.), mas esqueceu de usar o "&". Que comando (s) você usaria para fazer com que o processo fosse executado em segundo plano, enquanto NÃO tivesse que FECHAR essa aplicação? Dessa forma, você pode ter os dois processos abertos e trabalhando separadamente (por exemplo, o terminal de linha de comando usado para criar o processo e o processo, como um editor de texto, ainda em execução.?

    
por D0uble7 24.08.2016 / 23:21

4 respostas

44

Na janela do terminal, você normalmente digitaria Controle + Z para "suspender" o processo e depois usaria o comando bg para "background".

por exemplo, com um comando sleep

$ /bin/sleep 1000
^Z[1] + Stopped                  /bin/sleep 1000
$ bg
[1]     /bin/sleep 1000&
$ jobs
[1] +  Running                 /bin/sleep 1000
$ 

Podemos ver que o processo está em execução e ainda tenho minha linha de comando.

    
por 24.08.2016 / 23:24
14

Ctrl + Z é a maneira de fazer isso, mas apenas por completude: a pergunta pede por "comando", e isso seria (de outro terminal):

kill -STOP pid_of_the_running_applications

e depois, claro,

bg

do terminal de aplicativos.

    
por 25.08.2016 / 10:36
11

No Bash:

Ctrl + Z e, em seguida, bg .

Agora, execute jobs e veja o resultado.

    
por 24.08.2016 / 23:23
1

Como uma medida preventiva para a inconveniência de ter que pressionar CTRL - z , você poderia fazer um script wrapper para o seu editor ao qual executaria seu editor em segundo plano . Dessa forma, você não precisaria se preocupar em lembrar de iniciá-lo explicitamente no plano de fundo:

    #!/bin/sh

    EDITOR="emacs" # or whatever

    if [ -z "${DISPLAY}" ]; then
      ${EDITOR} "$@"
    else
      ${EDITOR} "$@" &
    fi

Acima nós primeiro tentamos determinar se você tem o servidor X disponível e só então rodamos o editor em segundo plano (se não, muitos editores Unix irão usar o seu terminal e você não quer rodar o editor como um processo em segundo plano este caso). Ele irá passar todos os argumentos para o seu editor de escolha na íntegra ( "$@" ) exatamente como você forneceu para o script wrapper.

Quanto ao comando que está faltando ... De acordo com minha experimentação básica, para programas GUI que não envolvam terminal, pode ser tão simples quanto enviar primeiro SIGSTOP e, em seguida, SIGCONT ao processo de primeiro plano (usando kill comando se você usar o shell script para implementar isso). É claro que você precisaria executá-lo em outra janela / guia de terminal, e a dificuldade seria encontrar de forma conveniente e genérica o PID para o qual deseja enviar seu sinal. Você poderia, por padrão, enviar os dois sinais para todos os processos do nome dado (padronizando para o seu editor favorito e permitindo também usar os PIDs como argumentos):

    #!/bin/sh

    EDITOR=emacs # whatever

    stop_cont_prog()
    {
      case "$1" in
        # begin with number is considered PID - this is not good 
        # enough to be taken seriously...
        [1-9]*) kill -SIGSTOP "$1"; kill -SIGCONT "$2";;
        *)      killall -SIGSTOP "$1"; killall -SIGCONT "$2";;
      esac
    }

    if [ -n "$1" ]; then
      for prog in "$@"; do stop_cont_prog "$1"; done
    else  
      stop_cont_prog "${EDITOR}"
    fi

Este método me deu corretamente minhas guias de terminal depois de executar (vários) emacs comandos em segundo plano. Mas o processo do emacs em execução no terminal não foi restaurado corretamente devido ao controle do trabalho do shell ou à confusão na configuração do terminal. Então, esse método se beneficiaria de alguma sofisticação.

O SIGSTOP é exatamente o que é enviado para o processo em primeiro plano quando você pressiona (por padrões comuns) CTRL - z . Consulte stty -a output

$ stty -a
speed 38400 baud; rows 50; columns 200; line = 0;
intr = ^C; [...] start = ^Q; stop = ^S; susp = ^Z; [...]
[...]

(saída abreviada) e stty página de manual:

   susp CHAR
          CHAR will send a terminal stop signal

Os processos parados usando o sinal SIGSTOP podem ser reiniciados enviando SIGCONT . Normalmente, é a lógica de controle da tarefa do shell que enviará o SIGCONT e cuidará de outras manipulações necessárias envolvidas com os comandos fg e bg que ignoramos.

    
por 26.08.2016 / 09:14

Tags