Meu problema é que o shell Bash para de mostrar os caracteres digitados nele. Ele lê os comandos embora.
Já me deparei com esse problema algumas vezes e não entendo o que o causa. Eu sei como resolver isso, mas eu realmente não gosto quando estou "vodu" minha maneira de sair dos problemas.
Descreverei as duas maneiras pelas quais me deparei com esse problema:
Estou executando um determinado processo, http://pythonpaste.org/script/ e, às vezes, quando eu paro isso ou quebra o controle, é devolvido ao shell. Quando eu digito comandos no shell, os caracteres digitados não aparecem. Quando pressiono enter, os comandos são enviados. Então, por exemplo:
- Eu digito "ls"
- Só vejo um prompt vazio e nada mais
- Pressiono enter e recebo uma lista dos arquivos, em outras palavras: o comando é executado
- quando eu dou o comando "reset" o shell começa a funcionar normalmente novamente
A segunda maneira que isso acontece é quando eu dou um comando como este:
$ grep foo * -l | xargs vim
Uso o grep para encontrar arquivos que tenham um determinado padrão e, em seguida, desejo abrir todos os arquivos resultantes do grep. Isso funciona como um encanto (embora não tão rápido quanto eu esperava). Mas quando saio do Vim, meu shell para de mostrar os caracteres digitados nele. Um comando de redefinição resolve o problema.
Meu palpite é que ambos os problemas têm uma razão subjacente, mas estou meio que perplexo em como ou qual é essa razão.
A pesquisa desse problema é problemática, porque a descrição é meio vaga e não possui termos de pesquisa rígidos.
Editar
Dando o
stty --all
comando conforme a solicitação de John S. Gruber deu a seguinte saída (espaço em branco editado para facilitar a leitura)
speed 0 baud;
rows 53;
columns 186;
line = 0;
intr = <undef>;
quit = <undef>;
erase = <undef>;
kill = <undef>;
eof = <undef>;
eol = <undef>;
eol2 = <undef>;
swtch = <undef>;
start = <undef>;
stop = <undef>;
susp = <undef>;
rprnt = <undef>;
werase = <undef>;
lnext = <undef>;
flush = <undef>;
min = 0;
time = 0;
-parenb
-parodd cs8
-hupcl
-cstopb cread
-clocal
-crtscts
-ignbrk
-brkint
-ignpar
-parmrk
-inpck
-istrip
-inlcr
-igncr
-icrnl
-ixon
-ixoff
-iuclc
-ixany
-imaxbel
-iutf8
-opost
-olcuc
-ocrnl
-onlcr
-onocr
-onlret
-ofill
-ofdel nl0 cr0 tab0 bs0 vt0 ff0
-isig
-icanon
-iexten
-echo
-echoe
-echok
-echonl
-noflsh
-xcase
-tostop
-echoprt
-echoctl
-echoke
fonte
stty --all
e coloque os resultados em sua pergunta. Eco é uma característica tty que está sendo desativada. O Vim fará isso enquanto estiver em execução e também colocará o terminal no modo bruto. Ao sair, deve redefinir as configurações do terminal. Quando o vim está sendo executado, você não deseja repetir oi
comando que coloca o editor no modo de inserção, por exemplo. Essas configurações informam ao dispositivo tty como ele deve processar o que você digita. Enquanto vim está em execução que cuida de ecoando o que deve ser feito eco, etc.stty --all
à minha pergunta. Desde já, obrigado!Respostas:
Ao executar um shell ou a maioria dos programas em um shell, qualquer coisa que você digitar é repetida no terminal do usuário pelo subsistema tty do kernel. Também há outro tratamento especial para apagar caracteres, Ctrl + R, Ctrl + Z e assim por diante.
Certos programas (em particular os editores) que são executados a partir de uma linha de comando não precisam ou querem isso. Por esse motivo, eles sinalizam o kernel com uma chamada IOCTL no dispositivo tty (terminal) de que não desejam esse comportamento. Eles também não querem que caracteres especiais façam coisas especiais. Em vez disso, eles solicitam ao kernel um modo "bruto". Em particular, o editor como o vim desativa várias "configurações de eco". Tudo isso se aplica aos terminais reais nas linhas seriais de um computador, ou aos terminais virtuais em Alt + Ctrl + F1, ou aos terminais realmente virtuais que você obtém ao executar algo como o gnome-terminal sob uma GUI.
Esses programas devem redefinir qualquer modo que eles alterem no tty virtual que estão usando antes de sair, digitando um comando quit editor ou recebendo um sinal (de Control + C), por exemplo.
Se eles não conseguirem fazer isso corretamente, o tty será deixado no estado engraçado que você descobriu. Como os programas podem falhar ao redefinir o terminal, o
reset
comando foi gravado para permitir que o usuário se recupere.Presumo que a interrupção esteja mexendo com o software python que você está executando. Eu acho que esse programa não está tendo a chance de redefinir o terminal ou simplesmente não está fazendo isso.
No caso do vim, quando executo seu exemplo, recebo o mesmo comportamento que você descreve. Também vejo a mensagem "Vim: Aviso: a entrada não é de um terminal" (desaparece quando você redefine). Isso ocorre porque o vim não é iniciado normalmente a partir do shell. Em vez disso, os comandos 'grep' e 'xargs' têm usado a entrada padrão, normalmente ocupada pelo tty, com a finalidade de passar os nomes de arquivo de
grep
ttoxargs
.Em sua saída publicada
stty -a
, podemos ver "-echo", também confirmando que este é o problema. Se você matasse o vim de forma que ele não pudesse lidar com o sinal normalmente, provavelmente veria o mesmo problema.O problema é descrito em outro lugar em https://stackoverflow.com/questions/3852616/xargs-with-command-that-open-editor-leaves-shell-in-weird-state .
Uma solução para o caso vim é evitar xargs e usar:
Aqui, a lista de arquivos é construída pelo shell, como havia sido o xargs, mas o shell está chamando vim, que está diretamente conectado ao tty. Há uma mensagem de aviso enviada ao arquivo de saída de erro e o vim define e redefine as configurações tty corretamente.
Mais referências aqui , e outra interessante aqui . Outra solução interessante é fornecida em uma resposta para https://stackoverflow.com/questions/8228831/why-does-locate-filename-xargs-vim-cause-strange-terminal-behaviour .
fonte
grep foo * -l | vim -
sem problemas. Então, acho que o problema não está no grep e no xargs, mas apenas no xargs. Você concordaria?git add -p
!Iniciava um novo usuário no sistema (refiro-me a um novo usuário limpo e fazia o login lá) e veria se o problema estava lá. Caso contrário, é o seu terminal ou o seu X11.
fonte
grep foo * -l | xargs vim
comando O problema ainda existe. Não entendo exatamente como minhas configurações do X11 podem influenciar a reação do meu terminal. Você poderia elaborar sobre isso? Obrigado!