Configure Linux memory management and swap optimization for high-performance workloads

Intermediate 25 min Apr 03, 2026 1,887 views
Ubuntu 24.04 Ubuntu 22.04 Debian 12 AlmaLinux 9 Rocky Linux 9 Fedora 41

Optimize Linux memory subsystem performance through advanced swap configuration, virtual memory tuning, and memory compression techniques. Learn to configure transparent huge pages, zram, and application-specific memory settings for high-performance workloads.

Prerequisites

  • Root or sudo access
  • Basic understanding of Linux system administration
  • Familiarity with command line operations

What this solves

Linux memory management directly impacts application performance, system responsiveness, and workload throughput. Poor memory configuration can lead to excessive swapping, memory pressure, and Out of Memory (OOM) kills that crash critical applications. This tutorial shows you how to optimize Linux memory subsystem settings, configure intelligent swap strategies, and implement memory compression to maximize performance for high-throughput workloads like databases, web servers, and analytics platforms.

Step-by-step configuration

Install memory monitoring tools

Install essential tools for monitoring memory usage, pressure, and swap activity.

sudo apt update
sudo apt install -y htop iotop sysstat procps util-linux
sudo dnf update -y
sudo dnf install -y htop iotop sysstat procps-ng util-linux

Analyze current memory configuration

Examine your system's current memory usage patterns, swap configuration, and pressure indicators before making changes.

free -h
cat /proc/meminfo | grep -E 'MemTotal|MemFree|MemAvailable|SwapTotal|SwapFree'
swapon --show
cat /proc/swaps
vmstat 1 5

Configure swap file optimization

Create an optimally-sized swap file with proper placement and permissions. Size should be 1-2x RAM for systems with 8GB+ RAM, or equal to RAM for smaller systems.

# Disable existing swap if present
sudo swapoff -a

# Remove old swap entries from fstab
sudo cp /etc/fstab /etc/fstab.backup
sudo sed -i '/swap/d' /etc/fstab

# Create optimized swap file (adjust size as needed - this creates 4GB)
sudo fallocate -l 4G /swapfile
sudo chmod 600 /swapfile
sudo mkswap /swapfile
sudo swapon /swapfile
# Add to /etc/fstab for persistence
echo '/swapfile none swap sw 0 0' | sudo tee -a /etc/fstab

Configure memory management sysctl parameters

Optimize virtual memory settings for high-performance workloads. These settings control swap behavior, memory overcommit, and memory reclaim strategies.

# Swap behavior optimization
# Reduce swappiness for better performance (default is 60)
vm.swappiness=10

# Only swap when under severe memory pressure
vm.vfs_cache_pressure=50

# Memory overcommit strategy
# 0 = heuristic overcommit (default)
# 1 = always overcommit 
# 2 = strict accounting (recommended for critical systems)
vm.overcommit_memory=2
vm.overcommit_ratio=80

# Dirty page handling for better I/O performance
vm.dirty_ratio=15
vm.dirty_background_ratio=5
vm.dirty_expire_centisecs=3000
vm.dirty_writeback_centisecs=500

# Memory reclaim optimization
vm.min_free_kbytes=65536
vm.zone_reclaim_mode=0

# OOM killer tuning
vm.panic_on_oom=0
vm.oom_kill_allocating_task=1

# Shared memory optimization
kernel.shmmax=68719476736
kernel.shmall=4294967296
sudo sysctl -p /etc/sysctl.d/99-memory-optimization.conf
sudo sysctl --system

Configure transparent huge pages

Optimize transparent huge pages (THP) settings. While THP can improve performance for some workloads, databases often perform better with THP disabled to avoid memory fragmentation and latency spikes.

# Check current THP status
cat /sys/kernel/mm/transparent_hugepage/enabled
cat /sys/kernel/mm/transparent_hugepage/defrag
[Unit]
Description=Disable Transparent Huge Pages (THP)
DefaultDependencies=no
After=sysinit.target local-fs.target
Before=mongod.service mysqld.service postgresql.service

