Secure Shell (ssh) Cheat Sheet and Guide

General Description of SSH

Secure Shell (SSH) is a cryptographic network protocol and network tool designed to provide secure communication over potentially insecure networks. Its primary purpose is to allow users and systems to log into remote machines, execute commands, and transfer files securely.

SSH achieves security through three core principles:

  1. Confidentiality – All traffic is encrypted, preventing eavesdropping.
  2. Integrity – Cryptographic checks ensure data is not altered in transit.
  3. Authentication – Both the client and server can verify each other’s identity.

SSH is most commonly used by system administrators, developers, and automation tools to manage servers remotely. It replaces legacy protocols such as telnet, rlogin, and ftp, which transmit credentials and data in plain text.

Typical uses include:

  • Remote login to servers for administration
  • Secure file transfers (SCP, SFTP) between systems
  • Remote command execution for administration
  • Port forwarding and tunnelling
  • Automation and orchestration
  • Acting as a secure transport for other applications

Understanding these use cases helps you choose the correct SSH options rather than relying on trial and error

By default, SSH listens on TCP port 22, though this can be changed for policy or security reasons.

 

Checking if SSH Is Installed

Before installing SSH, it is important to verify whether the SSH client and server are already present. Most modern UNIX and Linux systems include OpenSSH by default.

Checking the SSH Client

# ssh -V

This command prints the installed SSH client version. If SSH is installed correctly, you will see output similar to:

OpenSSH_9.0p1, OpenSSL 1.1.1k

If the command is not found, it indicates that the SSH client package is not installed or not in your PATH.

Checking the SSH Server (sshd)

The SSH daemon (sshd) is responsible for accepting incoming SSH connections.

# ps -ef | grep sshd

If sshd is running, it should appear in the process list. You can also test the configuration:

# ps -ef | grep sshd        (legacy)

# systemctl status sshd     (linux)

# service sshd status       (system V)

# svcs -l ssh              (Solaris)

 # sshd -T

This validates the server configuration and prints the effective settings.

 

Installing SSH

Red Hat Enterprise Linux (RHEL, Rocky, Alma, CentOS)

On Red Hat–based systems, SSH is provided by the OpenSSH packages.

# yum install openssh openssh-clients openssh-server (legacy)

# dnf install -y openssh openssh-clients openssh-server

  • openssh – core libraries
  • openssh-clients – ssh, scp, sftp
  • openssh-server – sshd daemon

After installation, enable and start the service:

# systemctl enable sshd

# systemctl start sshd

Verify that the service is running:

# systemctl status sshd

 

Solaris (Oracle Solaris 11+)

Solaris includes OpenSSH as a managed service.

Check whether SSH is installed:

# pkg info service/network/ssh

Install if necessary:

# pkg install service/network/ssh

Enable the SSH service using SMF:

# svcadm enable ssh

Confirm service state:

# svcs ssh

 

Basic SSH Command Usage

Remote Login

$ ssh [options] user@hostname

This command establishes an encrypted session to the remote host and spawns a shell after authentication.

Using a Non-Default Port

$ ssh -p 2222 user@hostname

Commonly Used Options:

-p  Specify port (default is 22)-I  Specify a private key for authentication-v  Verbose mode for debugging 

Executing a Single Remote Command

$ ssh user@host “uptime”

This is useful for scripting and monitoring, as it avoids starting an interactive shell.

 

Secure File Transfers

SCP (Secure Copy)

SCP copies files over SSH, inheriting SSH’s authentication and encryption.

$ scp file.txt user@host:/remote/path/

Recursive directory copy:

$ scp -r dir/ user@host:/remote/path/

SFTP (Secure FTP)

SFTP provides an interactive file transfer interface similar to FTP but fully encrypted.

$ sftp user@host

This is preferred over SCP for frequent or interactive file operations.

 

The ~/.ssh Directory and File Permissions

SSH relies heavily on files stored in the user’s ~/.ssh directory. Incorrect permissions are one of the most common causes of SSH failures.

~/.ssh/├── id_rsa├── id_rsa.pub├── authorized_keys├── known_hosts├── config

