swapon.sh
· 2.6 KiB · Bash
Raw
#!/usr/bin/env bash
set -euo pipefail
SWAPFILE="/swapfile"
FSTAB="/etc/fstab"
die() {
echo "ERROR: $*" >&2
exit 1
}
need_cmd() {
command -v "$1" >/dev/null 2>&1 || die "Required command not found: $1"
}
# Must be root
if [[ "${EUID}" -ne 0 ]]; then
die "Run this script as root (e.g. sudo bash script.sh)"
fi
need_cmd awk
need_cmd grep
need_cmd chmod
need_cmd mkswap
need_cmd swapon
need_cmd free
# Refuse if any swap is already active
if swapon --noheadings --show | grep -q .; then
echo "Swap is already active:"
swapon --show
die "Refusing to continue."
fi
# Refuse if fstab already has any non-comment swap entry
if awk '
$0 !~ /^[[:space:]]*#/ && NF >= 3 && $3 == "swap" { found=1 }
END { exit(found ? 0 : 1) }
' "$FSTAB"; then
echo "Existing swap entry found in $FSTAB:"
awk '$0 !~ /^[[:space:]]*#/ && NF >= 3 && $3 == "swap"' "$FSTAB"
die "Refusing to continue."
fi
# Refuse if /swapfile already exists
if [[ -e "$SWAPFILE" ]]; then
die "$SWAPFILE already exists. Refusing to continue."
fi
# Read RAM from /proc/meminfo (kB)
mem_kb="$(awk '/^MemTotal:/ {print $2}' /proc/meminfo)"
[[ -n "$mem_kb" ]] || die "Could not determine system RAM."
mem_mb=$((mem_kb / 1024))
mem_gb=$(((mem_mb + 1023) / 1024)) # rounded up
# Sizing policy:
# <=2GB => 2x RAM
# <=8GB => 1x RAM
# <=64GB => 0.5x RAM
# >64GB => 8GB cap
if (( mem_mb <= 2048 )); then
swap_mb=$((mem_mb * 2))
elif (( mem_mb <= 8192 )); then
swap_mb=$mem_mb
elif (( mem_mb <= 65536 )); then
swap_mb=$((mem_mb / 2))
else
swap_mb=8192
fi
# Minimum 1GB
if (( swap_mb < 1024 )); then
swap_mb=1024
fi
echo "Detected RAM: ${mem_mb} MB (~${mem_gb} GB)"
echo "Will create swap: ${swap_mb} MB (~$(((swap_mb + 1023) / 1024)) GB)"
echo
# Ensure there is enough free disk space on /
avail_kb="$(df --output=avail / | tail -n1 | tr -d ' ')"
need_kb=$((swap_mb * 1024))
if (( avail_kb < need_kb + 262144 )); then
die "Not enough free disk space on /. Need about ${swap_mb} MB plus some headroom."
fi
# Create swapfile
if command -v fallocate >/dev/null 2>&1; then
fallocate -l "${swap_mb}M" "$SWAPFILE" || {
echo "fallocate failed, falling back to dd..."
dd if=/dev/zero of="$SWAPFILE" bs=1M count="$swap_mb" status=progress
}
else
dd if=/dev/zero of="$SWAPFILE" bs=1M count="$swap_mb" status=progress
fi
chmod 600 "$SWAPFILE"
mkswap "$SWAPFILE"
swapon "$SWAPFILE"
# Backup fstab before editing
cp "$FSTAB" "${FSTAB}.bak.$(date +%Y%m%d%H%M%S)"
echo "$SWAPFILE none swap sw 0 0" >> "$FSTAB"
echo
echo "Swap successfully created and enabled."
echo
echo "Current memory/swap:"
free -h
echo
echo "Active swap:"
swapon --show
echo
echo "fstab entry added:"
tail -n 5 "$FSTAB"
| 1 | #!/usr/bin/env bash |
| 2 | set -euo pipefail |
| 3 | |
| 4 | SWAPFILE="/swapfile" |
| 5 | FSTAB="/etc/fstab" |
| 6 | |
| 7 | die() { |
| 8 | echo "ERROR: $*" >&2 |
| 9 | exit 1 |
| 10 | } |
| 11 | |
| 12 | need_cmd() { |
| 13 | command -v "$1" >/dev/null 2>&1 || die "Required command not found: $1" |
| 14 | } |
| 15 | |
| 16 | # Must be root |
| 17 | if [[ "${EUID}" -ne 0 ]]; then |
| 18 | die "Run this script as root (e.g. sudo bash script.sh)" |
| 19 | fi |
| 20 | |
| 21 | need_cmd awk |
| 22 | need_cmd grep |
| 23 | need_cmd chmod |
| 24 | need_cmd mkswap |
| 25 | need_cmd swapon |
| 26 | need_cmd free |
| 27 | |
| 28 | # Refuse if any swap is already active |
| 29 | if swapon --noheadings --show | grep -q .; then |
| 30 | echo "Swap is already active:" |
| 31 | swapon --show |
| 32 | die "Refusing to continue." |
| 33 | fi |
| 34 | |
| 35 | # Refuse if fstab already has any non-comment swap entry |
| 36 | if awk ' |
| 37 | $0 !~ /^[[:space:]]*#/ && NF >= 3 && $3 == "swap" { found=1 } |
| 38 | END { exit(found ? 0 : 1) } |
| 39 | ' "$FSTAB"; then |
| 40 | echo "Existing swap entry found in $FSTAB:" |
| 41 | awk '$0 !~ /^[[:space:]]*#/ && NF >= 3 && $3 == "swap"' "$FSTAB" |
| 42 | die "Refusing to continue." |
| 43 | fi |
| 44 | |
| 45 | # Refuse if /swapfile already exists |
| 46 | if [[ -e "$SWAPFILE" ]]; then |
| 47 | die "$SWAPFILE already exists. Refusing to continue." |
| 48 | fi |
| 49 | |
| 50 | # Read RAM from /proc/meminfo (kB) |
| 51 | mem_kb="$(awk '/^MemTotal:/ {print $2}' /proc/meminfo)" |
| 52 | [[ -n "$mem_kb" ]] || die "Could not determine system RAM." |
| 53 | |
| 54 | mem_mb=$((mem_kb / 1024)) |
| 55 | mem_gb=$(((mem_mb + 1023) / 1024)) # rounded up |
| 56 | |
| 57 | # Sizing policy: |
| 58 | # <=2GB => 2x RAM |
| 59 | # <=8GB => 1x RAM |
| 60 | # <=64GB => 0.5x RAM |
| 61 | # >64GB => 8GB cap |
| 62 | if (( mem_mb <= 2048 )); then |
| 63 | swap_mb=$((mem_mb * 2)) |
| 64 | elif (( mem_mb <= 8192 )); then |
| 65 | swap_mb=$mem_mb |
| 66 | elif (( mem_mb <= 65536 )); then |
| 67 | swap_mb=$((mem_mb / 2)) |
| 68 | else |
| 69 | swap_mb=8192 |
| 70 | fi |
| 71 | |
| 72 | # Minimum 1GB |
| 73 | if (( swap_mb < 1024 )); then |
| 74 | swap_mb=1024 |
| 75 | fi |
| 76 | |
| 77 | echo "Detected RAM: ${mem_mb} MB (~${mem_gb} GB)" |
| 78 | echo "Will create swap: ${swap_mb} MB (~$(((swap_mb + 1023) / 1024)) GB)" |
| 79 | echo |
| 80 | |
| 81 | # Ensure there is enough free disk space on / |
| 82 | avail_kb="$(df --output=avail / | tail -n1 | tr -d ' ')" |
| 83 | need_kb=$((swap_mb * 1024)) |
| 84 | if (( avail_kb < need_kb + 262144 )); then |
| 85 | die "Not enough free disk space on /. Need about ${swap_mb} MB plus some headroom." |
| 86 | fi |
| 87 | |
| 88 | # Create swapfile |
| 89 | if command -v fallocate >/dev/null 2>&1; then |
| 90 | fallocate -l "${swap_mb}M" "$SWAPFILE" || { |
| 91 | echo "fallocate failed, falling back to dd..." |
| 92 | dd if=/dev/zero of="$SWAPFILE" bs=1M count="$swap_mb" status=progress |
| 93 | } |
| 94 | else |
| 95 | dd if=/dev/zero of="$SWAPFILE" bs=1M count="$swap_mb" status=progress |
| 96 | fi |
| 97 | |
| 98 | chmod 600 "$SWAPFILE" |
| 99 | mkswap "$SWAPFILE" |
| 100 | swapon "$SWAPFILE" |
| 101 | |
| 102 | # Backup fstab before editing |
| 103 | cp "$FSTAB" "${FSTAB}.bak.$(date +%Y%m%d%H%M%S)" |
| 104 | |
| 105 | echo "$SWAPFILE none swap sw 0 0" >> "$FSTAB" |
| 106 | |
| 107 | echo |
| 108 | echo "Swap successfully created and enabled." |
| 109 | echo |
| 110 | echo "Current memory/swap:" |
| 111 | free -h |
| 112 | echo |
| 113 | echo "Active swap:" |
| 114 | swapon --show |
| 115 | echo |
| 116 | echo "fstab entry added:" |
| 117 | tail -n 5 "$FSTAB" |