HiddenSSH Config file, Cloud Firewall Single Node
Configured for running on a single node/server in cloud enviroment, with OpenSSH IP restrictions.
Note that this configuration works with public/private keys and not passowords.
Its 2026; You should be using security keys as an ssh agent, to protect your self against (key theft/unauthorized access), even using a file based public/private key is out dated in (secure environments/hardened/important servers).
Cloud-optimized SSHD config for single-node environments with IP-restricted user logins, hardened encryption, logging, and firewall integration.
#########################################################
# https://hiddenssh.com/cloud-single-node #
# #
# sshd_cloud_firewall_single_node #
# version 1.43 #
# Minor text edit fixes, and tweaks. #
# #
# Standard practice: keep a known-good recovery backup #
# https://hiddenssh.com/backup-sshd-config #
#########################################################
# Notes: if issues; run following commands.
# mkdir -p /run/sshd
# chmod 0755 /run/sshd
# chown root:root /run/sshd
# Network
# -------
# If you want to change the port on SELinux(enforcing mode);
# You need to change SELinux booleans, to allow this.
# semanage port -a -t ssh_port_t -p tcp 2222
# Port tcp/22, is priority traffic but depends usually on networks.
Port 22
Protocol 2
# Define inet; If you want to only listen on IPv4,
# keep in mind you need to firewall twice; rules for IPv4 & IPv6, if you use both IPv4 & IPv6 at the same time.
# This is NOT recommended!
# AddressFamily any = IPv4 & IPv6
# AddressFamily inet = IPv4
# AddressFamily inet6 = IPv6
AddressFamily inet
# Use dedicated IP for sshd; From a Different Network block,
# Trick from the 90s, credits "(Big Blue/IBM) worker".
# Seeing the IPv4 shortage today, this only works with IPv6 today.
# NOTE: Not recommended using (*/wildcard).
# *Change me*
ListenAddress 192.168.0.1
# (VPN) You need to listen to the IPv4 address inside the tunnel.
# Not recommended; adds chain of failure risk.
# *Change me*
#ListenAddress 10.0.0.1
TCPKeepAlive yes
# WARNING
AllowAgentForwarding no
# https://hiddenssh.com/ssh-socks5-proxy
AllowTcpForwarding no
# https://hiddenssh.com/ssh-tunnel
PermitTunnel yes
GatewayPorts no
# Firewall
# ---------
# https://hiddenssh.com/cloud-single-node see; OpenSSH Application Level Firewall.
# *Change me*
AllowUsers user1@192.168.0.10 user2@10.0.0.10
# Deamon
# -------
PidFile /var/run/sshd.pid
# Info
# ----
# Greating for brutforces, Shows up as.
# debug1: Remote protocol version 2.0, remote software version OpenSSH_8.7 HiddenSSH-cloud
# debug1: compat_banner: match: OpenSSH_8.7 HiddenSSH-cloud pat OpenSSH* compat
# *Change me*
VersionAddendum hiddenssh-cloud
# Print before login
#Banner /etc/ssh/login.txt
# Print /etc/motd at succesful login
PrintMotd yes
# Show last login IPs
PrintLastLog yes
# Encryption
# ----------
# Syntax: ssh -Q cipher check what Encryption Ciphers your sshd has been (compiled with/supports).
# aes256-cbc uses AES in cipher-block chaining (CBC) mode, which can be vulnerable to certain attacks if not used correctly.
# aes256-gcm@openssh.com uses AES in Galois/Counter Mode (GCM), which provides both encryption and authentication,
# making it resistant to certain types of attacks. However, it may not be as widely supported; use aes256-ctr if aes256-gcm@openssh.com breaks.
# twofish256-ctr is a good option but not supported by all systems
# chacha20-poly1305@openssh.com The ChaCha20 stream cipher is generally faster than AES, when without support for AES hardware acceleration.
# Run: cat /proc/cpuinfo to check the accelerators.
# Profile(Large data traffic):
#Ciphers aes128-gcm@openssh.com,aes256-gcm@openssh.com
# Profile(Best balance):
Ciphers aes256-gcm@openssh.com
# If you want to choose one MAC algorithm for the best security, hmac-sha2-512-etm@openssh.com would be the best choice.
MACs hmac-sha2-512-etm@openssh.com
# Profile(Hardware Security Key)
#KexAlgorithms curve25519-sha256@libssh.org
KexAlgorithms curve25519-sha256@libssh.org,diffie-hellman-group-exchange-sha256
# Public key types accepted
# NIST P-curves are possibly back-doored by the U.S. National Security Agency.
# ecdh-sha2-nistp256, ecdh-sha2-nistp384, ecdh-sha2-nistp521
# You should prerable ONLY use; ed25519 if possible.
# Profile(Hardware Security Key)
#PubkeyAcceptedKeyTypes ssh-ed25519-cert-v01@openssh.com
PubkeyAcceptedKeyTypes ssh-rsa,rsa-sha2-512,ssh-ed25519-cert-v01@openssh.com
# Profile(Hardware Security Key)
#PubkeyAcceptedKeyTypes ssh-ed25519-cert-v01@openssh.com
# Profile(Large data traffic):
#RekeyLimit 100G 1h
# Profile(Hardware Security Key)
#RekeyLimit 10G 8h
RekeyLimit 4G 1h
# SSH compression can leak secrets via side-channel attacks: if attacker-controlled text is compressed with secrets,
# output size changes reveal matching bytes, enabling gradual secret recovery.
# Profile(hardened): Disable compression.
Compression no
# Profile(Large data traffic):
#Compression delayed
# Hardening login
# ---------------
LoginGraceTime 2m
StrictModes yes
MaxAuthTries 5
MaxSessions 5
MaxStartups 10:30:100
ChallengeResponseAuthentication no
UseDNS yes
# Warning Will break some systems (Disables /etc/shadow file)
UsePAM no
PermitRootLogin no
DenyGroups root guest nobody ubuntu
# Never put this to yes!
PermitEmptyPasswords no
DenyUsers root admin administrator user test guest nobody ubuntu webmaster backup ftp ssh postgres mysql oracle tomcat apache www-data git docker mail pi
# Checks dead/unresponsive sessions, (0 = every X second).
ClientAliveInterval 0
ClientAliveCountMax 3
HostbasedAuthentication no
IgnoreUserKnownHosts yes
PermitTTY yes
# Needed for: (SCP/sshfs) (Disable if you dont use scp).
# Recommended: rsync -azvP -e "ssh" file.txt user1@host:/tmp/file.txt (No sftp needed)
Subsystem sftp /usr/libexec/openssh/sftp-server
# Logging
# -------
SyslogFacility AUTH
SyslogFacility AUTHPRIV
LogLevel info
# User Settings
# -------------
# With this option set to "yes", users can set arbitrary environment variables that can potentially
# override system settings/perform unauthorized actions.
# This can be especially dangerous if the user connecting via SSH has administrative privileges on the system.
# *Change me*
PermitUserEnvironment yes
Match user user1,user2
Match all
PermitUserEnvironment no
# Passwords are legacy and increasingly deprecated.
PasswordAuthentication no
PubkeyAuthentication yes
#PermitUserEnvironment yes
#Match user chroot-user
#ChrootDirectory /home/restricteduser
#ForceCommand internal-sftp
#AllowTcpForwarding no
#X11Forwarding no
#PermitTunnel no
# Passwords are legacy and increasingly deprecated.
#PasswordAuthentication no
#PubkeyAuthentication yes
# Chroot Jail
# https://members.hiddenssh.com/restricted-ssh
# A chroot jail restrict (user/service account/proces)s to a specific directory tree.
#ChrootDirectory /home/chroot-user/chroot/
# Allows SSH sessions to allocate a (terminal/normal interactive shell)
# With (process/service account) turn this off, for inviduall users with (Match User $USERNAME)
#PermitTTY no
# Environment variables
# ---------------------
# https://hiddenssh.com/sshd-env
# echo $hiddenssh
# env
AcceptEnv LC_IDENTIFICATION LC_ALL LANGUAGE
AcceptEnv XMODIFIERS
AcceptEnv hiddenssh oraclesecretkey oracleauthtoken cloudflaretoken openaikey
# Keys Settings
# -------------
# Root controlled Authorized Key files.
# AuthorizedKeysFile /etc/ssh/%u tells sshd to look for each user’s allowed SSH public keys in /etc/ssh/
# (e.g., /etc/ssh/user1) instead of ~/.ssh/authorized_keys.
# touch /etc/ssh/user1
# chmod 0644 /etc/ssh/user1
# chown root:root /etc/ssh/user1
# Profile(SELinux): chcon -v system_u:object_r:sshd_key_t:s0 /etc/ssh/user1 && restorecon -v /etc/ssh/user1
# Profile(OpenRC): /etc/init.d/sshd reload
# Profile(Systemd): systemctl reload sshd
#AuthorizedKeysFile /etc/ssh/%u
#
# Classic ~/.ssh/authorized_keys
AuthorizedKeysFile .ssh/authorized_keys .ssh/authorized_backup
#
# Certificate File
#TrustedUserCAKeys /etc/ssh/certificate-auth/user1-hiddenssh-cert.pub
# AuthorizedPrincipalsFile is mainly relevant when you use an SSH CA.
#AuthorizedPrincipalsFile none
# Centralized Authentication
# --------------------------
KerberosAuthentication no
#KerberosOrLocalPasswd no
#KerberosTicketCleanup no
#KerberosUseKuserok no
#GSSAPIAuthentication no
#GSSAPICleanupCredentials no
#GSSAPIStrictAcceptorCheck no
#GSSAPIStrictAcceptorCheck no
#GSSAPIKeyExchange no
#GSSAPIEnablek5users no
# Disables external key lookup helpers, such as scripts that fetch keys from LDAP, HTTP APIs, databases, etc. This reduces attack surface.
AuthorizedKeysCommandUser nobody
Iptables and firewall integration.
iptables -N ssh-ingress
iptables -A INPUT -j ssh-ingress
iptables -P INPUT DROP
iptables -A ssh-ingress -s 192.168.0.0/32 -d 192.168.0.1/32 -i Interface -p tcp -m tcp --dport 22 \
-m state --state NEW,RELATED,ESTABLISHED \
-m comment --comment "SSH client User1" -j ACCEPT
You need to match IPs in sshd_config and iptables,
because they work on different levels.
Iptables operates at the network/kernel level — it controls which source IPs can reach OpenSSH socket.
OpenSSH filters connections at the application level — it restricts which (IP/IPs) each user is allowed to login from.
Pay close attention to user1@ this part defines the user, rest defines the IP, this is specific for each user.
# Firewall
# --------- Invidually matched IPs to specific user
|
AllowUsers user1@192.168.0.10 user2@10.0.0.10 user3@1.1.1.*
| |
user1 must exist in /etc/passwords Wildcard allowing any IP in the .255 block
Note: Wildcards only work in the last block.
Pay close attention to ssh-ingress chain, and Policy of the CHAIN: DROP
Chain INPUT (policy DROP)
target prot opt source destination
ACCEPT 0 -- 0.0.0.0/0 0.0.0.0/0 ctstate RELATED,ESTABLISHED
ssh-ingress 2 -- 0.0.0.0/0 144.24.33.7 tcp dpt:22
Chain OUTPUT (policy DROP)
target prot opt source destination
ACCEPT 0 -- 0.0.0.0/0 0.0.0.0/0 ctstate ESTABLISHED /* NEEDED for 2 way communication */
Chain ssh-ingress (1 references)
target prot opt source destination
ACCEPT all -- 144.24.46.145/32 144.24.33.7/32 ctstate NEW,ESTABLISHED /* SSH Client User1 */
ACCEPT all -- 144.24.46.145/32 144.24.33.7/32 ctstate NEW,ESTABLISHED /* SSH Client User2 */