Important Files in .ssh:

id_rsa         Private key (should be kept secret)id_rsa.pub    Public key (can be shared with others)authorized_keys      List of public keys that are allowed for authenticationconfig         Custom ssh client configuration fileknown_hosts   Stores the fingerprints of known ssh servers

Recommended permissions:

chmod 700 ~/.ssh

chmod 600 ~/.ssh/id_rsa ~/.ssh/authorized_keys

chmod 644 ~/.ssh/id_rsa.pub

  • Private keys must never be readable by others
  • SSH will refuse to use keys if permissions are too open

 

Creating SSH Key Pairs

Key-based authentication is more secure and more convenient than passwords.

$ ssh-keygen -t rsa -b 4096

$ ssh-keygen -t rsa -b 2048 -f ~/.ssh/id_rsa

$ ssh-keygen -t ed25519 -C “user@host”

You will be prompted for a passphrase. Using a passphrase protects your private key if it is stolen.

If you specify ‘rsa’ key type, this will generate a private key (id_rsa) and a public key (id_rsa.pub).

RSA keys are generally most commonly used and good enough for most situations.

Ed25519 keys are preferred because they are:

  • Faster
  • More secure
  • Shorter in length

 

Passwordless SSH Logins

Passwordless login means authentication occurs using cryptographic keys instead of typed passwords.

The process is as follows:

  1. Generate a key pair (private and public).
  2. The public key is placed on the remote server in the ~/.ssh/authorized_keys file.
  3. When connecting, ssh uses the public key to challenge the local private key.
  4. Copy the public key to the server using ssh-copy-id or manually copy it into the ~/.ssh/authorized_keys file on the remote machine.
  5. When you use ssh user@hostname, you won’t be prompted for a password. If the private key matches the public key, authentication succeeds.

Copy Public Key to Remote Server:

$ cat id_rsa.pub | ssh user@host “mkdir -p ~/.ssh && cat >> ~/.ssh/authorized_keys” or  $ ssh-copy-id user@host

This command appends your public key to the remote user’s authorized_keys file.

Test it:

$ ssh user@host

Once configured, SSH will authenticate automatically using your private key.

 

Keys, Ciphers, and Key Exchange Algorithms

SSH security depends on multiple cryptographic components:

Key Types

  • RSA – Widely supported, but requires large key sizes
  • ECDSA – Less recommended due to implementation concerns
  • ED25519 – Best current choice

Ciphers

Ciphers encrypt the session data after authentication.

Recommended:

  • chacha20-poly1305
  • aes256-gcm

Key Exchange Algorithms

Key exchange securely negotiates a shared secret.

Recommended:

  • curve25519-sha256

Avoid legacy algorithms such as SHA-1–based Diffie-Hellman.

 

SSH Client Configuration (ssh_config)

Client configuration simplifies repeated connections. This file contains settings that affect all ssh client sessions.

File locations:

 

/etc/ssh/ssh_config

~/.ssh/config

 

Example entries:

 

Host myserver    HostName 192.168.1.10    User username    Port 22    IdentityFile ~/.ssh/id_rsa

This prevents mistakes and reduces command complexity.

 

SSH Server Configuration (sshd_config)

The server configuration controls authentication, encryption, and access policy.

File locations:

 

/etc/ssh/sshd_config

 

Example entries:

 Port 22PermitRootLogin noPasswordAuthentication noPubkeyAuthentication yesAllowUsers admin ops

Disabling password authentication greatly reduces brute-force risk.

 

Advanced SSH Use Case: Port Forwarding (Tunneling)

SSH tunnels securely forward traffic through an encrypted channel.

Local Port Forwarding

$ ssh -L 8080:localhost:80 user@remote

This allows access to a remote web service as if it were local. ie forward a local port to a remote host.

Remote Port Forwarding

$ ssh -R 9090:localhost:22 user@remote

This is the reverse ie forward a remote port to a local host.

Dynamic Forwarding (SOCKS Proxy)

$ ssh -D 1080 user@remote

Creates a SOCKS proxy, often used for secure browsing.

 

Advanced SSH Use Case: Jump Hosts and Bastion Hosts

