El kernel Linux es muy propenso a mandar memoria de procesos a swap aunque «no estemos cortos» de memoria RAM. Simplemente por inactividad de un proceso durante cierto tiempo. Este comportamiento se puede controlar con un parámetro de sysctl (vm.swappiness). Os dejo como ejercicio leer un poco de él. 🙂
Hay ocasiones que la cantidad de swap usado nos hace preguntarnos ¿quién está ahí?. Desde la versión 2.6.32 (en distribuciones RedHat & cía.) y 2.6.34 en otras (en Debian eso es Wheezy o superior salvo que uses un kernel de backports) hay indicadores del uso de swap de cada proceso. Se trata de la entrada que empieza con VmSwap: en /proc/<PID>/status o las líneas Swap: en /proc/<PID>/smaps. Éstas últimas más detalladas pero inaccesibles a usuarios corrientes.
Basándome en esta información y trás días de desarrollo he creado este one-liner que nos mostrará (sin necesidad de root y ordenando por tamaño usado) los procesos que tienen parte de memoria en swap:
for i in $( ls -d /proc/[0-9]* ) ; do SWAP=$(egrep --color '^VmSwap:[[:space:]]*[^0 ][0-9]* kB' "$i/status" 2>/dev/null ) && { cat "$i/cmdline" ; echo -n " (" $( basename $i ) ; echo -n "): " ; echo $( echo $SWAP | tr -s ' ' | cut -d' ' -f2- ) ; } ; done | sort -t':' -k2 -n
Una versión más reducida, pero menos vistosa, sería esta otra:
find /proc/ -maxdepth 2 -name status -exec grep -H VmSwap: {} \; | grep -v ' 0 kB'
La primera la podéis guardar en un alias o en un script llamado (p.e.) /usr/local/bin/whoswaps y así no tenéis que memorizarla. 😛
$ exit