Skip to content

Commit 97bad9b

Browse files
authored
Copyediting of the SSH docs (#551)
1 parent 4c9fa31 commit 97bad9b

File tree

2 files changed

+74
-75
lines changed

2 files changed

+74
-75
lines changed
+60-61
Original file line numberDiff line numberDiff line change
@@ -1,101 +1,100 @@
11
# SSH Agent
22

3-
An ssh agent acts as a program that holds a set of private keys and provides a way to sign
3+
An SSH agent acts as a program that holds a set of private keys and provides a way to sign
44
challenges with those keys, without ever letting the private keys leave the vault. These challenges
5-
can be sign in requests for logging into a server, and in newer SSH versions, they can also be used
6-
to sign arbitrary data (git commits, but also regular files).
5+
can be sign-in requests for logging into a server and in newer SSH versions they can also be used to
6+
sign arbitrary data e.g. Git commits, but also regular files.
77

88
## OS interface
99

10-
On Unix-like systems (Mac, Linux, BSDs), the ssh-agent is provided via a Unix domain socket. The
10+
On Unix-like systems (Mac, Linux, BSDs) the `ssh-agent` is provided via a Unix domain socket. The
1111
agent provides this socket and any application that wants to use the agent connects via this socket.
1212
This is done by getting the socket path from the `SSH_AUTH_SOCK` environment variable.
1313

14-
On Windows, the agent is provided via a global named pipe at `\\.\pipe\openssh-ssh-agent`. Since
15-
only a single application can act as the pipe server, the OpenSSH agent service first needs to be
16-
disabled in Windows. After which the Bitwarden desktop app can start the agent listening on this
17-
pipe.
14+
On Windows the agent is provided via a global named pipe at `\\.\pipe\openssh-ssh-agent`. Since only
15+
a single application can act as the pipe server, the OpenSSH agent service first needs to be
16+
disabled in Windows, after which the desktop app can start the agent listening on this pipe.
1817

19-
## SSH Agent Protocol
18+
## SSH agent Protocol
2019

21-
The ssh-agent protocol is specified at
22-
[SSH-Agent Spec](https://tools.ietf.org/html/draft-miller-ssh-agent-00). However, Bitwarden Desktop
23-
only implements a subset of this protocol, specifically the sign and list operations. List
24-
operations are always allowed by default, while sign operations require user verification.
20+
The `ssh-agent` protocol is specified as a
21+
[spec](https://tools.ietf.org/html/draft-miller-ssh-agent-00) however the desktop app only
22+
implements a subset of this protocol, specifically the sign and list operations. List operations are
23+
always allowed by default while sign operations require user verification.
2524

2625
### Signing during login
2726

28-
When logging into a server, the client and server first exchange the set of algorithms they support
29-
for key exchange and signing. The server has a host key, which is saved locally. Since - in contrast
30-
to TLS - we don't have central authorities proving the authenticity of a server, the first time
31-
connecting to a server the client will ask the user to verify the fingerprint of the server, saving
32-
it subsequently to the `known_hosts` file. In subsequent authentication requests the client will
27+
When logging into a server the client and server first exchange the set of algorithms they support
28+
for key exchange and signing. The server has a host key which is saved locally. In contrast to TLS,
29+
we don't have central authorities proving the authenticity of a server; the first time connecting to
30+
a server the client will ask the user to verify the fingerprint of the server, saving it
31+
subsequently to the `known_hosts` file. In subsequent authentication requests the client will
3332
compare the fingerprint against the saved one, to prevent subsequent machine-in-the-middle attacks.
3433

35-
The client and server then agree on authentication methods that they can continue with (for instance
36-
public key, password). For public keys, the client then offers the public keys to the server, and
37-
the server will reply which keys it accepts. To prevent leaking the set of keys the client has, they
38-
can additionally configure to offer specific keys to a specific server.
34+
The client and server then agree on authentication methods that they can continue with e.g. public
35+
key, password. For public keys the client then offers the public keys to the server and the server
36+
will reply which keys it accepts. To prevent leaking the set of keys the client has they can
37+
additionally configure to offer specific keys to a specific server.
3938

40-
The ssh client then, for all accepted keys - one by one - asks the agent to sign the login request
41-
for that specific key. This means that if a server accepts multiple keys, the agent might be asked
39+
The SSH client then for all accepted keys, one by one, asks the agent to sign the login request for
40+
that specific key. This means that if a server accepts multiple keys the agent might be asked
4241
multiple times to provide UV with different keys. These might be detectable by parsing the login
43-
request to sign, since it contains the user and server host key. The sign request does not contain
44-
the IP or hostname of the server, but this could be inferred using the `known_hosts` file.
42+
request to sign since it contains the user and server host key. The sign request does not contain
43+
the IP or hostname of the server but this could be inferred using the `known_hosts` file.
4544

46-
Only if public key authentication fails will it fallback to password.
45+
Only if public key authentication fails will it fall back to password.
4746

4847
## Agent forwarding
4948

50-
Any clients can access the agent via the socket / pipe. Further SSH supports a feature called agent
51-
forwarding. Forwarding can be used to log into a remote server A, and allow that server to access
52-
server B and authenticate to it, without ever giving the keys to server A. While convenient, care
53-
has to be taken, both about which servers the agent is forwarded to, but also to always require user
54-
verification for signing operations.
49+
Any clients can access the agent via the socket / pipe. Furthermore, SSH supports a feature called
50+
agent forwarding -- forwarding can be used to log into a remote server A and allow that server to
51+
access server B and authenticate to it without ever giving the keys to server A. While convenient
52+
care has to be taken, both about which servers the agent is forwarded to, but also to always require
53+
user verification for signing operations.
5554

56-
## SSH Signatures
55+
## SSH signatures
5756

58-
The ssh agent can not only sign login requests but also arbitrary data. The format for these
57+
The SSH agent can not only sign login requests but also arbitrary data. The format for these
5958
signature requests is specified at
6059
[`Protocol.sshsig`](https://github.com/openssh/openssh-portable/blob/master/PROTOCOL.sshsig). During
61-
a signature request, the desktop client detects `SSHSIG` requests and parses the namespace, passing
62-
it on to the UI to present.
60+
a signature request the desktop app detects `SSHSIG` requests and parses the namespace, passing it
61+
on to the UI to present.
6362

64-
## Verifying SSH Client Processes
63+
## Verifying SSH client processes
6564

6665
In order to present details about which application is requesting access to the any SSH key,
67-
information about the connecting process is gathered. On unix, this works via the `SO_PEERCRED`
68-
`socketopt`. This provides the PID of the connecting process. On Windows,
66+
information about the connecting process is gathered. On \*nix this works via the `SO_PEERCRED`
67+
`socketopt`; this provides the PID of the connecting process. On Windows,
6968
[`GetNamedPipeClientPRocessId`](https://learn.microsoft.com/en-us/windows/win32/api/winbase/nf-winbase-getnamedpipeclientprocessid)
7069
is used.
7170

72-
Using the process id, further information about the process (process name, signature, application
73-
name, application logo) can be acquired, but for now, just process name is used. Depending on the
74-
client application, the process hierarchy might look different, and the process connecting might be
75-
a one-time child process of the application that the user expects to connect.
71+
Using the process ID further information about the process (process name, signature, application
72+
name, and application logo) can be acquired, but for now just the process name is used. Depending on
73+
the client application the process hierarchy might look different and the process connecting might
74+
be a one-time child process of the application that the user expects to connect.
7675

77-
When agent forwarding is used, an `EXTENSION` command is sent to the client with the
78-
`extension_name` set to
76+
When agent forwarding is used an `EXTENSION` command is sent to the client with the `extension_name`
77+
set to
7978
[`session-bind@openssh.com`](https://raw.githubusercontent.com/openssh/openssh-portable/refs/heads/master/PROTOCOL.agent).
80-
This is detected and noted on the connection, so that the clients can handle this appropriately.
79+
This is detected and noted on the connection so that the clients can handle this appropriately.
8180

82-
## Architecture in Bitwarden Desktop
81+
## Architecture in the desktop app
8382

84-
Bitwarden desktop provides an ssh-agent implementation that provides signing functionality to
85-
applications running on the system. Since the applications running on the system, and remote
83+
The desktop app provides an `ssh-agent` implementation that provides signing functionality to
84+
applications running on the system. Since the applications running on the system and remote
8685
applications when forwarding the agent are untrusted, the agent requires user verification for
87-
signing operations. In total, the ssh agent feature consists of multiple components:
86+
signing operations. In total, the SSH agent feature consists of multiple components:
8887

89-
- [Desktop Native] The agent itself, handling the socket / pipe and signing requests
90-
- [Desktop Native] A key store that holds the private keys and corresponding cipher id's for the
91-
keys of the active and unlocked account
92-
- [Desktop Native & Desktop Electron] A communication layer that allows the native module to show UV
93-
prompts in the UI
94-
- [Desktop Electron] A UI component that shows the UV prompts and allows the user to accept or deny
95-
the signing request
88+
- **Desktop Native:** the agent itself, handling the socket / pipe and signing requests.
89+
- **Desktop Native:** a key store that holds the private keys and corresponding cipher IDs for the
90+
keys of the active and unlocked account.
91+
- **Desktop Native and Electron:** a communication layer that allows the native module to show UV
92+
prompts in the UI.
93+
- **Desktop Electron:** a UI component that shows the UV prompts and allows the user to accept or
94+
deny the signing request.
9695

9796
The key store is synced on an interval from the renderer process and receives the decrypted private
98-
keys from the vault ciphers. When locking / changing users, the private keys of the keystore are
99-
wiped. When locking, the public keys are kept, so that listing still works. This means that when
100-
locked after unlocking once, the correct ssh key for a server can be chosen, and a signing request
101-
made. This then prompts the user to unlock their vault in order to approve the request.
97+
keys from the vault ciphers. When locking / changing users the private keys of the keystore are
98+
wiped. When locking the public keys are kept so that listing still works -- this means that when
99+
locked after unlocking once the correct SSH key for a server can be chosen and a signing request
100+
made; this then prompts the user to unlock their vault in order to approve the request.

docs/architecture/deep-dives/ssh/index.md

+14-14
Original file line numberDiff line numberDiff line change
@@ -2,27 +2,27 @@
22

33
:::info
44

5-
For more information on how Bitwarden implements SSH Agent, see [SSH Agent](./agent).
5+
For more information on how Bitwarden implements its SSH agent, see [SSH Agent](./agent).
66

77
:::
88

99
## What are SSH Keys?
1010

11-
SSH keys are asymmetric key pairs that can be used for signing. Historically, they were intended for
12-
logging into servers, but recently they can also be used for signing arbitrary data, such as git
13-
commits or even regular files. These key pairs consist of a private key, an associated public key
14-
and fingerprint. The latter two can be used to verify a signature created using the private key.
11+
SSH keys are asymmetric key pairs that can be used for signing. Historically they were intended for
12+
logging into servers, but recently they can also be used for signing arbitrary data such as Git
13+
commits or even regular files. These key pairs consist of a private key, an associated public key,
14+
and fingerprint; the latter two can be used to verify a signature created using the private key.
1515

16-
When stored on disk, private keys can be stored in different formats. The modern, widely supported
17-
format is OPENSSH encoding, which supports all of `RSA`, `ECDSA`, and `Ed25519` keys. Some
18-
applications use the older `PKCS#8` format, which is more complex. Further, `PKCS#8` encoded
19-
`Ed25519` keys are not supported by openssh, and need to be converted to OPENSSH format before they
16+
When stored on disk private keys can be stored in different formats. The modern, widely supported
17+
format is `OPENSSH` encoding, which supports all of `RSA`, `ECDSA`, and `Ed25519` keys. Some
18+
applications use the older `PKCS#8` format which is more complex. Further, `PKCS#8` encoded
19+
`Ed25519` keys are not supported by OpenSSH and need to be converted to `OPENSSH` format before they
2020
can be used.
2121

2222
Private keys may be encrypted with a passphrase when stored on disk or left unprotected. When using
2323
a passphrase, the encryption key is derived from the passphrase using a
24-
[KDF](https://en.wikipedia.org/wiki/Key_derivation_function) such as bcrypt. SSH private keys can be
25-
encrypted using different ciphers (`AES-128`, `AES-192`, `AES-256`, `3DES`). Keys can be used
26-
directly by applications, but more commonly they are loaded and held in an SSH agent. An agents
27-
can - after decrypting - hold the keys in memory and provide signing capabilities. Keys can also be
28-
stored on hardware tokens like Yubikeys (`ed25519-sk`).
24+
[KDF](https://en.wikipedia.org/wiki/Key_derivation_function) such as `bcrypt`. SSH private keys can
25+
be encrypted using different ciphers -- `AES-128`, `AES-192`, `AES-256`, or `3DES`. Keys can be used
26+
directly by applications but more commonly they are loaded and held in an SSH agent. An agent can,
27+
after decrypting, hold the keys in memory and provide signing capabilities. Keys can also be stored
28+
on hardware tokens like YubiKeys (`ed25519-sk`).

0 commit comments

Comments
 (0)