 |
|
| |
keychain(1) |
https://www.funtoo.org |
keychain(1) |
keychain - Manager for ssh-agent, gpg-agent and private keys.
Compatible with POSIX systems.
keychain [ -hklQqV ] [ --clear --confhost --confallhosts --debug
--extended --gpg2 --help --ignore-missing --list --noask --nocolor --nogui
--noinherit --nolock --quick --quiet --ssh-allow-forwarded --ssh-rm
--ssh-spawn-gpg --systemd --version ] [ --ssh-agent-socket path ]
[ --dir dirname ] [ --host name ] [ --lockwait seconds ]
[ --stop which ] [ --timeout minutes ] [ --wipe which ] [ keys... ]
Keychain helps you to manage SSH and GPG keys in a
convenient and secure manner. It acts as a frontend to
"ssh-agent" and
"ssh-add", but allows you to easily have
one long running "ssh-agent" process per
system, rather than the norm of one
"ssh-agent" per login session.
This dramatically reduces the number of times you need to enter
your passphrase. With "keychain", you only
need to enter a passphrase once every time your local machine is rebooted.
Keychain also makes it easy for remote cron jobs to securely "hook
in" to a long running "ssh-agent"
process, allowing your scripts to take advantage of key-based logins.
Keychain also supports GnuPG 2.1 and later, and will automatically
start gpg-agent if any GPG keys are referenced on the command-line, and will
ensure these credentials are cached in memory and available for use.
Keychain supports most UNIX-like operating systems. It supports
integration with Bourne-compatible, csh-compatible and fish shells.
Additional documentation for Keychain can be found on
"https://www.funtoo.org/Funtoo:Keychain" in the Keychain wiki
page.
Typically, you configure keychain to run when you first log in to
a system. If you are using Bourne shell or bash, you will create a
"~/.profile" or
"~/.bash_profile" file and include the
following line in it:
eval "$(keychain --eval id_rsa)"
Keychain will start ssh-agent if one isn't already running.
Keychain then checks to make sure your private keys (in this example,
"id_rsa") are loaded into the agent. If they are not, you are
prompted for any passphrase necessary to decrypt them, so that they are
cached in memory and available for use.
In addition to printing some user-friendly output to your
terminal, keychain will also output important ssh-agent environment
variables, which the "$( )" (you can also use "` `")
captures, and the "eval" evaluates, setting these variables in
your current shell.
These ssh-agent environment variables are also written to
"~/.keychain/${HOSTNAME}-sh", so that
subsequent logins and non-interactive shells such as cron jobs can source
the file to access the running ssh-agent and make passwordless ssh
connections using the cached private keys -- even when you are logged out.
These files are collectively called pidfiles.
The key files specified on the command-line will be searched for
in the "~/.ssh/" directory, and keychain
will expect to find the private key file with the same name, as well as a
".pub" public key. Keychain will also see
if any GPG keys are specified, and if so, prompt for any passphrases to
cache these keys into "gpg-agent".
Typically, private SSH key files are specified by filename only,
without path, although it is possible to specify an absolute or relative
path to the private key file as well. Private key files can be symlinks to
the actual key as long as your system has the
"readlink" command available. More
advanced features are available for specifying keys as well -- see the
--extended and --confallhosts options for more information.
In addition, for GPG keys specified, similar steps will be taken
to ensure that gpg-agent has the GPG key cached in memory and ready for
use.
Keychain 2.9.0 has been streamlined, and with this maintenance
several command-line options have been retired as they are not completely
necessary. This simplifies the use of the tool by making it more intuitive
to use. The files created in ~/.keychain have also been cleaned up. This
section details all the important changes.
"Pidfile" is the nickname for files created in
"~/.keychain" which can then be sourced by
your scripts to access a running agent.
When using gpg-agent for GPG keys, keychain will no longer create
a "~/.keychain/${HOSTNAME}-sh-gpg"
pidfile. This file is no longer needed as the canonical GPG socket inside
"~/.gnupg/" will be used to detect the
running gpg-agent, which is the modern convention. GnuPG 2.1 and later have
stopped using environment variables to find the agent, so we follow this
upstream change.
A new --debug option is now available which will print
additional information related to keychain's decisions regarding why and how
an agent was found -- or not.
This section provides an overview of new and deprecated
command-line options. For full details on each option, see the respective
option definition under "OPTIONS".
Keychain 2.9.2
The "--confhost" option has been
deprecated. Instead of "--confhost
hostname", use "--extended
host:hostname". This extended format allows multiple keys of
multiple types (SSH, GPG and SSH-from-hostname) to be specified on the
command-line together. This is also fully compatible with
"--confallhosts", and keychain now
de-duplicates the list of keys to be loaded.
Keychain 2.9.1
The short-lived "--ssh-wipe" and
"--gpg-wipe" options that appeared only in
version 2.9.0 were replaced with "--wipe
which" to
work similarly to the "--stop" option, and
allows you to specify "ssh", "gpg" or
"all".
Keychain 2.9.0
The "--agents" option is now
deprecated. Keychain will always ensure an ssh-agent or equivalent is
running, or if "--ssh-spawn-gpg" is used,
potentially a gpg-agent for the purpose of storing SSH keys if no running
ssh-agent is available. To simply use a gpg-agent if one is already running,
falling back to launching ssh-agent if no agent is available, use the
"--ssh-allow-gpg" option.
Specifying a GPG key on the command-line will instruct keychain to
enable gpg-agent functionality automatically. This eliminates an option that
you need to specify ("--agents ssh,gpg")
when invoking keychain, and for many will avoid spawning a GPG agent you may
not be using.
Specifying the "--agents" option
will now display a warning that it's deprecated, but keychain will not
abort.
The "--inherit" option, which
took one of four arguments, has been deprecated. Keychain's default behavior
remains that of preferring to use an ssh-agent or equivalent referenced by
its pidfile, falling back to finding an ssh-agent in its environment. By
default, keychain will not use a gpg-agent socket for SSH keys unless at
least "--ssh-allow-gpg" is specified.
Similarly, the use of any forwarded SSH agent connection is disabled by
default and can be enabled via
"--ssh-allow-forwarded". Again, see the
full documentation for each option in the "OPTIONS" section.
You can still influence keychain's behavior via the still-present
"--noinherit" option which will prevent
all detection of existing SSH agents via the environment.
The "--clear" option is still
available, but isn't intended to be a "standalone" option, meaning
that it is used to perform an initial clearing of cached keys before loading
any specified keys when Keychain is run. To perform the sole action of
wiping all cached keys, use the "--wipe"
action. To remove an individual cached SSH private key or keys, use the
"--ssh-rm" keyfile option.
The "--stop" option will now
only stop any running ssh-agent processes, and still supports three possible
options: "mine", "others" and "all". It no
longer stops gpg-agent processes, which tend to get auto-respawned by GPG
tools, so killing gpg-agent typically doesn't make a lot of sense.
Keychain can now use an existing gpg-agent that has been started
in your environment to store ssh keys, rather than spawning its own
ssh-agent, by using the "--ssh-allow-gpg"
option.
If you would like keychain to spawn gpg-agent instead of
ssh-agent, and use it to store SSH keys, specify the
"--ssh-spawn-gpg" option.
Without either option, keychain will not use an SSH_AUTH_SOCK that
is provided by gpg-agent, and will spawn an official ssh-agent process.
In addition, behind the scenes, keychain now uses the
gpg-connect-agent executable to restart the agent, get official PID and
socket information, etc.
Please note that while gpg-agent provides full compatibility with
ssh-agent, its password prompt is handled by pinentry and its store may
encrypt your in-memory keys. For this reason, consider this new feature
experimental, and use GitHub issues to report back any anomalies or
suggested improvements for gpg-agent integration.
When keychain uses gpg-agent for either GnuPG or SSH support, then
keychain will display the GnuPG socket file in its output, rather than the
PID. Since the socket file has the
"~/.gnupg" path in it, this communicates
to you that gpg-agent, not ssh-agent, is active. If you see an integer PID,
this means that ssh-agent is being used. =head2 STREAMLINED STARTUP
By default, keychain will always ensure that an ssh-agent should
be started. It will only start a gpg-agent if a GPG key is referenced on the
command-line.
Modern versions of gpg-agent also support the caching of SSH keys,
allowing it to be a drop-in replacement for ssh-agent. With keychain 2.9.0,
a new "--ssh-spawn-gpg" option has been added, which when
specified will give keychain permission to spawn a gpg-agent in place of
ssh-agent.
With keychain 2.9.0, there has been significant code cleanup,
reducing the size of the script from 1500 lines to about 1100 lines. In
addition, the script is now fully compliant with ShellCheck
<https://shellcheck.net>, which will be hugely helpful to ensure
continued POSIX shell compatibility moving forward.
This section documents the official algorithm used for detecting
and if necessary starting ssh-agent, to facilitate understanding as well as
developer maintenance of the codebase.
There are several important definition related to the
algorithm:
- 1. The agent, "ssh-agent", which is a long-running
daemon. This can also in some cases be "gpg-agent", depending on
command-line options.
- 2. The inherited agent, which is the agent or forwarded agent that
was not started by keychain, but is detected in the environment or by other
means.
- 3. The adopted agent, which is an inherited agent whose
information has been persisted by being written to the pidfiles (see
below).
- 4. The environment variables "SSH_AUTH_SOCK", which
points to the socket file used to communicate with ssh-agent, and optionally
"SSH_AGENT_PID", which indicates its process ID if running locally
(although gpg-agent does not define "SSH_AGENT_PID", even if
running locally.)
- 5. The file "~/.keychain/${HOSTNAME}-sh" and related files,
which are collectively referred to as "pidfiles". Pidfiles
are used to persistently store "SSH_AUTH_SOCK" and
"SSH_AGENT_PID" environment variables for use by other scripts, as
well as by keychain itself, formatted so that they can be
"sourced" by shells of various types.
- 6. Relevant command-line options affecting behavior, which include
--noinherit, --ssh-allow-gpg, --ssh-spawn-gpg, and
--ssh-allow-forwarded.
When the keychain script is run, it will first attempt to find a
running ssh-agent.
- Phase 1: pidfile: To do
this, it will first look for an existing pidfile. If one exists, it
will be inspected and used to find a running agent, in alignment with
specified command-line options. If this process is successful, a
"keychain-spawned" agent is found and this process is complete.
Otherwise, we continue to the next step.
- Phase 2: environment: If
keychain's pidfile did not yield a running agent, keychain looks at
environment variables defined in the current environment. This step
will be skipped if the --noinherit option is specified. If an agent
is found that is in alignment with specified command-line options, it
is considered "inherited" by keychain, and the process is
complete. Otherwise, we continue to the next step.
- Phase 3: spawn agent: In
the absence of finding a keychain-spawned or existing agent that can be
adopted, keychain will spawn a new ssh-agent, or a new gpg-agent if
--ssh-spawn-gpg is specified and gpg-agent is available.
- Final Phase: update pidfile:
In addition, the pidfiles will be updated to reflect the
keychain-spawned or "inherited" agent. An
"inherited" agent, once written to the pidfile, is
now considered to be "adopted".
- Pidfile update
exception: If the --ssh-allow-forwarded option was specified, and a
forwarded SSH socket was found -- which is identified as a valid SSH socket
defined in a "SSH_AUTH_SOCK" variable, which has no associated or
valid "SSH_AGENT_PID" also defined in the environment and is also
determined to not be the socket of any running gpg-agent -- then this agent
will simply be used, but not persisted in any pidfile. This is
because this SSH-supplied socket will disappear when the underlying SSH
connection terminates, and thus it cannot be relied on to be available
persistently.
When the --quick option is specified, a special algorithm
will run prior to the main agent-detection algorithm listed above. A
pidfile, if it exists, will be evaluated as per Phase 1 of the main
algorithm. If a valid running agent is found, it will be queried for valid
keys. If at least one valid key is loaded into the agent, the quick start is
considered successful, and keychain will skip the regular agent startup
algorithm, and will use this found agent.
The keychain ssh-agent detection and startup algorithm is somewhat
sophisticated for a reason. There is an intention behind its behavior.
The algorithm has been specifically designed to prefer an agent
spawned by keychain, or previously adopted, if that agent is currently
available. This is by design, because other system software could spawn
ssh-agent and/or gpg-agent processes, and we want keychain to not coerced
into using these new agents which may suddenly appear in the environment
unexpectedly when new desktop sessions start and in other circumstances. If
keychain is too "suggestible", it will lose track of the agent
which currently holds valid keys, which can result in unncessary prompting
for passphrases, and general confusion.
- --absolute
- This option can be used with the --dir option, if you would like to
specify a non-default directory to store pidfiles (defaults to
"~/.keychain"). When this option is
used, the script does not automatically append
"/.keychain" to the path, allowing you
to use any arbitrary directory name for the storing of pidfiles. Please
note that Keychain 2.9.3 adds some extra security checks related to
directory and file permissions -- you must have exclusive ownership of any
directory that keychain uses to store pidfiles, or keychain will
abort.
- --clear
- When specified, this option adds an initial step prior to adding any keys
to the agents of wiping all existing cached keys/passphrases. This is
intended to be used alongside keychain --eval to ensure that only the
specified keys are loaded, and that keychain should assume that you are an
intruder until proven otherwise and force all interactive logins to
specify valid passphrases. This option increases security and still allows
your cron jobs to use your ssh keys when you're logged out.
- --confallhosts
- In addition to any keys specified on the command-line, this option will
tell keychain to scour "~/.ssh/config"
for all private keys referenced in all
"IdentityFile" lines, and load all keys
for all hosts.
- --confirm
- Keys are subject to interactive confirmation by the SSH_ASKPASS program
before being used for authentication. See the -c option for
ssh-add(1).
- --debug
- Keychain 2.9.0 introduces the --debug option, which will output
additional information related to how Keychain makes its agent-selection
process. Specifically, it will output when an SSH_AUTH_SOCK is
rejected because it is being supplied by gpg-agent -- and this is not
allowed due to no --ssh-allow-gpg option, or when it is rejected
because it appears to be from a forwarded SSH connection, and
--ssh-allow-forwarded was not supplied.
- --dir
dirname
- This option allows you to use another directory besides
"$HOME/.keychain". for the storing of
pidfiles. Please note that Keychain 2.9.3 adds some extra security checks
related to directory and file permissions -- you must have exclusive
ownership of any directory that keychain uses to store pidfiles, or the
script will abort. Also see the --absolute option.
- --env
filename
- After parsing options, keychain will load additional environment settings
from "filename". By default, if "--env" is not given,
then keychain will attempt to load from ~/.keychain/[hostname]-env or
alternatively ~/.keychain/env. The purpose of this file is to override
settings such as PATH, in case ssh is stored in a non-standard place.
- --eval
- Keychain will print lines to be evaluated in the shell on stdout. It
respects the SHELL environment variable to determine if Bourne shell or C
shell output is expected.
- --extended
- This enables extended command-line key processing with more features, and
is a replacement for the old
"--confhost" option. When specified,
each key specified on the command-line must have a prefix to explictly.
categorize it. SSH keys must have a prefix of "sshk:"
immediately followed by the path or key name (the part after the
"sshk:" is processed just like a SSH key is without the
"--extended" option). GPG keys must be
in the format "gpgk:" immediately followed by the 8 or
16-character fingerprint. If "host:<hostname>" is
specified, then Keychain will extract the SSH configuration for the
specified hostname, grab all identityfile options (private keys)
specified, and these keys will be included in the set of keys to be loaded
by keychain. This allows multiple keys of multiple types, including
SSH-keys-by-host, to be specified together, which wasn't possible with
"--confhost".
- --gpg2
- This option changes the default gpg calls to use gpg2 instead to support
distributions such as Ubuntu which has both gpg and gpg2
- --help -h
- Show help that looks remarkably like this man-page. As of 2.6.10, help is
sent to stdout so it can be easily piped to a pager.
- --host
name
- Set alternate hostname for creation of pidfiles
- --ignore-missing
- Don't warn if some keys on the command-line can't be found. This is useful
for situations where you have a shared .bash_profile, but your keys might
not be available on every machine where keychain is run.
- -l --list
- List signatures of all active SSH keys, and exit, similar to "ssh-add
-l".
- -L --list-fp
- List fingerprints of all active SSH keys, and exit, similar to
"ssh-add -L".
- --lockwait
seconds
- How long to wait for the lock to become available. Defaults to 5 seconds.
Specify a value of zero or more. If the lock cannot be acquired within the
specified number of seconds, then this keychain process will forcefully
acquire the lock.
- --noask
- This option tells keychain do everything it normally does (ensure
ssh-agent is running, set up the ~/.keychain/[hostname]-{c}sh files)
except that it will not prompt you to add any of the keys you specified if
they haven't yet been added to ssh-agent.
- --nocolor
- Disable color highlighting for non ANSI-compatible terms.
- --nogui
- Don't honor SSH_ASKPASS, if it is set. This will cause ssh-add to prompt
on the terminal instead of using a graphical program.
- --noinherit
- Don't inherit any agent processes, overriding the default behavior of
inheriting all non-forwarded ssh-agent and any existing gpg-agent
processes. Also see "AGENT DETECTION AND STARTUP
ALGORITHM".
- --nolock
- Don't attempt to use a lockfile while manipulating files, pids and
keys.
- --query
- Keychain will print lines in KEY=value format representing the values
which are set by the agents.
- --quick -Q
- If an ssh-agent process is running then use it. Don't verify the list of
keys, other than making sure it's non-empty. This option avoids locking
when possible so that multiple terminals can be opened simultaneously
without waiting on each other. See the "THE QUICK SHORT-CIRCUIT"
section for more information regarding how this fits into the overall
startup algorithm.
- --quiet -q
- Only print messages in case of warning, error or required interactivity.
As of version 2.6.10, this also suppresses "Identities added"
messages for ssh-agent.
- --stop -k
which
- Kill currently running ssh-agent processes and exit.
Note that previous versions of keychain (2.8.5 and earlier)
allowed killing of gpg-agent as well. This functionality was removed as
ssh-agent and gpg-agent have a bit different design philosophies and you
almost always only have at most one gpg-agent running at a time. Use
"killall gpg-agent" if you really want to kill gpg-agent.
However, since this option also removes pidfiles, it will remove any
gpg-agent processes adopted by keychain that were being used to store
ssh keys.
The following values are valid for "which" which
controls which ssh-agents to target:
- all
- Kill all ssh-agent processes and quit keychain immediately. Prior to
keychain-2.5.0, this was the behavior of the bare "--stop"
option.
- others
- Kill agent processes other than the ones keychain is providing. Prior to
keychain-2.5.0, keychain would do this automatically. The new behavior
requires that you specify it explicitly if you want it.
- mine
- Kill keychain's agent processes, leaving other agents alone.
- --ssh-agent-socket
path
- Use this option to specify the path to the socket file that you would like
ssh-agent to create and use as its official socket. By default, ssh-agent
will create its own socket file, typically in /tmp.
- --ssh-allow-forwarded
- By default, keychain will not use a forwarded ssh-agent connection, which
is a ssh-agent socket created by SSH that has no associated local process.
To permit keychain to use a forwarded ssh-agent connection, specify this
option. If a SSH-forwarded socket is used, it will not be persisted in the
pidfiles, as it is not likely to be available outside of the
currently-active SSH session.
- --ssh-allow-gpg
- Would you like to have keychain use an already-running gpg-agent to store
your SSH keys, rather than spawning a new ssh-agent? This option does just
that. When this option is specified, keychain will accept an SSH_AUTH_SOCK
environment variable in its environment, even if it was created by
gpg-agent. Modern versions of gpg-agent are also able to store SSH keys.
By default, keychain has a special check to avoid using a gpg-agent that
has set the SSH_AUTH_SOCK environment variable, and will instead spawn its
own ssh-agent. With this option enabled, this restriction is turned off.
Please note that this option does not actually instruct keychain to
spawn a gpg-agent for storing SSH keys if no agent is available --
if you want that, see the --ssh-spawn-gpg option, below.
ALSO NOTE: When a gpg-agent is adopted for ssh-agent duties in
this way, the
"~/.keychain/${HOSTNAME}-sh" pidfile
will be updated to reference the gpg-agent socket, so it will be
seamlessly used by future cron jobs needing an ssh-agent, as well as by
future invocations of keychain, as long as the --ssh-allow-gpg or
--ssh-spawn-gpg (which implies --ssh-allow-gpg) are
specified.
- --ssh-spawn-gpg
- This is the option to use if you're really on-board with using gpg-agent
as a replacement for ssh-agent. Not only will keychain use a running
gpg-agent if found as per the --ssh-allow-gpg, but if it needs to
spawn a new ssh-agent, it will go ahead and spawn a gpg-agent in its
place, and use it instead. Also see notes for the --ssh-allow-gpg
option, as this option also implies --ssh-allow-gpg.
- --ssh-rm -r
keys
- Only perform the single action of removing the specified cached keys from
the running ssh-agent, and then exit.
- --systemd
- Inject environment variables into the systemd --user session.
- --timeout
minutes
- Allows a timeout to be set for identities added to ssh-agent. When this
option is used with a keychain invocation that starts ssh-agent itself,
then keychain uses the appropriate ssh-agent option to set the default
timeout for ssh-agent. The --timeout option also gets passed to ssh-add
invocations, so any keys added to a running ssh-agent will be individually
configured to have the timeout specified, overriding any ssh-agent
default.
Most users can simply use the timeout setting they desire and
get the result they want -- with all identities having the specified
timeout, whether added by keychain or not. More advanced users can use
one invocation of keychain to set the default timeout, and optionally
set different timeouts for keys added by using a subsequent invocation
of keychain.
- --version
-V
- Show version information.
- --wipe
which
- Only perform the single action of wiping all agent's cached keys. Specify
'ssh', 'gpg' or 'all' for SSH keys, GPG keys and all agents respectively.
Also see the "--ssh-rm" action and the
"--clear" option.
This snippet should work in most shells to load two ssh keys and
one gpg key:
eval `keychain --eval id_rsa id_dsa 0123ABCD`
For the fish shell, use the following format:
if status --is-interactive
keychain --eval --quiet -Q id_rsa | source
end
If you have trouble with that in csh:
setenv SHELL /bin/csh
eval `keychain --eval id_rsa id_dsa 0123ABCD`
This is equivalent for Bourne shells (including bash and zsh) but
doesn't use keychain's --eval feature:
keychain id_rsa id_dsa 0123ABCD
[ -z "$HOSTNAME" ] && HOSTNAME=`uname -n`
[ -f $HOME/.keychain/$HOSTNAME-sh ] && \
. $HOME/.keychain/$HOSTNAME-sh
This is equivalent for C shell (including tcsh):
keychain id_rsa id_dsa 0123ABCD
host=`uname -n`
if (-f $HOME/.keychain/$host-csh) then
source $HOME/.keychain/$host-csh
endif
Likewise, the following commands can be used in fish:
keychain id_rsa id_dsa 0123ABCD
test -z "$hostname"; and set hostname (uname -n)
if test -f "$HOME/.keychain/$hostname-fish"
source $HOME/.keychain/$hostname-fish
end
To load keychain variables from a script (for example from cron)
and abort unless id_dsa is available:
# Load keychain variables and check for id_dsa
[ -z "$HOSTNAME" ] && HOSTNAME=`uname -n`
. $HOME/.keychain/$HOSTNAME-sh 2>/dev/null
ssh-add -l 2>/dev/null | grep -q id_dsa || exit 1
ssh-agent(1), gpg-agent(1), ssh-add(1),
ssh(1)
Keychain was created and is currently maintained by Daniel
Robbins. If you need to report a bug or request an enhancement, please
report it to the GitHub project page at
<https://github.com/funtoo/keychain>. For more information about
keychain, please visit <https://www.funtoo.org/Funtoo:Keychain>.
Visit the GSP FreeBSD Man Page Interface. Output converted with ManDoc.
|