OpenSSH ships with a default configuration that prioritizes high compatibility. However, this compatibility comes at a price: some of the included ciphers and algorithms may be outdated or contain known vulnerabilities. To strengthen the encryption and gain a transparent overview of known weaknesses, ssh-audit is the essential auditing tool.
My hardening strategy uses the Mozilla Security Guidelines on OpenSSH as a base, which I then refined using the specific findings from ssh-audit
.
Part I: Initial Server Hardening and Auditing
Before tuning algorithms, I enforce core security policy: limiting access to specific users, disabling root login, and preventing password authentication.
AuthenticationMethods publickey
PermitRootLogin no
# AllowUsers replace-with-your-usernames,separate-by-comma
1. Installation and Usage of ssh-audit
I use pip3
to install and maintain ssh-audit
to ensure I have the most current version, which is necessary for accurate vulnerability assessment.
Server Audit (Debian 12 Default) Output: Running ssh-audit localhost on a default installation reveals critical weaknesses. The output serves as our baseline:
# general
(gen) banner: SSH-2.0-OpenSSH_9.2p1 Debian-2+deb12u2
(gen) software: OpenSSH 9.2p1
(gen) compatibility: OpenSSH 8.5+, Dropbear SSH 2018.76+
(gen) compression: enabled (zlib@openssh.com)
# key exchange algorithms
(kex) sntrup761x25519-sha512@openssh.com -- [info] available since OpenSSH 8.5
(kex) curve25519-sha256 -- [info] available since OpenSSH 7.4, Dropbear SSH 2018.76
`- [info] default key exchange since OpenSSH 6.4
(kex) curve25519-sha256@libssh.org -- [info] available since OpenSSH 6.4, Dropbear SSH 2013.62
`- [info] default key exchange since OpenSSH 6.4
(kex) ecdh-sha2-nistp256 -- [fail] using elliptic curves that are suspected as being backdoored by the U.S. National Security Agency
`- [info] available since OpenSSH 5.7, Dropbear SSH 2013.62
(kex) ecdh-sha2-nistp384 -- [fail] using elliptic curves that are suspected as being backdoored by the U.S. National Security Agency
`- [info] available since OpenSSH 5.7, Dropbear SSH 2013.62
(kex) ecdh-sha2-nistp521 -- [fail] using elliptic curves that are suspected as being backdoored by the U.S. National Security Agency
`- [info] available since OpenSSH 5.7, Dropbear SSH 2013.62
(kex) diffie-hellman-group-exchange-sha256 (3072-bit) -- [info] available since OpenSSH 4.4
`- [info] OpenSSH's GEX fallback mechanism was triggered during testing. Very old SSH clients will still be able to create connections using a 2048-bit modulus, though modern clients will use 3072. This can only be disabled by recompiling the code (see https://github.com/openssh/openssh-portable/blob/V_9_4/dh.c#L477).
(kex) diffie-hellman-group16-sha512 -- [info] available since OpenSSH 7.3, Dropbear SSH 2016.73
(kex) diffie-hellman-group18-sha512 -- [info] available since OpenSSH 7.3
(kex) diffie-hellman-group14-sha256 -- [warn] 2048-bit modulus only provides 112-bits of symmetric strength
`- [info] available since OpenSSH 7.3, Dropbear SSH 2016.73
(kex) kex-strict-s-v00@openssh.com -- [info] pseudo-algorithm that denotes the peer supports a stricter key exchange method as a counter-measure to the Terrapin attack (CVE-2023-48795)
# host-key algorithms
(key) rsa-sha2-512 (2048-bit) -- [warn] 2048-bit modulus only provides 112-bits of symmetric strength
`- [info] available since OpenSSH 7.2
(key) rsa-sha2-256 (2048-bit) -- [warn] 2048-bit modulus only provides 112-bits of symmetric strength
`- [info] available since OpenSSH 7.2
(key) ecdsa-sha2-nistp256 -- [fail] using elliptic curves that are suspected as being backdoored by the U.S. National Security Agency
`- [warn] using weak random number generator could reveal the key
`- [info] available since OpenSSH 5.7, Dropbear SSH 2013.62
(key) ssh-ed25519 -- [info] available since OpenSSH 6.5
# encryption algorithms (ciphers)
(enc) chacha20-poly1305@openssh.com -- [info] available since OpenSSH 6.5
`- [info] default cipher since OpenSSH 6.9
(enc) aes128-ctr -- [info] available since OpenSSH 3.7, Dropbear SSH 0.52
(enc) aes192-ctr -- [info] available since OpenSSH 3.7
(enc) aes256-ctr -- [info] available since OpenSSH 3.7, Dropbear SSH 0.52
(enc) aes128-gcm@openssh.com -- [info] available since OpenSSH 6.2
(enc) aes256-gcm@openssh.com -- [info] available since OpenSSH 6.2
# message authentication code algorithms
(mac) umac-64-etm@openssh.com -- [warn] using small 64-bit tag size
`- [info] available since OpenSSH 6.2
(mac) umac-128-etm@openssh.com -- [info] available since OpenSSH 6.2
(mac) hmac-sha2-256-etm@openssh.com -- [info] available since OpenSSH 6.2
(mac) hmac-sha2-512-etm@openssh.com -- [info] available since OpenSSH 6.2
(mac) hmac-sha1-etm@openssh.com -- [fail] using broken SHA-1 hash algorithm
`- [info] available since OpenSSH 6.2
(mac) umac-64@openssh.com -- [warn] using encrypt-and-MAC mode
`- [warn] using small 64-bit tag size
`- [info] available since OpenSSH 4.7
(mac) umac-128@openssh.com -- [warn] using encrypt-and-MAC mode
`- [info] available since OpenSSH 6.2
(mac) hmac-sha2-256 -- [warn] using encrypt-and-MAC mode
`- [info] available since OpenSSH 5.9, Dropbear SSH 2013.56
(mac) hmac-sha2-512 -- [warn] using encrypt-and-MAC mode
`- [info] available since OpenSSH 5.9, Dropbear SSH 2013.56
(mac) hmac-sha1 -- [fail] using broken SHA-1 hash algorithm
`- [warn] using encrypt-and-MAC mode
`- [info] available since OpenSSH 2.1.0, Dropbear SSH 0.28
# fingerprints
(fin) ssh-ed25519: SHA256:---
(fin) ssh-rsa: SHA256:---
# algorithm recommendations (for OpenSSH 9.2)
(rec) -ecdh-sha2-nistp256 -- kex algorithm to remove
(rec) -ecdh-sha2-nistp384 -- kex algorithm to remove
(rec) -ecdh-sha2-nistp521 -- kex algorithm to remove
(rec) -ecdsa-sha2-nistp256 -- key algorithm to remove
(rec) -hmac-sha1 -- mac algorithm to remove
(rec) -hmac-sha1-etm@openssh.com -- mac algorithm to remove
(rec) !rsa-sha2-256 -- key algorithm to change (increase modulus size to 3072 bits or larger)
(rec) !rsa-sha2-512 -- key algorithm to change (increase modulus size to 3072 bits or larger)
(rec) -diffie-hellman-group14-sha256 -- kex algorithm to remove
(rec) -hmac-sha2-256 -- mac algorithm to remove
(rec) -hmac-sha2-512 -- mac algorithm to remove
(rec) -umac-128@openssh.com -- mac algorithm to remove
(rec) -umac-64-etm@openssh.com -- mac algorithm to remove
(rec) -umac-64@openssh.com -- mac algorithm to remove
# additional info
(nfo) For hardening guides on common OSes, please see: <https://www.ssh-audit.com/hardening_guides.html>
(nfo) Be aware that, while this target properly supports the strict key exchange method (via the kex-strict-?-v00@openssh.com marker) needed to protect against the Terrapin vulnerability (CVE-2023-48795), all peers must also support this feature as well, otherwise the vulnerability will still be present. The following algorithms would allow an unpatched peer to create vulnerable SSH channels with this target: chacha20-poly1305@openssh.com. If any CBC ciphers are in this list, you may remove them while leaving the *-etm@openssh.com MACs in place; these MACs are fine while paired with non-CBC cipher types.
Part II: Mitigating Weak Cryptography
1. Hardening Diffie-Hellman (GEX) Moduli
I use awk
to filter the /etc/ssh/moduli
file to enforce a minimum size of 3072 bits, eliminating low-strength moduli.
awk '$5 >= 3071' /etc/ssh/moduli > /etc/ssh/moduli.tmp && mv /etc/ssh/moduli.tmp /etc/ssh/moduli
2. Replacing Host Keys
I replace the default host keys with stronger settings, which is essential for modern security. The Ed25519 key is the current gold standard for key exchange performance and security.
rm /etc/ssh/ssh_host_*
ssh-keygen -t rsa -b 4096 -f /etc/ssh/ssh_host_rsa_key -N ""
ssh-keygen -t ed25519 -f /etc/ssh/ssh_host_ed25519_key -N ""
3. Finalizing the SSHD Configuration
I explicitly define the allowed algorithms in a dedicated drop-in file (/etc/ssh/sshd_config.d/ciphers.conf
) to ensure that only the secure algorithms identified by ssh-audit
remain.
# /etc/ssh/sshd_config.d/ciphers.conf
# Ciphers
HostKeyAlgorithms ssh-ed25519-cert-v01@openssh.com,ssh-ed25519,rsa-sha2-512,rsa-sha2-256
KexAlgorithms curve25519-sha256@libssh.org,curve25519-sha256,sntrup761x25519-sha512@openssh.com,diffie-hellman-group-exchange-sha256,diffie-hellman-group16-sha512,diffie-hellman-group18-sha512
Ciphers chacha20-poly1305@openssh.com,aes256-gcm@openssh.com,aes128-gcm@openssh.com,aes256-ctr,aes192-ctr,aes128-ctr
MACs hmac-sha2-512-etm@openssh.com,hmac-sha2-256-etm@openssh.com,umac-128-etm@openssh.com
Part III: Auditing Clients and Avoiding Pitfalls
1. Client-Side Hardening
I recommend applying a strong default set of algorithms to the client’s ~/.ssh/config
file to reduce its attack surface, overriding weak defaults when connecting to external hosts.
# ~/.ssh/config
Host *
HashKnownHosts yes
HostKeyAlgorithms ssh-ed25519-cert-v01@openssh.com,ssh-ed25519
KexAlgorithms curve25519-sha256@libssh.org,curve25519-sha256,diffie-hellman-group16-sha512,...
Ciphers chacha20-poly1305@openssh.com,aes256-gcm@openssh.com,aes128-gcm@openssh.com,...
MACs hmac-sha2-512-etm@openssh.com,hmac-sha2-256-etm@openssh.com,umac-128-etm@openssh.com
2. Defense Tool Context (RKhunter and Lynis)
When using system auditing tools, I recognize that their checks can be incomplete or based on outdated assumptions.
- RKhunter Context: RKhunter incorrectly read the active drop-in configuration (
sshd_config.d
), confirming the necessity of manual verification. - Lynis Context: Changing port 22 or disabling modern compression offers minimal additional protection on systems already hardened with public-key authentication. Do not apply settings blindly.
3. Reducing Service Footprint (Defense-in-Depth)
Finally, I hide the OpenSSH version for minor defense-in-depth:
Plaintext
# /etc/ssh/sshd_config.d/other.conf
Banner none
DebianBanner no
This reduces the public information available to automated scanners.
Sources / See Also
- Mozilla Security Guidelines. OpenSSH Recommended Configuration.
https://wiki.mozilla.org/Security/Guidelines/OpenSSH
- SSH-Audit. SSH Hardening Guides for Common OSes.
https://www.ssh-audit.com/hardening_guides.html
- OpenSSH. Release Notes for OpenSSH 7.4 (Removal of pre-auth compression).
https://www.openssh.com/txt/release-7.4
- OpenSSH. Release Notes for OpenSSH 4.2 (Delayed compression).
https://www.openssh.com/txt/release-4.2
- GitHub (OpenSSH Portable). Source Code Reference for GEX fallback mechanism.
https://github.com/openssh/openssh-portable/blob/V_9_4/dh.c#L477
- CISOfy Lynis. Control Reference for SSH Hardening (SSH-7408).
https://cisofy.com/controls/SSH-7408/