ssh-agent i screen

8

Jakiś czas temu w StackOverflow zadałem to pytanie dotyczące ssh-agent i crontab . Mam podobne pytanie dotyczące ssh-agent i screena w systemach Linux.

Tak więc na moim Macu ssh-agent uruchamia się przy starcie systemu, więc zawsze jest dla mnie dostępny. Myślę, że byłoby to prawdą w moim systemie Linux (redhat el5 / fedora), gdybym korzystał z X-Windows. Jest to jednak zdalny serwer i zawsze loguję się przez ssh.

Chciałbym mieć poprawnie skonfigurowane klucze ssh, aby nie musiałem wpisywać hasła wiele razy podczas aktualizacji svn lub zatwierdzania. Z przyjemnością wpisuję moje hasło raz na sesję i zniechęcam nasz zespół do posiadania kluczy SSH bez hasła.

Przez krótki lśniący moment wydawało się, że wykonanie polecenia „eval` ssh-agent -s` ”w moim .bash_profile, w połączeniu z poleceniem zabicia ssh-agent po wylogowaniu, zadziałałoby. Jednak intensywnie wykorzystujemy ekran do zarządzania długo działającymi programami interaktywnymi i środowiskami programistycznymi. Jeśli uruchomisz i zatrzymasz ssh-agent, tak jak to właśnie opisałem, zostanie zabity, gdy wyjdziesz z terminala, a podsekcje ekranu, które kiedyś odnosiły się do tej instancji ssh-agent, zostaną porzucone.

Więc ... jak mogę być użytkownikiem konsoli, który używa screena, który używa hasła ze swoimi kluczami ssh, który nie musi ciągle wpisywać hasła?

Michael H.
źródło

Odpowiedzi:

4

Dzięki poniższej konfiguracji nie będziesz potrzebować żadnego opakowania do wywołania screen. Ponadto unika używania /tmp(z wynikającym z tego ryzykiem bezpieczeństwa).

  1. Upewnij się, że masz katalog ~ / tmp:

    mkdir ~/tmp
    
  2. Dodaj do .screenrcnastępującego wiersza:

    setenv SSH_AUTH_SOCK "$HOME/tmp/ssh-agent-screen"
    
    • Gwarantuje to, że wewnątrz screen, sshszuka gniazda zawsze w tym samym miejscu, zamiast zmieniać ścieżki.
    • Musisz użyć setenvdowolnej powłoki, ponieważ jest to ekran, a nie polecenie powłoki.
  3. Dodaj do .bash_profilenastępującego wiersza:

    [ -n "$SSH_AUTH_SOCK" ] && [ "$SSH_AUTH_SOCK"!="$HOME/tmp/ssh-agent-screen" ] && ln -sf "$SSH_AUTH_SOCK" "$HOME/tmp/ssh-agent-screen"
    
    • Spowoduje to link z ustalonej lokalizacji (gdzie sshwygląda) do rzeczywistej i musi pojawić się po uruchomieniu ssh-agent.
    • Używanie [ -n "$SSH_AUTH_SOCK" ]odpowiednio zapobiegnie błędom, gdy SSH_AUTH_SOCKnie jest ustawione.
    • [ "$SSH_AUTH_SOCK"!="$HOME/tmp/ssh-agent-screen" ]zapobiegnie łączeniu sesji ekranowych $ HOME / tmp / ssh-agent-screen ze sobą, jeśli źródła ekranu .bash_profile.
  4. Zamiast rozpoczynać ssh-agentsię .bash_profile, można rozważyć podłączenie z ssh -A(by użyć agenta spedycji i dokonać zdalnego wykorzystania maszyny agent).

Po tej konfiguracji możesz po prostu użyć standardowego polecenia ekranowego. Musisz tylko odtworzyć istniejące sesje lub ręcznie ustawić SSH_AUTH_SOCK w nich na stałą lokalizację kroku 2.

Podziękowania dla tej witryny za pomysł; Unikałem używania /tmp. Ta odpowiedź jest podobna, ale wykorzystuje dodatkowe aliasy.

Blaisorblade
źródło
2

Czy możesz uruchomić ssh-agent z initscript zamiast .bash_profile? Na przykład, mogę powiedzieć

su -c 'ssh-agent -s > ~/.ssh_agent_env' myusername

w odpowiedniej części /etc/conf.d/local, chociaż RHEL / Fedora prawdopodobnie używa innego systemu. Jak wskazano w komentarzu, sesje terminalowe będą musiały być w stanie połączyć się z agentem, dlatego polecenie to tworzy plik .ssh_agent_envw katalogu osobistym użytkownika. Następnie możesz dodać

[ -f ~/.ssh_agent_env ] && source ~/.ssh_agent_env >/dev/null

w .bash_profile.

Inną rzeczą, którą możesz zrobić, to umieścić następujące informacje .bash_profile

ps -U myusername | grep -q ssh-agent || ssh-agent -s > ~/.ssh_agent_env
source ~/.ssh_agent_env >/dev/null

który uruchomi się ssh-agenttylko wtedy, gdy jeszcze nie działa. Więc nie musisz tego zabijać.

