bash: ¿Existe alguna forma de invocar comandos de vinculación (por ejemplo, redibujar la línea actual) mediante programación?

bash: ¿Existe alguna forma de invocar comandos de vinculación (por ejemplo, redibujar la línea actual) mediante programación?

He encontrado varias explicaciones sobre cómo asignar redraw-current-lineuna pulsación de tecla usando bind, pero me gustaría volver a dibujar el mensaje por otras razones (por ejemplo, temporizador, trabajo en segundo plano), sin que el usuario ingrese una pulsación de tecla. Supuse que esto sería fácil pero no encuentro nada. ¡Gracias!

Respuesta1

Tuve el mismo problema pero no encontré nada satisfactorio, así que aquí hay algunas soluciones.

${PS1@P}

En las versiones más nuevas de bash, puede imprimir el mensaje usted mismo con echo "${PS1@P}". La ${var@P}forma de expansión de variables significa expandir los escapes rápidos dentro de una variable.

kill -WINCH "$$"

Otro truco que puedes probar es matar tu caparazón con SIGWINCH. Eso hará que readline vuelva a dibujar el mensaje. Ejemplo:

$ (sleep 2; echo foo; sleep 2; kill -WINCH "$$") &
[1] 2295
<immediately press l and s; the "foo" text will mess up the current line>
$ lsfoo
<after 1s the prompt is redrawn again without the parasitic text>
$ ls

ioctl(TIOCSTI)

Otro truco más es vincular alguna clave no utilizada redraw-current-linecomo de costumbre y luego simular esa clave con TIOCSTIioctl (todavía funciona sin privilegios adicionales en elactualtty en Linux). Pero necesitarías C, Perl, Python, etc. para eso:

$ bind '"\xff": redraw-current-line'
$ redraw_current_line(){ perl -e 'ioctl STDIN, 0x5412, $x = "\xff"' </dev/tty; }
$ (sleep 2; echo foo; sleep 2; redraw_current_line) &
.... same as in SIGWINCH example ...

Este último truco es sólo para Linux; el número ioctl de TIOCSTIotro sistema que pueda admitirlo es diferente.


Nota:Si alguien piensa que debería require "sys/ioctl.h"en lugar de cablear el número ioctl:No, no debería. Incluso si funciona por casualidad enesteEn este caso, Perl h2phestá dañado y los .pharchivos deberíannoser usado:

$ perl -e 'require "sys/ioctl.ph"; printf "%x\n", TIOCGPTN()'
80005430
$ cc -include stdio.h -include sys/ioctl.h -xc - \
   <<<'int main(){printf("%lx\n",TIOCGPTN);}' -o /tmp/foo && /tmp/foo
80045430

Observe el bit extra en lo real:! 80045430=80005430

información relacionada