Remote Support Start download

Linux Server Hardening: 15-Minute Checklist

LinuxSecurityHardeningServer
Linux Server Hardening: 15-Minute Checklist

A freshly installed Linux server is usable by default — but not hardened. Anyone who puts it on the internet unchanged runs with default SSH configuration, without a firewall, without automatic security updates and with root as a real account. That is not acceptable in 2026, not even for internal servers.

The good news: the most important hardening steps can be done in about 15 minutes. This checklist covers ten areas — for each step the most important command or config snippet. For deeper coverage we have the more detailed article Linux server hardening: measures on our site.

The checklist fits Debian 12/13, Ubuntu 24.04/26.04 LTS and Rocky/RHEL 9. Adapt commands to your distribution where needed.

1. SSH Hardening — the Most Important Point

SSH is the most common attack surface. In /etc/ssh/sshd_config or better in a file under /etc/ssh/sshd_config.d/99-hardening.conf:

PermitRootLogin no
PasswordAuthentication no
PubkeyAuthentication yes
AllowUsers admin1 admin2
MaxAuthTries 3
LoginGraceTime 30
ClientAliveInterval 300
ClientAliveCountMax 2

Prerequisite: the admin user’s SSH public key is in ~/.ssh/authorized_keys. Then systemctl restart sshd. Important: keep the current SSH session open and test login with a second SSH session before closing the first.

In addition: enable fail2ban as basic brute-force protection — see our templates Linux Fail2ban: jail templates for SMBs.

2. Automatic Security Updates

On Debian/Ubuntu:

apt install unattended-upgrades
dpkg-reconfigure -plow unattended-upgrades

In /etc/apt/apt.conf.d/50unattended-upgrades ensure that security updates are active. On Rocky/RHEL:

dnf install dnf-automatic
systemctl enable --now dnf-automatic.timer

Configuration in /etc/dnf/automatic.conf — set apply_updates = yes, at least for security updates.

3. Firewall: ufw or nftables

Minimal sensible ufw configuration:

ufw default deny incoming
ufw default allow outgoing
ufw allow 22/tcp comment 'SSH'
ufw enable

Only allow further ports if the server actually offers them (e.g. 80/443 for web). On Rocky/RHEL you use firewalld instead; the principle is identical.

Those who want to configure nftables directly have more control — for most SMB servers ufw as a wrapper is enough.

4. Auditing — What Happens on the System?

Light auditing: centralising journald is enough for many SMBs. For more, use auditd:

apt install auditd

Most important default rules for SMBs in /etc/audit/rules.d/hardening.rules:

-w /etc/passwd -p wa -k user-modify
-w /etc/shadow -p wa -k credential-modify
-w /etc/ssh/sshd_config -p wa -k ssh-config
-w /var/log/lastlog -p wa -k logins
-a always,exit -F arch=b64 -S execve -F euid=0 -k root-exec

Then augenrules --load. Output is queried with ausearch and aureport. For central evaluation forward logs to Loki/Grafana — see step 9.

5. Sudo Instead of Root — NOPASSWD Tightly Scoped

Direct root login should be off-limits (see SSH hardening). Use sudo instead:

usermod -aG sudo admin1

In /etc/sudoers.d/admin1:

admin1 ALL=(ALL) ALL

If NOPASSWD is required (for automation), only for specific commands, not globally:

deploy ALL=(ALL) NOPASSWD: /usr/bin/systemctl restart myapp

Never deploy ALL=(ALL) NOPASSWD: ALL — that is effectively a root account without authentication.

6. System Limits — Protection Against Fork Bombs and Resource Exhaustion

In /etc/security/limits.d/hardening.conf:

* hard nproc 10000
* hard nofile 65536
* soft nofile 32768
* hard core 0

hard nproc limits processes per user, hard core disables core dumps (preventing sensitive memory contents from ending up on disk). For DBMS, Java servers etc. adjust service-specific limits.

7. Disable Useless Services

A server image often runs services that are not needed. List them with:

systemctl list-unit-files --state=enabled --type=service