[Service]
Type=oneshot
ExecStart=/bin/sh -c 'echo never | tee /sys/kernel/mm/transparent_hugepage/enabled > /dev/null'
ExecStart=/bin/sh -c 'echo never | tee /sys/kernel/mm/transparent_hugepage/defrag > /dev/null'
RemainAfterExit=true

[Install]
WantedBy=multi-user.target
sudo systemctl daemon-reload
sudo systemctl enable disable-thp.service
sudo systemctl start disable-thp.service
Note: For memory-intensive applications like machine learning or scientific computing, you might want to keep THP enabled with "madvise" mode instead of "never".

Install and configure zram for memory compression

Set up zram to provide compressed RAM-based swap that's faster than disk-based swap and increases effective memory capacity.

sudo apt install -y zram-tools
sudo dnf install -y zram
# Configuration for zram swap
# Percentage of RAM to use for zram (50% recommended)
PERCENT=50

# Compression algorithm (lz4 is fastest, zstd has better ratio)
ALGO=lz4

# Priority (higher than disk swap)
PRIORITY=100
sudo systemctl enable zramswap
sudo systemctl start zramswap

# Verify zram setup
zramctl
swapon --show

Configure memory pressure monitoring

Set up monitoring for memory pressure events and OOM conditions to track optimization effectiveness.

[Unit]
Description=Memory Pressure Monitor
After=multi-user.target

[Service]
Type=simple
ExecStart=/usr/local/bin/memory-monitor.sh
Restart=always
RestartSec=30
User=root

[Install]
WantedBy=multi-user.target
#!/bin/bash

# Memory pressure monitoring script
LOGFILE="/var/log/memory-monitor.log"
THRESHOLD_FREE_MB=500
THRESHOLD_SWAP_PERCENT=50

while true; do
    TIMESTAMP=$(date '+%Y-%m-%d %H:%M:%S')
    
    # Get memory info
    MEM_FREE=$(free -m | awk 'NR==2{printf "%d", $7}')
    SWAP_TOTAL=$(free -m | awk 'NR==3{printf "%d", $2}')
    SWAP_USED=$(free -m | awk 'NR==3{printf "%d", $3}')
    
    if [ $SWAP_TOTAL -gt 0 ]; then
        SWAP_PERCENT=$(( (SWAP_USED * 100) / SWAP_TOTAL ))
    else
        SWAP_PERCENT=0
    fi
    
    # Check for memory pressure
    if [ $MEM_FREE -lt $THRESHOLD_FREE_MB ] || [ $SWAP_PERCENT -gt $THRESHOLD_SWAP_PERCENT ]; then
        echo "$TIMESTAMP WARNING: Memory pressure detected - Free: ${MEM_FREE}MB, Swap Used: ${SWAP_PERCENT}%" >> $LOGFILE
        
        # Log top memory consumers
        echo "$TIMESTAMP Top memory processes:" >> $LOGFILE
        ps aux --sort=-%mem | head -6 >> $LOGFILE
        echo "---" >> $LOGFILE
    fi
    
    sleep 60
done
sudo chmod +x /usr/local/bin/memory-monitor.sh
sudo systemctl enable memory-monitor.service
sudo systemctl start memory-monitor.service

Configure OOM killer optimization

Fine-tune the Out of Memory killer to protect critical system processes and terminate resource-heavy applications appropriately.

#!/bin/bash

# Protect critical system processes from OOM killer
for pid in $(pgrep -f "systemd|kernel|kthreadd|ksoftirqd|migration|rcu_|watchdog"); do
    echo -1000 > /proc/$pid/oom_score_adj 2>/dev/null || true
done

# Protect SSH daemon
for pid in $(pgrep sshd); do
    echo -900 > /proc/$pid/oom_score_adj 2>/dev/null || true
done

# Make memory-intensive applications more likely to be killed
for service in mysql postgresql redis elasticsearch; do
    for pid in $(pgrep $service); do
        echo 200 > /proc/$pid/oom_score_adj 2>/dev/null || true
    done
