Debian SSH - Il ridimensionamento del terminale non si registra con bash


11

Recentemente abbiamo reinstallato il nostro server a causa di un errore del disco e ora abbiamo un problema con il ridimensionamento dei terminali. Abbiamo installato Debian 6.0.6.

Sintomi

Quando si ridimensiona un terminale, nessuna app basata su ncurses (testata: ytalk, irssi, screen, tmux, alcune delle applicazioni di esempio ncurses) sembra ridimensionare correttamente. Lo schermo in genere finisce vuoto. Forzare un ridisegno nell'applicazione verrà ridisegnato utilizzando le dimensioni del vecchio terminale.

Quando si ridimensiona una finestra al prompt bash (4.1.5 (1)), le variabili COLONNE e LINEE non vengono mai aggiornate.

Diagnostica

Tentando di intrappolare SIGWINCH in bash, sembra che non venga mai ricevuto. Questo è stato testato con:

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

Che avrebbe dovuto creare entrambi i file nella mia home directory. Ha solo creato /home/user/sigusr1.

Provare a kill -s SIGWINCH $$non provoca un aggiornamento delle variabili $ COLUMNS / $ LINES.

Abilitando checkwinsize( shopt -s checkwinsize), bash aggiornerà $ COLUMNS / $ LINES al ritorno da qualsiasi applicazione (come previsto). Ciò porta a quanto segue dopo il ridimensionamento di un terminale con checkwinsizeabilitato:

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

Cambiare la mia shell di login in qualcosa come tcsh e tentare di ridimensionare il terminale funziona come previsto, così come bash su altre caselle che ho testato.

Ho provato a rimuovere il mio .bashrc e non ha fatto nulla. Questo problema si verifica per molti altri utenti con diverse configurazioni bash sia in PuTTY che in una sorta di terminale di tipo rxvt da una scatola Linux.

strace

Ho eseguito strace su bash e ho provato a ridimensionare il terminale, non è successo nulla (è rimasto bloccato su una readchiamata immediatamente dopo aver stampato il prompt).

Ho colpito return su una riga vuota e bash ha fatto un sacco di cose. L'output che ritengo rilevante è: ( 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,

Il che dimostra bash, per la mia comprensione: (Potrei essere terribilmente frainteso questo. Sono molto fuori dal mio elemento qui.)

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.

La stessa sequenza eseguita su una scatola senza questi problemi (Ubuntu, bash 4.2.24 (1)) ha comportato:

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,

Domanda

