Que fait CTRL + 4 (et CTRL + \) dans bash?

22

Je viens de découvrir par accident que CTRL+ 4 ferme les programmes lisant les stdinentrées de la ligne de commande.

Voici à quoi ça ressemble quand je tape CTRL+ 4ou CTRL+ / dans les programmes en train de lirestdin

$ cat
wefwef
wefwef
^\Quit
$ bc
bc 1.06.95
Copyright 1991-1994, 1997, 1998, 2000, 2004, 2006 Free Software Foundation, Inc.
This is free software with ABSOLUTELY NO WARRANTY.
For details type `warranty'. 
^\Quit
$

Je suis ^\Quitaffiché puis le programme se ferme. Quelle est la différence par rapport à l'utilisation de ^Cou ^D? Que fait ^\Quit-il?

Edit : J'ai découvert que CTRL+ \fait exactement la même chose.

wefwefa3
la source

Réponses:

37

Ctrl + 4 envoie ^ \

Les terminaux envoient des caractères (ou plus précisément des octets), pas des clés. Lorsqu'une touche représentant un caractère imprimable est enfoncée, le terminal envoie ce caractère à l'application. La plupart des touches de fonction sont codées comme des séquences d'échappement: des séquences de caractères qui commencent par le numéro de caractère 27. Certains accords de touches de la forme Ctrl+ character, et quelques touches de fonction, sont envoyés en tant que caractères de contrôle - dans le jeu de caractères ASCII , que tous les ordinateurs modernes utiliser comme base (Unicode, ISO Latin- n, etc. sont tous des sur-ensembles ASCII), 33 caractères sont des caractères de contrôle: les caractères 0 à 31 et 127. Les caractères de contrôle ne sont pas imprimables, mais destinés à avoir un effet dans les applications; par exemple, le caractère 10, qui est Control-J (généralement écrit ^ J), est un caractère de nouvelle ligne, donc lorsqu'un terminal affiche ce caractère, il déplace le curseur sur la ligne suivante, plutôt que d'afficher un glyphe. Le caractère d'échappement lui-même est un caractère de contrôle, ^ [(valeur 27).

Il n'y a pas suffisamment de caractères de contrôle pour couvrir tous les accords Ctrl+ characterclés. Seules les lettres et les caractères @[\]^_?ont un caractère de contrôle correspondant. Lorsque vous appuyez sur Ctrl+ 4ou Ctrl+ $(ce qui, je suppose, est Ctrl+ Shift+ 4), le terminal doit choisir quelque chose à envoyer. Selon le terminal et sa configuration, il existe plusieurs possibilités communes:

  • Le terminal ignore le Ctrlmodificateur et envoie le caractère 4ou $.
  • Le terminal envoie une séquence d'échappement qui code la touche exacte et les modificateurs qui ont été enfoncés.
  • Le terminal envoie un autre caractère de contrôle.

De nombreux terminaux envoient des caractères de contrôle pour certaines touches de la ligne des chiffres:

  • Ctrl+ 2→ ^ @
  • Ctrl+ 3→ ^ [
  • Ctrl+ 4→ ^ \
  • Ctrl+ 5→ ^]
  • Ctrl+ 6→ ^^
  • Ctrl+ 7→ ^ _
  • Ctrl+ 8→ ^?

Je ne sais pas d'où vient cette convention particulière.

Ctrl+ |envoie le même caractère car c'est Ctrl+ Shift+ \et le terminal envoie ^ \ que la touche Maj ait été enfoncée ou non.

^ \ quitte

Le terminal lui-même (plus précisément, le support de terminal générique dans le noyau) interprète spécialement quelques caractères de contrôle. Cette interprétation peut être configurée pour mapper différents caractères ou désactivée par les applications qui souhaitent traiter les caractères par eux-mêmes. Une telle interprétation bien connue est que ^ M, le caractère envoyé par la Returntouche, envoie la ligne courante à l'application, si le terminal est en mode cuit , dans lequel les applications reçoivent l'entrée ligne par ligne.

Quelques caractères envoient des signaux à l'application au premier plan. ^ C envoie le signal d'interruption (SIGINT), qui indique classiquement à l'application d'arrêter ce qu'elle fait et de lire la prochaine commande de l'utilisateur. Les applications non interactives se terminent généralement. ^ \ envoie le signal de sortie (SIGQUIT), qui indique classiquement à l'application de quitter le plus tôt possible sans rien enregistrer; de nombreuses applications ne remplacent pas le comportement par défaut, qui consiste à tuer l'application immédiatement¹. Ainsi, lorsque vous appuyez sur Ctrl+ 4(ou sur tout élément qui envoie le caractère ^ \) dans catou bc, qui ne remplace pas le comportement par défaut, l'application est supprimée.

Le terminal lui-même imprime la ^\partie du message: c'est une représentation visuelle du caractère que vous avez tapé, et le terminal est en mode cuit et avec l'écho activé (les caractères sont affichés par le terminal dès que vous les tapez, par opposition à mode non-écho où les caractères ne sont envoyés qu'à l'application, qui peut ou non choisir de les afficher). La Quitpartie vient de bash: elle remarque que son processus enfant est mort à partir d'un signal d'arrêt, et c'est sa façon de vous le faire savoir.

Les shells gèrent tous les signaux courants, de sorte que si vous tapez ^ \ dans un shell, vous ne tuez pas votre session, vous obtenez simplement une nouvelle invite, identique à ^ C.

Vous pouvez jouer avec les paramètres du terminal avec la sttycommande.

¹ Et génèrent traditionnellement un vidage de mémoire , mais de nombreux systèmes le désactivent par défaut de nos jours.

Gilles 'SO- arrête d'être méchant'
la source
SIGINT tue le groupe de processus de premier plan et SIGQUIT le tue avec un vidage de mémoire. Les deux signaux peuvent être traités. Je ne sais pas ce que vous voulez dire en lisant la commande suivante . Les systèmes ne désactivent pas les vidages de mémoire autrement qu'en définissant la limite de coredumpsize initiale à 0 (pas le disque dur, vous êtes généralement libre de l'augmenter).
Stéphane Chazelas
@ StéphaneChazelas Dans un programme qui effectue des interactions utilisateur, la sémantique habituelle de SIGINT est d'annuler la commande utilisateur courante et de permettre à l'utilisateur d'interagir avec le programme, c'est-à-dire de revenir à la boucle de commande principale. D'un autre côté, je ne me souviens pas avoir vu un programme où SIGQUIT ne se ferme pas (sauf bogues dans le gestionnaire de signal). En effet, la façon dont de nombreux systèmes désactivent les vidages de mémoire par défaut est de définir la limite souple de taille de vidage de mémoire à 0, laissant les utilisateurs libres de modifier ce paramètre par défaut s'ils le souhaitent.
Gilles 'SO- arrête d'être méchant'
Voilà l'exception. SIGINT tue la tâche en cours d'exécution. Seules quelques applications pourraient étendre cela pour tuer leur propre tâche "de premier plan". Vous devez penser à lessou vim. Notez que dans cmd | less, CTRL-Ctue généralement cmd(alors que lessc'est géré pour annuler l'action en cours (comme une recherche)) (suite)
Stéphane Chazelas
Je trouve le libellé de votre réponse déroutant à cet égard. Le fait que SIGQUIT ne soit généralement pas géré est qu'il n'est pas utilisé de la même manière. Vous appuyez sur CTRL-C pour abandonner ce que vous faites actuellement. Vous utiliseriez `CTRL- \` seulement très occasionnellement pour le débogage pour générer un vidage de mémoire. Il n'y a généralement aucune raison pour qu'une application veuille vous gêner.
Stéphane Chazelas
@ StéphaneChazelas Non seulement moins et vim, la plupart des applications basées sur des terminaux qui lisent les commandes des utilisateurs. Par exemple REPL (bash, dash, ksh, zsh, python, irb, fsharpi, Mathematica,…). Ce n'est pas rare. Votre premier commentaire s'oppose à peindre SIGINT et SIGQUIT comme trop différent et vos derniers commentaires à peindre SIGINT et SIGQUIT comme trop similaire, ce qui me laisse perplexe quant à ce que vous conduisez.
Gilles 'SO- arrête d'être méchant'
7

En plus de la réponse de Gilles, permettez-moi d'ajouter que vous pouvez toujours saisir des caractères non imprimables en bash avec Ctrl-v+ key( Ctrl-v+ Ctrl+4dans ce cas) et vérifier le code de caractère avec

$ printf '^\' | od -An -tu    # input ^\ as C-v C-4
28

vous obtenez le code décimal du caractère qui, comme vous pouvez le vérifier, man asciicorrespond au séparateur de fichiers (FS) .

jimmij
la source
Alors, que fait ctrl + v? J'ai l'habitude d'être un "presse-papiers".
JDługosz
2
@ JDługosz: Ctrl-V indique au terminal de ne pas interpréter le caractère suivant. Il est regrettable que les combinaisons de touches de l'interface graphique aient pris le contrôle de ces caractères de contrôle, provoquant une confusion inutile. Auparavant, Linux utilisait Alt- [Key] pour les clés de l'interface graphique (par exemple Alt-C / Alt / V pour copier / coller), mais les gens pensaient évidemment que faire la même chose que Windows était plus important; pendant ce temps, les utilisateurs de Mac n'ont toujours aucun problème à utiliser la touche Commande au lieu de la touche Ctrl pour ces opérations.
celtschk
La commande (la plus courte) est printf '%d\n' '"^\':?
Isaac