done
sudo chmod +x /usr/local/bin/oom-score-tuning.sh

# Add to crontab to run on boot and periodically
echo '@reboot /usr/local/bin/oom-score-tuning.sh' | sudo crontab -
echo '*/10 * * * * /usr/local/bin/oom-score-tuning.sh' | sudo crontab -

Configure application-specific memory settings

Apply memory optimizations for common high-performance applications. These settings should be adjusted based on your specific workload requirements.

# Memory-related limits for applications
# Format: domain type item value

# Increase memory lock limits for databases
* soft memlock 64
* hard memlock 64

# Increase virtual memory limits
* soft as unlimited
* hard as unlimited

# Increase stack size for applications
* soft stack 8192
* hard stack 32768

# Specific limits for database users
mysql soft memlock unlimited
mysql hard memlock unlimited
postgres soft memlock unlimited
postgres hard memlock unlimited
# Application-specific memory tuning

# Increase shared memory for databases
kernel.shmmax=137438953472
kernel.shmall=33554432

# Network buffer optimization
net.core.rmem_max=16777216
net.core.wmem_max=16777216
net.ipv4.tcp_rmem=4096 87380 16777216
net.ipv4.tcp_wmem=4096 65536 16777216

# Process scheduling for memory-intensive workloads
kernel.sched_migration_cost_ns=5000000
kernel.sched_autogroup_enabled=0
sudo sysctl -p /etc/sysctl.d/99-app-memory.conf

Apply configuration and reboot

Apply all memory management configurations and restart the system to ensure all settings take effect properly.

# Verify all sysctl settings are loaded
sudo sysctl --system

# Check memory configuration
free -h
cat /proc/sys/vm/swappiness
cat /proc/sys/vm/overcommit_memory

# Reboot to ensure all settings are applied
sudo reboot

Verify your setup

After reboot, verify that all memory optimizations are working correctly and monitoring systems are active.

# Check memory and swap status
free -h
swapon --show
zramctl

# Verify sysctl settings
sysctl vm.swappiness
sysctl vm.overcommit_memory
sysctl vm.dirty_ratio

# Check transparent huge pages status
cat /sys/kernel/mm/transparent_hugepage/enabled

# Verify services are running
sudo systemctl status zramswap
sudo systemctl status memory-monitor
sudo systemctl status disable-thp

# Check memory pressure monitoring
sudo tail -f /var/log/memory-monitor.log

# Test memory pressure response
stress --vm 2 --vm-bytes 1G --timeout 30s

Performance benchmarking

Use these commands to benchmark memory performance and validate your optimizations.

# Memory bandwidth test
sudo apt install -y sysbench
sysbench memory --memory-total-size=2G run

# I/O performance with memory pressure
sysbench fileio --file-total-size=2G --file-test-mode=rndrw prepare
sysbench fileio --file-total-size=2G --file-test-mode=rndrw run
sysbench fileio --file-total-size=2G --file-test-mode=rndrw cleanup

# Monitor memory during benchmarks
watch -n 1 'free -h && echo && cat /proc/pressure/memory'

Common issues

Symptom Cause Fix
High swap usage despite available RAM vm.swappiness too high Set vm.swappiness=10 in sysctl configuration
OOM killer killing wrong processes Default OOM scores Run oom-score-tuning.sh to protect critical processes
Memory allocation failures Strict overcommit policy Adjust vm.overcommit_ratio or use vm.overcommit_memory=0
Poor database performance Transparent huge pages enabled Disable THP using the systemd service
zram not working after reboot Service not enabled sudo systemctl enable zramswap
Memory pressure not detected Monitoring thresholds too low Adjust THRESHOLD values in memory-monitor.sh

Next steps

Automated install script

Run this to automate the entire setup

Don't want to manage this yourself?

We handle infrastructure for businesses that depend on uptime. Fully managed, with one fixed contact who knows your setup.

You get one fixed contact who knows your setup

Rotterdam 01:28 · reachable in a message, no ticket form