Lorsque j'exécute un programme sans spécifier le chemin d'accès complet à l'exécutable, et Bash doit rechercher les répertoires dans $PATH
pour trouver le binaire, il semble que Bash se souvienne du chemin dans une sorte de cache. Par exemple, j'ai installé une version de Subversion de la source vers /usr/local
, puis tapé svnsync help
à l'invite Bash. Bash a localisé le binaire /usr/local/bin/svnsync
pour "svnsync" et l'a exécuté. Puis quand j'ai supprimé l'installation de Subversion dans /usr/local
et relancé svnsync help
, Bash répond:
bash: /usr/local/bin/svnsync: No such file or directory
Mais, lorsque je démarre une nouvelle instance de Bash, il trouve et exécute /usr/bin/svnsync
.
Comment effacer le cache des chemins d'accès aux exécutables?
bash
met en cache le chemin complet d'une commande. Vous pouvez vérifier que la commande que vous essayez d'exécuter est hachée avec la commande type
:
$ type svnsync
svnsync is hashed (/usr/local/bin/svnsync)
Pour vider l'intégralité du cache:
$ hash -r
Ou juste une entrée:
$ hash -d svnsync
Pour plus d'informations, consultez help hash
et man bash
.
Pour effacer une seule entrée, vous avez besoin d'un indicateur différent:
hash -d svnsync
Le -r
L'indicateur ne prend pas de paramètre et supprimera toujours tout le cache.
(Au moins dans bash 3.2.39 sur Debian Lenny)
Il existe des solutions non mentionnées ici.
Vous pouvez désactiver le hachage avec set +h
ou set +o hashall
help set
dit:
-h - N'oubliez pas l'emplacement des commandes lorsqu'elles sont recherchées pour exécution. C'est activé par défault.
hashall - Identique à -h
set -h # enable hashing
shopt -u checkhash # disable command existence check
hash -p /some/nonexisting/dir/date date # bind date with /some/nonexisting/dir/date
date # bash: /some/nonexisting/dir/date: No such file or directory
set +h
date # normal date output
Vous pouvez vérifier qu'une commande trouvée dans la table de hachage existe avant d'essayer de l'exécuter avec shopt -s checkhash
help shopt
dit:
checkhash - S'il est défini, bash vérifie qu'une commande trouvée dans la table de hachage existe avant d'essayer de l'exécuter. Si une commande hachée n'existe plus, une recherche de chemin normale est effectuée.
set -h # enable hashing
shopt -u checkhash # disable command existence check
hash -p /some/nonexisting/dir/date date # bind date with /some/nonexisting/dir/date
hash -t date # prints /some/nonexisting/dir/date
date # bash: /some/nonexisting/dir/date: No such file or directory
shopt -s checkhash # enable command existence check
date # normal date output
hash -t date # prints /bin/date
Vous pouvez lier NAME avec PATH avec hash -p PATH NAME
ou BASH_CMDS[NAME]=PATH
:
shopt -u checkhash # disable command existence check
hash -p /some/nonexisting/dir/date date
date # bash: /some/nonexisting/dir/date: No such file or directory
BASH_CMDS[date]=/bin/date
date # normal date output
La magie: PATH="$PATH"
exécute hash -r
De variables.c
:
/* What to do just after the PATH variable has changed. */
void
sv_path (name)
char *name;
{
/* hash -r */
phash_flush ();
}
Essayer:
set -h
hash -r
date
hash # prints 1 /bin/date
PATH="$PATH"
hash # prints hash: hash table empty