Typical candidates to mask (not just disable — masking prevents accidental re-enablement):

systemctl mask bluetooth.service
systemctl mask cups.service
systemctl mask avahi-daemon.service

Before masking, check whether the service is really not needed (e.g. CUPS should obviously stay active on a print server).

8. Time Synchronisation: chrony Instead of ntpd

Correct time is the foundation for logs, auditing, Kerberos, TLS certificates. chrony is the standard in 2026:

apt install chrony
systemctl enable --now chrony

In /etc/chrony/chrony.conf use trusted sources — e.g. the PTB (German national metrology institute) for German servers:

server ptbtime1.ptb.de iburst
server ptbtime2.ptb.de iburst
server ptbtime3.ptb.de iburst

Check status with chronyc tracking and chronyc sources -v.

9. Centralise Logging

Local logs are not trustworthy in an incident — attackers can delete them. Centralisation is mandatory. Variant with rsyslog/journald to Loki:

In /etc/systemd/journald.conf:

ForwardToSyslog=yes

Then rsyslog/promtail/vector to the Loki server. Those without a Loki stack can also work with a central syslog server (classic via UDP/TCP-514 or better RELP). See our in-depth practice article Grafana, Prometheus, Loki: self-hosted stack.

For an SMB quick start: every server sends its logs to a central Loki container, Grafana displays them. 30 minutes of setup, years of value.

10. Kernel Hardening via sysctl

In /etc/sysctl.d/99-hardening.conf a proven snippet:

# IP stack
net.ipv4.tcp_syncookies=1
net.ipv4.conf.all.rp_filter=1
net.ipv4.conf.all.accept_source_route=0
net.ipv4.conf.all.accept_redirects=0
net.ipv4.conf.all.send_redirects=0
net.ipv4.conf.all.log_martians=1
net.ipv6.conf.all.accept_source_route=0
net.ipv6.conf.all.accept_redirects=0

# Address space layout randomisation
kernel.randomize_va_space=2

# Hide pointer addresses in /proc
kernel.kptr_restrict=2

# Restrict dmesg
kernel.dmesg_restrict=1

# YAMA ptrace protection
kernel.yama.ptrace_scope=1

Activate with sysctl --system. Each value has a purpose — those who understand it can disable specific ones if applications report problems.

Bonus: Boot Loader and Disk Encryption

Beyond the 15-minute list but sensible, just not in the quick package:

  • Set GRUB password (prevents bootloader manipulation)
  • LUKS encryption on system partitions for hardware-theft resilience
  • Enable Secure Boot when UEFI is present
  • Keep SELinux / AppArmor in enforcing mode (default on RHEL/Rocky/Ubuntu)

These are more 60-minute topics — important for production, but not for the quick first hardening.

What This Checklist Does NOT Replace

Honestly: hardening is never “done”. This 15-minute list covers the basics. What else must at least be in place:

  • Regular vulnerability scanning (e.g. with Lynis as quick audit)
  • Patch management process documented (see also Cyber insurance 2026)
  • Backup of the server (/etc, databases, application data)
  • Monitoring of the most important indicators (CPU, RAM, disk, login anomalies)
  • Incident response plan for what to do on suspected compromise

Running Lynis once (apt install lynis && lynis audit system) gives you a score and concrete further recommendations — a good starting point for phase 2.

Conclusion

Ten steps, about 15 minutes per server — and a freshly installed Linux server is significantly harder than the default. The list is not a “maximum security concept”, but the minimum every productive server should have in 2026. Every step is explainable, every command available in standard distributions, no voodoo.

For deeper hardening — SELinux customisation, kernel live patching, compliance-conformant hardening to CIS benchmarks — there are further tools and concepts. But the foundation are the ten points above. Anyone who applies them consistently to every new server gains a significant security advantage over default installations.

DATAZONE automates this hardening via Ansible roles — new servers come online with the complete hardening list, reproducible and documented. On request.

More on these topics:

Need IT consulting?

Contact us for a no-obligation consultation on Proxmox, OPNsense, TrueNAS and more.

Get in touch