Jako nieco inna alternatywa dla drugiej sugestii, zamiast sprawdzać istnienie ssh-agentprocesu, możesz sprawdzić istnienie pliku ~/.ssh_agent_env,

[ -f ~/.ssh_agent_env ] || ssh-agent -s > ~/.ssh_agent_env
source ~/.ssh_agent_env >/dev/null

Jeśli wszystko działa poprawnie, nie powinno być żadnej znaczącej różnicy między tymi dwoma sposobami.

David Z
źródło
Pomysł na skrypt startowy jest interesujący - w zasadzie wystarczy uruchomić go przy starcie systemu dla wszystkich użytkowników, którzy go chcą? To może zadziałać. Nie mamy wielu użytkowników, którzy by się tym przejmowali. To, czy jest to znacznie lepsze niż brak hasła, jest interesującym pytaniem, ponieważ podejrzewam, że oznacza to, że będziesz musiał wprowadzić go tylko raz na ponowne uruchomienie komputera. Hmm Zarówno ta, jak i druga sugestia polegają na tym, że nowe sesje terminali mogą połączyć się z agentem ssh, jeśli już działa. Nie jestem do końca pewien, czy to takie proste, ale jeszcze nie próbowałem. Dzięki za pomysły!
Michael H.
@khedron: Tak, ale musiałbyś wstawić jedną linię /etc/conf.d/local(lub ekwiwalent) dla każdego użytkownika korzystającego z agenta, aby uruchomić osobny ssh-agentproces dla każdego użytkownika. Jeśli, jak mówisz, nie masz ogromnej liczby użytkowników, nie byłoby źle. Podnosisz dobrą rację (o której zapomniałem wziąć pod uwagę) na temat sesji terminalowych dołączanych do agenta; zobacz moją edycję odpowiedzi.
David Z
2

Sprawdź pęku kluczy . Robi to wszystko powyżej. Spójrz szczególnie na opcje --cleari --timeout.

Neil Mayhew
źródło
2

Lepszym rozwiązaniem jest użycie przekazywania agenta ssh ( -Aopcja). Pozwala to osobie używającej ssh na używanie kluczy od agenta ssh działającego na maszynie, z której pochodzą, prawdopodobnie na stacji roboczej, na której faktycznie siedzą.

Neil Mayhew
źródło
Pozwala to również atakującemu, który naruszy Twoje konto, na złamanie zabezpieczeń kont na innych komputerach, do których agent ten może uzyskać dostęp. Dlatego staram się ograniczyć przekazywanie agentów ssh do minimum.
Paul Price
2

aby śledzić przekazywanie agenta ssh, domyślnie przekierowane poświadczenia ssh nie będą dostępne dla sesji ekranowej po wylogowaniu, zalogowaniu się i ponownym dołączeniu do sesji.

Można jednak obejść ten problem, ustawiając zmienną środowiskową SSH_AUTH_SOCK na coś dobrze znanego i aktualizując tę ​​znaną lokalizację do bieżącego gniazda uwierzytelniania.

Używam tej funkcji powłoki, aby ponownie wejść do ekranu i naprawić ssh auth sock:

function sr () { 
    if [ ${+STY} = 1 ] ;then 
            echo already in screen\!
    else
            if [ "${SSH_AUTH_SOCK}x" != "x" ]; then
                    if [ ! -d /tmp/screenssh ]; then
                            mkdir /tmp/screenssh 
                    fi
                    rm -f /tmp/screenssh/socket
                    ln -s $SSH_AUTH_SOCK /tmp/screenssh/socket
                    echo $REMIP > /tmp/screenssh/remip
            fi                
            screen -DR
    fi
}

i mam to w moim .screenrc:

setenv SSH_AUTH_SOCK /tmp/screenssh/socket

Mam nadzieję że to pomoże.

Dan Pritts
źródło
Użycie / tmp oznacza, że ​​każdy inny na komputerze może zablokować dowolny z twoich plików, jeśli zna ich ścieżkę.
Blaisorblade,
1

Jeśli dobrze cię zrozumiałem, po prostu chcesz sesji ekranowej, którą czasami odłączasz i dołączasz ponownie, ale nigdy więcej nie chcesz ponownie wprowadzać haseł do ssh-agent (hasło klucza prywatnego).

Myślę, że najprostszym sposobem jest uruchomienie ekranu, niż uruchomienie ssh-agent za pomocą podpowłoki, a następnie pozostanie w tej podpowłoce. To znaczy

screen
ssh-agent bash
ssh-add   # enter your password once

# some commands, some logins and logouts to remote servers via ssh public key

# <ctrl>+<a>, <ctrl>+<d> to detach screen
# you can now logout from this computer
# login again

# reattach to your screen
screen -r
# ssh-agent is still running
erik
źródło
Zasadniczo to robię. Używam screena, aby oznaczyć jedną z „zakładek” jako posiadających moce ssh-agent, i używam go do pracy svn itp. Istnieje dodatkowe zmarszczenie, w którym zmuszam ssh-agent do ponownej autoryzacji po kilku godzinach, ale tak, to jest po prostu tam, gdzie jestem.
Michael H.