Cosa diavolo sta succedendo e perché la mia bash è rotta? :(

Immagino che ci sia probabilmente solo un'opzione da qualche parte che è passata per impostazione predefinita a qualcosa di inaspettato, ma ore su Google non hanno prodotto nulla.

Qualsiasi aiuto e / o suggerimenti sono molto apprezzati. Questo è davvero frustrante.

Grazie.


Non sei il primo: lists.gnu.org/archive/html/bug-bash/2007-01/msg00084.html Se a exec bashmano (quindi non è più una shell di login) si comporta ancora male? In caso contrario, che dire exec bash -l(quindi è una shell di accesso)? Se è così, allora c'è qualcosa che non va nei tuoi script di login ( /etc/profile /etc/profile.d/ ~/.bash_profile ~/.profile), ma non so nemmeno cosa dirti di cercare che possa dire alla shell di non farlo SIGWINCH.
DerfK,

Entrambi exec bashed exec bash -lesibiscono lo stesso comportamento. Suppongo sia una piccola consolazione che non sono solo in questo. Sono profondamente confuso su ciò che potrebbe causare questo, però. Il colo ha installato un'installazione minima da un'immagine Debian appena scaricata. Dovrò provare a installare localmente e vedere se ci sono problemi e (supponendo che nessuno, dal momento che ciò non sembra accadere per altre persone), iniziare a confrontare con il sistema in esecuzione.
Cane nucleare

Ho fatto una nuova installazione in una macchina virtuale, generato un elenco di somme md5 di tutti i file in / etc e / usr e confrontato con il sistema rotto. A colpo d'occhio, non riesco a vedere nulla ovviamente sbagliato. /etc/bash.bashrce tutti i file /etc/profilee /etc/profile.drimangono invariati rispetto a un'installazione pulita. Ho scaricato bash source ( apt-get source bash) e sto giocando con vari argomenti ./configureper cercare di restringere il problema prima di scavare nel sorgente.
Cane nucleare

Ho compilato bash meno tutte le patch di Debian --disable-readline --enable-minimal-config --disable-job-control, ho eseguito uno strace per vedere quali file fosse open, ho rinominato tutti quei file, quindi ho effettuato nuovamente l'accesso. Stesso problema. Ho decisamente escluso qualsiasi cambiamento di configurazione con bash stesso.
Cane nucleare

Ho replicato lo stesso problema con bash 3.2, 4.1 e 4.2 compilato da fonti recuperate direttamente da GNU. Non sono stato in grado di compilare 4.2 senza controllo del lavoro e con una configurazione minima a causa di alcuni bug (segnalati al team di bash). Dato che ciò si verifica con diverse versioni di bash, sto iniziando a credere che l'errore potrebbe risiedere in una delle librerie da cui dipende. Passando a quello.
Cane nucleare

Risposte:


11

Qualcosa mi aveva infastidito per l'output di strace. Vale a dire che sembrava che quando iniziò Bash, sembrava che avesse già mascherato SIGWINCH. Non potevo essere sicuro, non capivo la metà di ciò che stava sputando, ma a questo punto valeva sicuramente la pena di essere esplorato.

Sono corso strace -o strace_file bash -lda una shell tcsh, in cui il problema non era presente. bash non ha mai mascherato SIGWINCH. Quando lo stava mascherando, era solo perché stava tentando di ripristinare la maschera precedente. Quindi da dove veniva la maschera iniziale?

Ancora un po 'di tempo su Google e una mente nuova e ho trovato questo post in cui si diceva che l'attitudine a volte può causare l'avvio di sshd con SIGWINCH mascherato e che verrà ereditato da tutti i processi generati direttamente nella shell.

Ho provato ps axwwws(tutto, staccato, uscita ampia, segnali). Ha mostrato che molti dei processi sshd generati avevano SIGWINCH mascherato.

Il processo server / ascolto (sshd stesso) no. Né i processi che ospitavano connessioni che utilizzavano tcsh. Quella parte mi confonde. Sto indovinando (ancora una volta, sapendo molto poco di tutto ciò) che la maschera di segnale è larga dal gruppo di processo o qualcosa del genere, tcsh la stava reimpostando all'avvio, e questo stava influenzando anche ssh.

Quindi, per un capriccio, mi sono collegato a tcsh (per ottenere un termine pulito senza maschera SIGWINCH), ho riavviato ssh, ho cambiato la mia shell di nuovo in bash ... E ha funzionato! Tutto è tornato alla normalità!

Per quanto ne so, aptitude non è stato eseguito su questa casella e ssh è stato riavviato alcune volte per modifiche alla configurazione. Da qualche parte lungo la linea, però, la maschera si fece strada e infettò tutto come una brutta malattia.

Per riconoscere lo stesso problema, esegui ps axwwws | grep sshde cerca i processi sshd con la seconda colonna lunga ( BLOCKED) che ha impostato 0x8000000. Questo è SIGWINCH. Qualcosa di simile a:

   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

Per risolverlo (forse non la soluzione migliore, ha funzionato per me):

$ 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

Ed è stato risolto.

Saluti!


1

Prova questo. Fare

bash$ shopt -s checkwinsize

nella tua shell, quindi ridimensiona la finestra del tuo terminale.


2
Benvenuti in ServerFault. Hai notato che l'utente aveva già risolto questo problema anni fa?
pulcini,

1
Mi è sembrata una soluzione alternativa usando tcsh invece di bash.
gjvc,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.