The fix on Linux and macOS
eval "$(ssh-agent -s)"
ssh-add ~/.ssh/id_ed25519
ssh-add -l
The first line starts the agent and sets two variables in your current shell. The last line lists the loaded keys. In the fish shell, use eval (ssh-agent -c).
Diagnose it
echo "$SSH_AUTH_SOCK"
ssh-add -l
echo $?
| Exit status and text | Meaning |
|---|---|
| 0, lists keys | The agent works and has keys |
1, The agent has no identities. | The agent works and is empty. Run ssh-add |
2, Could not open a connection to your authentication agent. | SSH_AUTH_SOCK is not set or is empty |
2, Error connecting to agent: No such file or directory | The variable points to a socket that no longer exists |
Common reasons
You ran ssh-agent without eval
Run by itself, ssh-agent starts a background process and prints shell commands. Nothing runs them, so your shell learns nothing and the error stays:
$ ssh-agent
SSH_AUTH_SOCK=/tmp/ssh-XXXXXX/agent.5467; export SSH_AUTH_SOCK;
SSH_AGENT_PID=5468; export SSH_AGENT_PID;
echo Agent pid 5468;
$ ssh-add -l
Could not open a connection to your authentication agent.
Each attempt like this also leaves an unused agent running. pgrep -l ssh-agent lists them, and you can end the extras with kill.
A new shell, tmux, cron or sudo
The variables only exist in the shell where you ran eval and in the programs it starts. Another terminal, a cron job or an existing tmux session does not have them. sudo usually removes them.
To reuse one agent from several shells, give it a fixed socket path:
export SSH_AUTH_SOCK="$HOME/.ssh/agent.sock"
ssh-add -l >/dev/null 2>&1
[ $? -eq 2 ] && { rm -f "$SSH_AUTH_SOCK"; eval "$(ssh-agent -s -a "$SSH_AUTH_SOCK")"; }
This can go in ~/.bashrc or ~/.zshrc. It starts an agent only if none answers on that socket. Many Linux desktops and macOS already start an agent at login, so check echo "$SSH_AUTH_SOCK" in a fresh terminal first. On a Mac, see ssh-agent and the macOS keychain.
A stale socket
Older shells keep the old path after the agent stops, or a reattached tmux session keeps one from an earlier login:
ls -l "$SSH_AUTH_SOCK"
If the file is gone, start a new agent as shown above, or in tmux set the variable again from a new shell.
You are on a server, expecting your laptop's agent
Without agent forwarding, a login on a server has no agent, and this message there is normal. If you want a key on the server to use, start an agent there. For agent forwarding, read its risks first, because anyone with root on that server can use your forwarded keys while you are connected.
Windows
Windows runs the agent as a service, and it is disabled by default. PowerShell needs no eval. In an administrator PowerShell:
Get-Service ssh-agent | Set-Service -StartupType Automatic
Start-Service ssh-agent
Get-Service ssh-agent
The last line should show Running. Then, in a normal PowerShell:
ssh-add $env:USERPROFILE\.ssh\id_ed25519
In Git Bash, use the commands at the top of this page instead. They start the agent that comes with Git, which is separate from the Windows service.
Do you need the agent?
Not always. SSH uses key files directly, and only asks for a passphrase each time. To load a key into an agent automatically on first use, add this to ~/.ssh/config:
Host *
AddKeysToAgent yes
Questions
Why does ssh-add work in one terminal and not in another?
The agent's variables exist only in the shell where you ran eval and in the programs it starts. Start the agent from ~/.bashrc or ~/.zshrc with a fixed socket, or use the agent your desktop starts at login.
Do I need ssh-agent to use SSH keys?
No. ssh reads key files directly and asks for the passphrase each time. The agent only keeps unlocked keys in memory, so you type the passphrase once.
How do I start ssh-agent on Windows?
In an administrator PowerShell, set the ssh-agent service to Automatic and start it. In Git Bash, run eval "$(ssh-agent -s)" as on Linux.
Sources
- ssh-agent(1), OpenBSD manual
- ssh-add(1), OpenBSD manual
- Key-based authentication in OpenSSH for Windows, Microsoft