força a saída para entrada (buffer) como “\ 033 [6n” em um script

1

Eu tentei usar pipes e redirecionamentos para que a saída (programa C ou scripts) acabasse no buffer de entrada, da mesma forma que o printf "3[6n" , mas sem resultados positivos.

Alguém sabe como isso é possível:

  1. uma linha de comando
  2. em um script de shell
  3. código C

A saída de tubulação _cmd_ > /dev/stdin e o código C fprintf(stdin, "blah\n"); não têm efeito mensurável.

Nota: Eu não quero "canalizar" a entrada para outro comando, eu quero "injetar" caracteres no "buffer de teclado" (por assim dizer).

    
por Paul Wratt 24.11.2017 / 01:28

2 respostas

0

writevt /dev/tty# text , pelo menos no Linux, talvez BSD e Unix, atualmente parte do pacote console-tools . O usuário deve ter privilégios write para o VT. Especificamente, a resposta completa e correta ao OP é:

writevt 'tty' "'_cmds_'"

Esta questão mostra a falta de profundidade de conhecimento sobre os sistemas operacionais de base pela comunidade do StackExchange como um todo. writevt é muito antigo, é um comando base instalado em sistemas 99% (do Linux). Até junho de 2002, não havia man page ou mantenedor para isso no Debian, o que pode explicar por que muitas pessoas não sabem sobre isso, mesmo que isso tenha acontecido 15 anos atrás. No entanto, mesmo no Kali Linux (que tem tudo ), na maioria das vezes ele não está listado nos comandos disponíveis , mesmo que esteja lá desde o início começar.

    
por 05.12.2017 / 05:04
0

Editar: A resposta curta era /dev/uinput , agora é TIOCSTI (veja o final da postagem)

Esta é a resposta até agora e para abordar os comentários:

man ioctl_tty Eu não tenho, mas uma pesquisa de TIOCSTI na fonte do kernel (via FreeElectrons mostrará tiocsti "caractere de entrada falso", que usa um contexto tty_struct .

O aplicativo em questão está sendo executado o tempo todo, de forma interativa, para que os canais e redirecionamentos não possam ser usados. Pode shell sair para o script, no entanto, ao contrário de um monte de outros aplicativos semelhantes, não permite, nem permite, capturar os resultados, permitindo apenas stdin & stdout para fazer suas coisas de acordo com o normal.

Para o futuro previsível, não há chance de mudar isso, não é minha aplicação. No entanto, consegui cortar os resultados de "3[6n" , que foram injetados no buffer de teclado pelo kernel através de tty_insert_flip_char & tty_schedule_flip in src/drivers/tty/tty_buffer.c , que usa um contexto tty_port .

Se a memória serve, antes da estrutura do arquivo FD ser alterada, quando havia apenas 4 descritores de arquivo, pode ter sido possível conseguir isso. Hoje em dia, embora você possa escrever para /dev/stdin ou /proc/self/fd/0 , eles estão conectados a /dev/tty# e qualquer coisa gravada em um dispositivo TTY terminará na tela ( /dev/stdout ). O kernel parece ignorar a rota do descritor de arquivo ao usar TTY's, observe que as funções flip se referem a ele como uma porta .

Qualquer aplicativo userland não tem acesso a nenhuma dessas funções do kernel. No X-Windows, é possível usar xvkbd e xdotool ou xte , mas este aplicativo está sendo usado no console do Linux (VT).

A resposta (quase) real:

Embora /dev/uinput não tenha privilégios de usuário (na maioria dos sistemas), sudo um script que printf all arguments funcionará.

Como alternativa, o teclado evento também funcionará, pois todos os usuários têm acesso a ele, mas ele muda por inicialização e por sistema (o meu normalmente é /dev/input/event0 , mas nem sempre).

Após mais pesquisas, nenhuma dessas abordagens é prática, especialmente para scripts. A coisa que precisamos entender sobre o que precisa ser feito é que apenas queremos apresentar texto no buffer de entrada, não "simular um pressionamento de tecla" (que é como os dispositivos acima funcionam).

A resposta real (mais prática):

Uma pergunta fora do local remetida a uma resposta no stackexchange, de 2011 ( aqui ). Usa TIOCSTI . Depois de rever o exemplo Perl novamente, também pode ser prático para o script, onde um aplicativo não é fornecido.

perl -le 'require "sys/ioctl.ph";
      ioctl(STDIN, &TIOCSTI, $_) for split "", join " ", @ARGV
     ' '_cmds_'

No entanto, também faz eco na tela. Após muitas horas de pesquisa e experimentação, o seguinte é prático em um script ou na linha de comando:

stty -echo; perl -le 'require "sys/ioctl.ph"; ioctl(STDIN, &TIOCSTI, $_) for split "", join " ", @ARGV ' '_cmds_' ;stty echo

Observação: embora TIOCSTI tenha sido revogado no BSD (novembro de 2017), aparentemente, os desenvolvedores do Kernel do Linux estão na mente oposto, categoricamente recusando-se a revogá-lo

    
por 24.11.2017 / 12:09