Jak wyczyścić pamięć podręczną Bash ścieżek do plików wykonywalnych?


256

Kiedy uruchamiam program bez podania pełnej ścieżki do pliku wykonywalnego, a Bash musi przeszukać katalogi w $PATHcelu znalezienia pliku binarnego, wydaje się, że Bash pamięta ścieżkę w jakiejś pamięci podręcznej. Na przykład zainstalowałem kompilację Subversion ze źródła do /usr/local, a następnie napisałem svnsync helpw wierszu polecenia Bash. Bash zlokalizował plik binarny /usr/local/bin/svnsyncdla „svnsync” i wykonał go. Następnie, kiedy usunąłem instalację Subversion /usr/locali uruchomiłem ponownie svnsync help, Bash odpowiada:

bash: /usr/local/bin/svnsync: No such file or directory

Ale kiedy uruchamiam nową instancję Bash, wyszukuje i wykonuje /usr/bin/svnsync.

Jak wyczyścić pamięć podręczną ścieżek do plików wykonywalnych?


7
najgłupsza funkcja w historii
Romeno

Odpowiedzi:


322

bashbuforuje pełną ścieżkę do polecenia. Możesz sprawdzić, czy polecenie, które próbujesz wykonać, jest mieszane za pomocą typepolecenia:

$ type svnsync
svnsync is hashed (/usr/local/bin/svnsync)

Aby wyczyścić całą pamięć podręczną:

$ hash -r

Lub tylko jeden wpis:

$ hash -d svnsync

Aby uzyskać dodatkowe informacje, skontaktuj się help hashi man bash.


15
@Daniel Warto dodać, że w bashu możesz użyć polecenia „type command ”, aby dowiedzieć się, jaki to rodzaj polecenia - jeśli twoje polecenie jest zaszyfrowane, „type” powie ci. Przydatne jest również określenie, czy coś jest wbudowane w powłokę, czy jest to alias.
lunchmeat317

4
Jako FYI, aby zmienić buforowaną ścieżkę, jeśli jest uruchomiona csh, polecenie to rehash.
kurtm

Powyższe rehashpolecenie działa również dla zsh.
Neil Traft,

Aby uzyskać bardziej kompletną odpowiedź, zobacz unix.stackexchange.com/questions/86012/...
Ioannis Filippidis

4
W jednym poleceniu można wywołać wybiórcze powtórzenie hash svnsync.
Ioannis Filippidis

25

Aby usunąć tylko jeden wpis, potrzebujesz innej flagi:

hash -d svnsync

-rFlaga nie bierze parametr i zawsze usunąć całą pamięć podręczną.
(Przynajmniej w bash 3.2.39 na Debianie Lennym)


20

Istnieją rozwiązania niewymienione tutaj.

  1. Możesz wyłączyć haszowanie za pomocą set +hlubset +o hashall

    help set mówi:

    -h - Zapamiętaj lokalizację poleceń podczas wyszukiwania. Jest to domyślnie włączone.

    hashall - Taki sam jak -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
    
  2. Możesz sprawdzić, czy polecenie znalezione w tabeli skrótów istnieje, zanim spróbujesz je wykonać shopt -s checkhash

    help shopt mówi:

    checkhash - Jeśli jest ustawiony, bash sprawdza, czy istnieje polecenie znalezione w tabeli skrótów, przed próbą jego wykonania. Jeśli polecenie skrótu już nie istnieje, przeprowadzane jest normalne wyszukiwanie ścieżki.

    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
    
  3. Możesz powiązać NAME z PATH za pomocą hash -p PATH NAMElub 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
    
  4. Magia: PATH="$PATH"wykonujehash -r

    Od variables.c:

    /* What to do just after the PATH variable has changed. */
    void
    sv_path (name)
        char *name;
    {
        /* hash -r */
        phash_flush ();
    }
    

    Próbować:

    set -h
    hash -r
    date
    hash # prints 1 /bin/date
    PATH="$PATH"
    hash # prints hash: hash table empty
    

1
Nigdy nie zrozumiałem, dlaczego cały ten dodatkowy mechanizm jest dostarczany, gdy ŚCIEŻKA = $ ŚCIEŻKA działa dobrze. Jeśli zmienna PATH ulegnie zmianie, pamięć podręczna wyszukiwania PATH powinna zostać unieważniona. Ma sens.
jrw32982

Przypadek użycia nieobsługiwany przez unieważnienie pamięci podręcznej, gdy zmienna PATH zmienia się, gdy zmienia się lokalizacja plików wykonywalnych. Może się to zdarzyć często, gdy używasz powłoki do dodawania lub usuwania programów, tylko w celu buforowania ostatniego miejsca, w którym je znalazł.
Adam,

Bałaganowanie przy użyciu tabeli skrótów poleceń to wspaniały sposób, aby naprawdę zdezorientować kogoś, kto próbuje debugować skrypt bash.
Erik Aronesty

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.