Debian SSH - O terminal de redimensionamento não se registra no bash

10

Recentemente, reinstalamos nosso servidor devido a uma falha no disco, e agora estamos com um problema no redimensionamento de terminais. Nós instalamos o Debian 6.0.6.

Sintomas

Quando você redimensiona um terminal, nenhum aplicativo baseado em ncurses (testado: ytalk, irssi, screen, tmux, alguns dos aplicativos de exemplo ncurses) parece redimensionar corretamente. A tela normalmente fica em branco. Forçar um redesenho no aplicativo será redesenhado usando o tamanho antigo do terminal.

Ao redimensionar uma janela em um prompt bash (4.1.5 (1)), as variáveis COLUMNS e LINES nunca são atualizadas.

Diagnóstico

Tentando capturar o SIGWINCH no bash, parece que nunca está sendo recebido. Isso foi testado com:

trap 'touch /home/user/sigwinch' SIGWINCH
trap 'touch /home/user/sigusr1' SIGUSR1
kill -s SIGWINCH $$
kill -s SIGUSR1 $$

Qual deve ter criado os dois arquivos em meu diretório pessoal. Apenas criou /home/user/sigusr1 .

Tentar kill -s SIGWINCH $$ não causa uma atualização das variáveis $ COLUMNS / $ LINES.

A ativação de checkwinsize ( shopt -s checkwinsize ) fará com que o bash atualize $ COLUMNS / $ LINES ao retornar de qualquer aplicativo (conforme esperado). Isso leva ao seguinte após o redimensionamento de um terminal com checkwinsize ativado:

$ echo $COLUMNS ; ls > /dev/null ; echo $COLUMNS
72
107

Alterar meu shell de login para algo como tcsh e tentar redimensionar o terminal funciona como esperado, assim como o bash em outras caixas que testei.

Eu tentei remover meu .bashrc e ele não fez nada. Esse problema está ocorrendo para vários outros usuários com diferentes configurações bash no PuTTY e em algum tipo de terminal do tipo rxvt de uma caixa Linux.

strace

Eu corri strace no bash e tentei redimensionar o terminal, nada veio (ele permaneceu bloqueado em uma chamada read imediatamente após a impressão do prompt).

Eu acertei o retorno em uma linha vazia, e o bash fez um monte de coisas. A saída que eu acredito ser relevante é: ( full strace )

1: rt_sigprocmask(SIG_SETMASK, [WINCH], NULL, 8) = 0
2: rt_sigaction(SIGWINCH, {0x80e2c20, [], SA_RESTART}, {0x809c310, [], 0}, 8) = 0
3: rt_sigprocmask(SIG_BLOCK, [INT], [WINCH], 8) = 0
4: write(2, "aa:~$ ", 6)                   = 6
5: rt_sigprocmask(SIG_SETMASK, [WINCH], NULL, 8) = 0
6: rt_sigprocmask(SIG_BLOCK, NULL, [WINCH], 8) = 0
7: read(0,

O que mostra bash, no meu entendimento: (Eu poderia estar horrivelmente entendendo mal isso. Estou fora do meu elemento aqui.)

1: Disabling delivery of the SIGWINCH signal, when previously it was allowed.
2: Registering a handler for the SIGWINCH signal.
3: Masking some other combination of signals. As evidenced by line 5, this does not include SIGWINCH.
4: Printing the prompt.
5: Masking SIGWINCH, where previously nothing was blocked.
6: Masking the "union of null and SIGWINCH" which, to my understanding, would result in SIGWINCH being masked.
7: Waiting on input.

Este mesmo strace executado em uma caixa sem esses problemas (Ubuntu, bash 4.2.24 (1)) resultou em:

1: rt_sigprocmask(SIG_SETMASK, [], NULL, 8) = 0
2: rt_sigaction(SIGWINCH, {0x49e320, [], SA_RESTORER|SA_RESTART, 0x7f7ef49f64c0}, {0x457880, [], SA_RESTORER, 0x7f7ef49f64c0}, 8) = 0
3: rt_sigprocmask(SIG_BLOCK, [INT], [], 8) = 0
4: write(2, "aaaaaaa:~$ ", 11)             = 11
5: rt_sigprocmask(SIG_SETMASK, [], NULL, 8) = 0
6: rt_sigprocmask(SIG_BLOCK, NULL, [], 8)  = 0
7: read(0,

Pergunta

O que diabos está acontecendo e por que minha festa está quebrada? : (

Eu estou supondo que provavelmente há apenas uma opção em algum lugar que padrão para algo inesperado, mas horas no Google não apareceram nada.

Qualquer ajuda e / ou ponteiros são muito apreciados. Isso é realmente frustrante.

Obrigado.

    
por NuclearDog 26.11.2012 / 21:51

2 respostas

10

Alguma coisa estava me incomodando sobre a saída da strace. Ou seja, parecia que quando o bash começou, parecia que já tinha o SIGWINCH mascarado. Não podia ter certeza, não entendia metade do que estava cuspindo, mas certamente valia a pena alguma exploração neste momento.

Eu corri strace -o strace_file bash -l de um shell tcsh, onde o problema não estava presente. bash nunca mascarou o SIGWINCH. Quando estava mascarando, era apenas porque estava tentando restaurar a máscara anterior. Então, de onde vem a máscara inicial?

Mais um pouco de tempo no Google e uma nova ideia e achei este post que mencionou que o aptitude pode algumas vezes fazer com que o sshd seja iniciado com o SIGWINCH mascarado, e que ele seja então herdado por todos os processos gerados diretamente no shell.

Eu tentei ps axwwws (todos, saída separada, sinais largos). Ele mostrou vários dos processos sshd gerados pelo SIGWINCH mascarados.

O processo servidor / escuta (o próprio sshd) não. Nem os processos que hospedavam conexões que usavam o tcsh. Essa parte é confusa para mim. Eu estou supondo (mais uma vez, sabendo muito pouco sobre isso) que a máscara de sinal é ampla no grupo de processos ou algo assim, tcsh estava redefinindo isso no início, e isso também estava afetando o ssh.

Então, por um capricho, eu me conectei com o tcsh (para obter um termo limpo sem máscara SIGWINCH), reiniciei o ssh, mudei meu shell de volta para o bash ... E deu certo! Tudo voltou ao normal!

Tanto quanto eu saiba, o aptitude não foi executado nesta caixa, e o ssh foi reiniciado algumas vezes para mudanças na configuração. Em algum lugar ao longo da linha, a máscara invadiu e infectou tudo como uma doença grave.

Para reconhecer o mesmo problema, execute ps axwwws | grep sshd e procure por processos sshd com a segunda coluna longa ( BLOCKED ) configurada como 0x8000000. Isso é SIGWINCH. Algo como:

   0 26425 0000000000000000 0000000008000000 0000000000001000 0000000180004003 Ss   ?          0:00 sshd: aa [priv]
1000 26430 0000000000000000 0000000008000000 0000000000001000 0000000180010000 S    ?          0:02 sshd: aa@pts/24

Para corrigir (possivelmente não é a melhor solução, funcionou para mim):

$ sudo apt-get install tcsh
[snip]
$ chsh -s /bin/tcsh
[connect in with a new connection, leave the old one open in case of any issues with tcsh]
$ sudo /etc/init.d/ssh restart

E está consertado.

Felicidades!

    
por 27.11.2012 / 20:08
1

Tente isso. Fazer

bash$ shopt -s checkwinsize

no seu shell, em seguida, redimensione sua janela de terminal.

    
por 30.09.2017 / 16:08