Esta mañana me he encontrado con una alerta en un servidor RedHat 6, cuyo mensaje de error era:
Semaphores exhausted: OS support please check: 0 semaphores available
He podido entrar correctamente al servidor pero al ejecutar algunos comandos, se quedaban colgados sin responder jamás.
Así que le he echado un vistazo al estado de los semáforos.
Resulta que el usuario root había consumido el total de los semáforos disponibles configurados para él en el sistema:
[root ~]# ipcs -s |wc -l
254
[[email protected] ~]# sysctl -a |grep sem
kernel.sem = 256 32000 32 256
[root ~]#
El siguiente paso es averiguar cuál es el proceso que los está agotando, así que ejecuto:
[root ~]# ipcs -s |more
------ Semaphore Arrays --------
key semid owner perms nsems
0x00000000 0 root 600 1
0x00000000 65537 root 600 1
0x720b09d9 196610 root 666 2
0x310b0a19 229379 root 666 5
0x010b238d 458756 root 664 1
0x010b09f9 327685 root 664 1
La lista es muy larga como para ponerla entera en el blog.
Lo importante es sacar información de alguno de los semáforos que están en marcha. En concreto, me interesa obtener el PID del proceso que lo está utilizando para poder analizarlo:
[root ~]# ipcs -s -i 526385401 Semaphore Array semid=526385401
uid=0 gid=0 cuid=0 cgid=0
mode=0600, access_perms=0600
nsems = 1
otime = Not set
ctime = Fri Jun 15 09:28:36 2018
semnum value ncount zcount pid
0 0 1 0 27748
Y aquí tenemos el proceso problemático:
[root ~]# ps -ef |grep 27748 |grep -v grep
root 27748 1 0 09:28 ? 00:00:00 /opt/OV/bin/oalicense -getASSD
[root ~]#
Tras reiniciar esta aplicación, el uso de los semáforos vuelve a ser normal.
Me gusta mucho utilizar el siguiente comando para averigurar qué procesos son los que están utilizando cada semáforo:
[root ~]# ipcs -s |grep root |awk '{print "ipcs -s -i " $2}' |sh |grep -A3 pid |grep -v ^$ |grep -v "\-\-" |grep -v pid |awk '{print " ps -ef |grep " $5}' |sh |grep -v grep
root 1214 2 0 2018 ? 00:00:00 [ext4-dio-unwrit]
root 7566 1 0 2018 ? 00:00:00 /usr/sbin/atd
root 16797 1 0 Apr09 ? 00:00:00 /opt/perf/bin/ttd
root 16116 1 0 Apr09 ? 00:01:30 /opt/perf/bin/midaemon
root 16116 1 0 Apr09 ? 00:01:30 /opt/perf/bin/midaemon
root 27212 27204 0 12:10 ? 00:00:00 /opt/OV/bin/ovbbccb -nodaemon
root 27395 27204 0 12:12 ? 00:00:00 /opt/OV/lbin/eaagt/opcmsgi
root 27395 27204 0 12:12 ? 00:00:00 /opt/OV/lbin/eaagt/opcmsgi
root 27411 27204 0 12:12 ? 00:00:01 /opt/OV/lbin/eaagt/opcle -std
root 27411 27204 0 12:12 ? 00:00:01 /opt/OV/lbin/eaagt/opcle -std
root 27437 27204 0 12:12 ? 00:00:34 /opt/OV/bin/oacore oacore /var/opt/OV/conf/oa/PipeDefinitions/oacore.xml
root 27389 27204 0 12:12 ? 00:00:00 /opt/OV/lbin/eaagt/opcmsga
root 8573 1 0 2018 tty1 00:00:00 /sbin/mingetty /dev/tty1
root 8575 1 0 2018 tty2 00:00:00 /sbin/mingetty /dev/tty2
hpddpers 8576 8539 0 13:22 ? 00:00:00 sshd: [email protected]/2
root 8577 1 0 2018 tty3 00:00:00 /sbin/mingetty /dev/tty3
hpddpers 8578 8576 0 13:22 pts/2 00:00:00 -bash
root 8579 1 0 2018 tty4 00:00:00 /sbin/mingetty /dev/tty4
root 8612 8578 0 13:22 pts/2 00:00:00 -bash
root 16116 1 0 Apr09 ? 00:01:30 /opt/perf/bin/midaemon
root 27458 27204 0 12:12 ? 00:00:00 /opt/OV/lbin/eaagt/opcmona
root 27458 27204 0 12:12 ? 00:00:00 /opt/OV/lbin/eaagt/opcmona
root 16127 15515 0 13:37 pts/2 00:00:00 ps -ef
[root ~]#
Eliminar los semáforos huérfanos
Hay aplicaciones que no gestionan bien los semáforos del sistema y los dejan en uso, incluso, si la aplicación ya se ha cerrado, causando una ocupación innecesaria del número de semáforos disponibles en el sistema hasta llegarlos a agotar.
Para detectar y eliminar los semáforos huérfanos, es decir, semáforos en uso por PIDs que ya no existen en el sistema, utilizo el siguiente script:
[root ~]# cat get_orph_sem.sh
#!/bin/sh
# Semaforos
for SEM in `ipcs -s |grep apache |awk '{print $2}'`;
do
PID=`ipcs -s -i $SEM |tail -2 |awk '{print $5}' |awk NF`
PROC=`ps -ef |grep $PID |grep -v grep`
if [[ -z $PROC ]]
then
echo El proceso $PID ya no existe en el sistema. Vamos a matar el semaforo huerfano $SEM
ipcrm -s $SEM
fi
done
[root ~]#
Si lo ejecutamos, veremos cómo se van eliminando los semáforos huérfanos:
El proceso 21266 ya no existe en el sistema. Vamos a matar el semaforo huerfano 1713602824
El proceso 12242 ya no existe en el sistema. Vamos a matar el semaforo huerfano 1831371017
El proceso 3199 ya no existe en el sistema. Vamos a matar el semaforo huerfano 1864335626
El proceso 12536 ya no existe en el sistema. Vamos a matar el semaforo huerfano 2061369611
El proceso 27236 ya no existe en el sistema. Vamos a matar el semaforo huerfano 2127692044
El proceso 9069 ya no existe en el sistema. Vamos a matar el semaforo huerfano 326664461
El proceso 24656 ya no existe en el sistema. Vamos a matar el semaforo huerfano 808648974
Al finalizar, podemos comprobar que se han eliminado los semáforos correspondientes con el comando ipcs -l. Veremos que ya hay muchos menos.
Estos comandos los he utilizado en Linux RedHat 6.