Jump hosts provide controlled access to internal systems ie allows you to connect to a remote host via an intermediary server.

$ ssh -J user@bastion user@target and optional config file: Host target    HostName 10.0.0.10    User admin    ProxyJump user@bastion

This avoids exposing internal servers directly to the internet.

 

Advanced SSH Use Case: SSH Proxies

 

ssh -o ProxyCommand=”ssh -W %h:%p user@proxy” user@target

 

 

Advanced SSH Use Case: Advanced Algorithm Configuration

ssh supports different key exchange methods (KEX) for secure communication:

  • diffie-hellman-group14-sha1
  • ecdh-sha2-nistp256
  • curve25519-sha256@libssh.org

Client-side:

$ ssh -o KexAlgorithms=curve25519-sha256 user@host

Server-side Config file:

Host myserver

KexAlgorithms curve25519-sha256, ecdh-sha2-nistp256

Ciphers chacha20-poly1305,aes256-gcm

 

Troubleshooting SSH

This section focuses on understanding what is happening on the wire when SSH fails. SSH problems often fall into three layers:

  1. Network layer (TCP/IP) – packets not reaching the server
  2. Transport / cryptographic layer – key exchange or cipher negotiation failures
  3. Authentication / session layer – user or key-related issues

Using packet captures alongside SSH verbose output allows you to clearly identify which layer is failing.

 

Using Verbose Mode (SSH Perspective)

Verbose mode shows each major SSH phase:

  1. TCP connection attempt
  2. Protocol version exchange
  3. Key exchange (KEX)
  4. Authentication
  5. Session setup

$ ssh -vvv user@host

If the output stops before SSH2_MSG_KEXINIT, the problem is almost always network-related.

ssh Connection Success:

$ ssh user@192.168.1.10Welcome to Ubuntu 20.04 LTSLast login: Fri Apr  7 14:15:35 2025 from 192.168.1.5

ssh Verbose Output:

$ ssh -v user@192.168.1.10Openssh_8.4p1 Debian-5, OpenSSL 1.1.1k  25 Mar 2021debug1: Reading configuration data /etc/ssh/ssh_configdebug1: Connecting to 192.168.1.10 [192.168.1.10] port 22.debug1: Connection established.

 

Permissions Problems

Common Errors:

  • Permission Denied (publickey): This error usually happens when the remote server cannot verify your key. Check that your public key is in the correct place and that the permissions are correct.
  • Connection Refused: This can happen if the ssh server is not running, or if it’s running on a different port.
  • Host Key Verification Failed: This happens when the remote host’s key has changed. You can remove the old key from ~/.ssh/known_hosts.

How to Fix Permission Denied (publickey):

  • Ensure that the private key permissions are set to 600:

$ chmod 600 ~/.ssh/id_rsa 

Ensure the public key is properly added to the authorized_keys file.

 

Capturing SSH Traffic with tcpdump

To observe SSH at the packet level, capture traffic on the client or server.

Basic capture

 

# tcpdump -i eth0 port 22 -nn -vv

  • -nn prevents DNS and service name resolution
  • -vv increases protocol detail

For deeper analysis, save to a file:

# tcpdump -i eth0 port 22 -w ssh_capture.pcap

This file can be analyzed with Wireshark.

 

TCP 3-Way Handshake Analysis

A healthy SSH connection starts with a successful TCP handshake:

Client → Server : SYNServer → Client : SYN-ACKClient → Server : ACK 

Sample tcpdump output (successful handshake)

 

IP 10.0.0.5.54321 > 10.0.0.10.22: Flags [S]IP 10.0.0.10.22 > 10.0.0.5.54321: Flags [S.]IP 10.0.0.5.54321 > 10.0.0.10.22: Flags [.]  

Common problems

  1. SYN sent, no SYN-ACK returned

IP 10.0.0.5.54321 > 10.0.0.10.22: Flags [S](repeated)

What this means:

  • Firewall blocking port 22
  • SSH daemon not running
  • Routing issue

Fixes:

  • Check firewall rules (iptables, firewalld, network ACLs)
  • Confirm sshd is listening (ss -lntp | grep :22)

 

  1. SYN-ACK returned, then RST

