New anser 2023!
Some tips and tricks
In addition to all existing answer I want to share some tricks I use.
Reading free
's output
First, ensure that output of free
is not localized, for this you have to prepend command by LANG=C free -k
:
total used free shared buff/cache available
Mem: 32739720 9436264 8704992 883044 15959152 23303456
Swap: 23437308 5450752 17986556
Where, if you compute buff/cache + available
the result will be bigger than total
! This is wrong!!
Just consider if available mem
is bigger than used swap
, before purging swap!
msgs=("NOT " "")
{ # read `free` output, ignore 1st line and all values but free and swaped.
read _
read -r _{,,,,,} avail
read -r _ _ swaped _
} < <(LANG=C free -k)
printf 'Avail: %d swaped: %d Can %sunswap!\n' \
"$avail" "$swaped" "${msgs[ avail > swaped ]}"
Avail: 23303456 swaped: 5450752 Can unswap!
Alternative using /proc/meminfo
instead of free
Accessing directly /proc/meminfo
instead of running a fork to free
, you could obtain same values by:
msgs=("NOT " "")
while read field val _; do
case $field in
MemAvailable: ) avail=$val ;;
SwapTotal: ) declare -i swaped=$val ;;
SwapFree: ) swaped+=-$val; break ;;
esac
done < /proc/meminfo
printf 'Avail: %d swaped: %d Can %sunswap!\n' \
"$avail" "$swaped" "${msgs[ avail > swaped ]}"
Avail: 23303456 swaped: 5450752 Can unswap!
Purging swap swapoff -a
.
I've build a little script that
- correctly parse
free
's output,
- show human readable swaped and avail memory,
- offer to run
swapoff - swaponn
loop if user don't interact
- then compute elapsed time used to
unswap
.
There is my bash script, based on bash V>5.0
:
#!/bin/bash
msgs=("NOT " "")
while read field val _; do
case $field in
MemAvailable: ) avail=$val ;;
SwapTotal: ) declare -i swaped=$val ;;
SwapFree: ) swaped+=-$val; break ;;
esac
done < /proc/meminfo
txtsize() { # Convert integer into readable string, store result in $2 varname
local i=$(($1>=1<<50?5:$1>=1<<40?4:$1>=1<<30?3:$1>=1<<20?2:$1>1023?1:0))
local a=(K M G T P)
((i>4?i+=-2:0)) && a=(${a[@]:2}) && set -- $(($1>>20)) $2
local r=00$((1000*$1/(1024**i)))
printf -v $2 %.2f%s ${r::-3}.${r: -3} ${a[i]}
}
txtsize $avail havail
txtsize $swaped hswaped
printf 'Avail: %s (%d) swaped: (%s) %d Can %sunswap!\n' \
"$havail" $avail "$hswaped" $swaped "${msgs[ avail > swaped ]}"
if (( avail > swaped )); then
if read -sn 1 -t 5 -p\
'Proceed in 5 seconds. Hit any key to stop now. '; then
echo $'\nUser abort.'
exit 0
fi
echo
elapsedTime=${EPOCHREALTIME/.}
swapoff -a
elapsedTime=00000$(( ${EPOCHREALTIME/.} - elapsedTime ))
swapon -a
elapsedMin=$(( 10#$elapsedTime / 60000000 ))
elapsedSec=00000$(( 10#$elapsedTime % 60000000 ))
printf 'Swap: %s purged in %d minutes and %.3f secs (%.4f").\n' \
"$hswaped" "$elapsedMin" ${elapsedSec::-6}.${elapsedSec: -6} \
${elapsedTime::-6}.${elapsedTime: -6}
fi
His ouptut look like:
Avail: 23.86G (25023596) swaped: (1.14G) 1192460 Can unswap!
Proceed in 5 seconds. Hit any key to stop now.
Swap: 1.14G purged in 1 minutes and 51.166 secs (111.1661").
This script require root
privilege. But you could edit them to add sudo
before swapoff -a
and swapon -a
.
From there, as this opereation could take some time, I've built a Full purgeSwap script, showing progression with a nice progress bar and compute end time estimation, you my download here: 👉 purgeSwap.sh.
This answer is linked to this other one: How to find out which processes are using swap space in Linux?
About swapiness
I'm not totally convinced on how this compute percent of used memeory: including swap or not... For my tests, I'v seen swaping a lot before reaching percents configured in this kernel variable.
Anyway, for my servers, I still use:
echo 10 > /proc/sys/vm/swappiness
for running system that was not already configured by:
echo >/etc/sysctl.d/90-swapiness.conf 'vm.swappiness = 10'
before last reboot.
Use of vmstat 1
I often use this, but as I like graphical presentation, I've build (in 2009)
a perl CGI, that could work in standalone:
http://perso.f-hauri.ch/~felix/marcm/vmstat.cgi
This script is self-downloadable, work in any web server, but could be used directly on poor systems. Graphics are drawn in svg and rendered by your browser.
Sample of use:
wget -O vmstat.pl http://perso.f-hauri.ch/~felix/marcm/vmstat.cgi/download/vmstat.cgi
LANG=C perl vmstat.pl
CGI::Pretty is DEPRECATED and will be removed in a future release. Please see https://github.com/leejo/CGI.pm/issues/162 for more information at /usr/share/perl5/CGI/Pretty.pm line 20.
Server started at port 8881
Yes, it's an old script Don't run them as root!!.
...Then you could connect with a browser:
http://ip.add.re.ss:8881/
http://127.0.0.1/?delay=1&width=1800&height=120
Here 1'800 dots with a delay of 1 seconds make half hour graphs.