SyntaxStudy
Sign Up
Linux / Bash SSH Config, Tunnels, and Port Forwarding
Linux / Bash Beginner 1 min read

SSH Config, Tunnels, and Port Forwarding

The SSH client configuration file at `~/.ssh/config` allows you to define aliases and per-host settings, eliminating the need to remember hostnames, ports, usernames, and key paths for every server. Each `Host` block in the config matches connection attempts by alias or pattern and applies the specified settings. This transforms long commands like `ssh -i ~/.ssh/work_key -p 2222 alice@192.168.1.50` into simply `ssh myserver`. SSH tunnelling creates encrypted channels that forward TCP traffic between machines. Local port forwarding (`-L`) creates a local port that tunnels to a remote destination through the SSH server — useful for accessing internal services securely. Remote port forwarding (`-R`) exposes a local service through the SSH server. Dynamic port forwarding (`-D`) creates a SOCKS proxy. SSH multiplexing with `ControlMaster` settings reuses an existing SSH connection for new sessions, dramatically reducing connection latency for frequent reconnects. The `ServerAliveInterval` and `ServerAliveCountMax` settings prevent idle connections from being dropped by firewalls or NAT devices.
Example
# ---- ~/.ssh/config ----
# Create or edit the config file
# cat ~/.ssh/config

# Example configuration:
# Host myserver
#     HostName 192.168.1.50
#     User alice
#     Port 2222
#     IdentityFile ~/.ssh/id_ed25519
#     ServerAliveInterval 60
#     ServerAliveCountMax 3

# Host bastion
#     HostName bastion.example.com
#     User ec2-user
#     IdentityFile ~/.ssh/aws_key.pem

# Host internal-db
#     HostName 10.0.1.15
#     User dbadmin
#     ProxyJump bastion

# Host *
#     AddKeysToAgent yes
#     IdentityFile ~/.ssh/id_ed25519
#     ControlMaster auto
#     ControlPath ~/.ssh/sockets/%r@%h:%p
#     ControlPersist 10m

# Connect using alias
ssh myserver
ssh internal-db    # Automatically hops through bastion

# ---- Port Forwarding ----

# Local port forwarding: access remote MySQL locally
# Forwards localhost:3307 to db-server:3306 via gateway
ssh -L 3307:db-server:3306 gateway.example.com
# Then: mysql -h 127.0.0.1 -P 3307 -u user -p

# Remote port forwarding: expose local web server
# Forwards remote:8080 to localhost:3000
ssh -R 8080:localhost:3000 server.example.com

# Dynamic forwarding (SOCKS5 proxy on port 1080)
ssh -D 1080 -N gateway.example.com

# Keep tunnel alive in background
ssh -fNL 3307:db-server:3306 gateway.example.com
# -f = background, -N = no remote command