IP 10.0.0.10.22 > 10.0.0.5.54321: Flags [R]

What this means:

  • Service actively refusing connection
  • TCP wrappers or security software rejecting client

 

SSH Protocol Banner Exchange

After TCP handshake, SSH exchanges protocol banners:

SSH-2.0-OpenSSH_9.0 

Packet capture view

 

Client → Server: SSH-2.0-OpenSSH_9.0Server → Client: SSH-2.0-OpenSSH_7.4

Problems at this stage usually indicate:

  • Middleboxes modifying traffic
  • Non-SSH service on port 22

If no banner is returned, SSH will appear to hang.

 

Key Exchange (KEX) Failures / Incompatible Algorithms

Key exchange negotiates algorithms and establishes encryption.

Typical failure message

 

no matching key exchange method found 

Packet capture indicators

In Wireshark, look for:

  • SSH2_MSG_KEXINIT
  • Lists of supported algorithms

If the client sends KEXINIT but the server immediately closes the connection, it usually indicates:

  • Legacy server
  • Disabled algorithms

Temporary workaround:

$ ssh -o KexAlgorithms=+diffie-hellman-group14-sha256 user@host

Long-term fix: upgrade the server or explicitly configure supported algorithms.

 

Cipher and MAC Mismatch

After key exchange, SSH negotiates:

  • Encryption cipher
  • MAC (message authentication code)

Capture symptoms

  • Connection closes immediately after KEX
  • No authentication attempt seen

Verbose output may show:

no matching cipher found

This is common when modern clients connect to hardened or very old servers.

 

Authentication Failures (Packet-Level)

At this stage, encryption is already active.

You will not see credentials, but you can infer failures by:

  • Repeated SSH2_MSG_USERAUTH_REQUEST
  • Server responding with SSH2_MSG_USERAUTH_FAILURE

Common causes:

  • Public key not in authorized_keys
  • Wrong user
  • Incorrect file permissions

 

Packet Drops and Retransmissions

In tcpdump or Wireshark, look for:

  • TCP retransmissions
  • Duplicate ACKs

These indicate:

  • Packet loss
  • MTU issues
  • Network congestion

SSH symptoms:

  • Very slow login
  • Session freezes

Fixes:

  • Check interface errors
  • Validate MTU consistency
  • Test with ping -M do -s <size>

 

MTU and Fragmentation Issues

SSH is sensitive to MTU mismatches, especially during key exchange.

Symptoms:

  • Connection hangs during login
  • Works on one network but not another

Packet capture shows:

  • ICMP fragmentation-needed messages
  • Missing large packets

Workaround:

$ ssh -o IPQoS=lowdelay user@host

 

Common Troubleshooting Workflow

  1. Confirm TCP handshake with tcpdump
  2. Verify SSH banner exchange
  3. Inspect KEX negotiation
  4. Check authentication attempts
  5. Correlate with ssh -vvv output

This layered approach prevents random configuration changes and leads to faster resolution.

 

Common Mistakes and Fixes

 

Problem

Explanation

Fix

SSH ignores key

Permissions too open

chmod files

Password prompt still appears

Key not installed

Check authorized_keys

Connection timeout

Network/firewall issue

Check port and routing

Algorithm error

Old server

Adjust Kex temporarily

 

Security Best Practices

  • Prefer Ed25519 keys
  • Disable password authentication
  • Use bastion hosts
  • Regularly audit authorized_keys
  • Keep OpenSSH updated

 

Command Reference Summary

 

ssh user@hostssh -i key user@hostssh -L local:remote user@hostssh -D 1080 user@hostscp file user@host:/path

 

Final Notes

ssh is an essential tool for securely accessing and managing remote systems. By understanding key management, configuring the ssh server, and utilizing advanced features like tunnelling and proxies, you can effectively manage systems securely. Troubleshooting common errors and understanding configurations will help you maintain a secure and functional environment.

Check out our other Cheat Sheets and Blogs and if you would like us to write a cheat sheet for you, for FREE, (and we find it suitable) Contact Us.