Parfois, je fais des choses comme démarrer un sous-shell avec vim :sh
. Comment puis-je savoir si je suis dans un sous-shell où exit
je vais simplement me renvoyer d'un niveau, par opposition à être dans le shell le plus à l'extérieur où exit
je vais me déconnecter ou fermer ma session.
Existe-t-il une sorte de totem d'Inception que je puisse faire tourner ou quelque chose pour savoir combien de niveaux je suis?
command-line
Wyck
la source
la source
echo $0
. Si c'est le shell toplevel, il commencera probablement par un tiret. (Ceci est vrai au moins pour bash, et le tiret signifie qu'il s'agit d'un shell dit de connexion.)Réponses:
Vous pouvez utiliser la commande
pstree
(fournie par défaut avec Ubuntu). Voici un exemple - actuellement, je n'ai qu'une seule fenêtre de terminal ouverte sur WSL:Dans un environnement Linux / Ubuntu réel, l'arborescence des processus sera plus compliquée. Nous pouvons filtrer l’arbre par l’option
-s
qui montrera les parents d’un processus sélectionné. Donc, notre commande pourrait êtrepstree -s $$
, où$$
est une variable d’environnement contenant le PID actuel:Les références:
Ajouter un indicateur à l'invite du shell: Sur la base de l' idée de @ waltinator , afin d'avoir un compteur devant l'invite pour plusieurs obus différents lorsque le niveau est supérieur à un, j'ai ajouté les lignes affichées en dessous de la démo, au bas des fichiers d’ exécution commandes (
~/.*rc
) pertinents .J'ai effectué des tests sur WSL, Ubuntu 16.04, Ubuntu 18.04 (serveur / ordinateur de bureau), Ubuntu 19.04, dans les sessions gnome-terminal, tty et ssh. Voici comment cela fonctionne:
La limitation est que: le compteur ne fonctionne que pour 13-14 niveaux de profondeur, en fonction du système d'exploitation. Je n'ai pas l'intention d'enquêter sur les raisons :)
bash
>.bashrc
:csh
ettcsh
>.cshrc
:zsh
>.zshrc
:ksh
>.kshrc
:sh
c'est en faitdash
sur Ubuntu - ici les choses sont un peu compliquées et câblées (lisez les références ci-dessous pour plus d'informations):Editez le
~/.profile
fichier et ajoutez la ligne suivante en bas:Créez le fichier
~/.shrc
avec le contenu suivant, noteksh
lit également le$ENV
:Les références:
.profile
et.kshrc
Créez une commande qui affichera la profondeur: Une autre option consiste à créer une commande shell qui affichera la profondeur. Pour cela, créez le fichier exécutable (il devrait donc être accessible à l’ensemble du système):
/usr/local/bin/depth
Editez le fichier avec votre éditeur favori et ajoutez les lignes suivantes comme contenu:
Le script ci-dessus a deux options
-v
ou--verbose
qui produira une liste des shells impliqués. Et l’autre option permettant de vérifier si la profondeur est supérieure à 1 et sur cette base sera retournéexit 0
ouexit 1
, vous pouvez donc l’utiliser de cette manièredepth && exit
. Voici quelques exemples d'utilisation:Comparaison par les autres solutions: j'ai passé un peu plus de temps à découvrir certaines faiblesses des approches présentées ici. J'ai pu imaginer les deux cas suivants (les majuscules sont nécessaires pour une meilleure mise en évidence de la syntaxe):
Quand
su
ousudo -i
sont impliqués:Lorsqu'un processus en arrière-plan est lancé:
la source
systemd───xfce4-terminal───bash───pstree
. Pourquoi est-ce ainsi?xfce4-terminal
, ce qui a lancé unbash
shell, dans lequel vous avez courupstree
, qui a rapporté lui-même et ses parents. Si vous parlez du manque d'étapes entre systemd et xfce4-terminal, il se peut que tout ce qui a été lancé que xfce4-terminal soit mort ou désavoué, auquel cas il serait hérité par init.SHLVL
? La portabilité entre les processus et les systèmes, je suppose, mais pstree peut ne pas être installé.$SHLVL
n'est pas pris en charge par certains shells. Plus spécifique, selon l’environnement de la démo ci-dessus, il n’est pas supporté uniquement parsh
(dash
) - et ce shell n’est pas du tout compté par cette variable. D'autre partpstree
fait partie du paquet psmisc qui fournit égalementfuser
,killall
et quelques autres - c'est le composant principal d'Ubuntu - je ne l'ai pas installé sur les systèmes mentionnés dans cette réponse.Vérifiez la valeur de la
SHLVL
variable shell:Citant de
bash
la page de manuel de:Il est également soutenu par
zsh
.la source
:sh
défaut le shell de connexion de l'utilisateur, je pense (c'est vraiment une forme abrégée de:shell
plutôt que le nom d'un fichier binaire de shell spécifique):sh
devim
avant de poster cette réponse, et il a fait évoluer le niveau de shell pour moi. Mon shell de connexion est bash.Dans ma
.bashrc
, j’utilisais$SHLVL
pour ajuster$PS1
en ajoutant des+
signes " " à ma$SUBSHELL
variable:Ensuite, je peux voir à quelle profondeur je suis:
la source
awk:
pgrep:
Vous pouvez placer l'une des deux versions dans un fichier et utiliser source pour rendre $ DEPTH disponible.
la source
Vous pouvez simplement utiliser,
ps
sans aucun argument supplémentaire, l'ensemble de la pile de shell (y compris la pile actuelle). Il montrera également tous les jobs d'arrière-plan que vous avez commencés ainsi queps
lui-même, mais il peut vous donner une estimation approximative de votre profondeur.la source
{ echo hello world; ps; } &
pour prouver laps
réponse ci-dessus.