La empresa Qualys ha identificado dos vulnerabilidades en las herramientas apport (CVE-2025-5054) y systemd-coredump (CVE-2025-4598), utilizadas para procesar archivos core generados tras la finalización anómala de procesos. Las vulnerabilidades permiten acceder a archivos core guardados después de un cierre anómalo de aplicaciones suid o de algunos procesos en segundo plano del sistema, en cuya memoria pueden encontrarse credenciales en caché o claves de cifrado. La herramienta apport se invoca automáticamente para guardar los core dumps en Ubuntu, mientras que systemd-coredump lo hace en Red Hat Enterprise Linux 9+, Fedora y muchas otras distribuciones de Linux.
Se ha demostrado una técnica de ataque en la que se generan condiciones para un cierre anómalo de la aplicación suid unix_chkpwd y se obtiene acceso al archivo core con el volcado de estado durante el fallo. En el core dump guardado estaban presentes los hashes de las contraseñas de los usuarios del sistema, que permanecían en la memoria del proceso que falló tras cargar el contenido de /etc/shadow. La posibilidad de explotación de las vulnerabilidades se ha demostrado en Ubuntu 24.04 y Fedora 40/41, pero se supone que otras distribuciones también son vulnerables a ataques similares.
Ambas vulnerabilidades son causadas por una condición de carrera que permite sustituir un proceso suid que ha fallado por otro proceso en el momento después de que el núcleo inicia el manejo del fallo, pero antes de que el manipulador verifique en el espacio de usuario los parámetros del proceso a través de /proc/pid/files. La invocación de apport y systemd-coredump se realiza de la siguiente manera: el núcleo, tras recibir la información sobre el fallo del proceso, llama al manipulador especificado en el archivo /proc/sys/kernel/core_pattern y luego le pasa el contenido del core dump a través de un flujo de entrada.
La generación del core dump y el inicio del manipulador no son instantáneos y hay tiempo suficiente para sustituir el proceso suid que ha fallado por un proceso de usuario normal. En caso de sustitución, el manipulador de core dumps en ejecución considerará que la falla no ocurrió en el proceso suid, sino en una aplicación de usuario normal y, en consecuencia, guardará el archivo core con acceso para un usuario normal, no solo para un administrador.
El ataque a apport se reduce a los siguientes pasos:
- Se deriva un nuevo proceso y se llama a la función execve() para iniciar un programa suid, como unix_chkpwd.
- Se omite el tiempo necesario para cargar los datos confidenciales en la memoria por parte del programa suid (en el caso de unix_chkpwd, se espera la carga de los hashes de las contraseñas de todos los usuarios del sistema desde el archivo /etc/shadow).
- Antes de que finalice la ejecución del comando, se envía una señal SIGSEGV o SIGSYS al proceso para finalizarlo de manera forzada.
- En respuesta a la finalización forzada, el núcleo genera un volcado de memoria (core dump) y lanza el proceso apport para procesar el volcado en el espacio del usuario.
- Después de iniciar apport, pero antes de comenzar el análisis, se envía una señal SIGKILL al proceso que terminó de manera anómala, y el mismo proceso es reemplazado por otro sin la bandera suid. Para evitar las verificaciones en apport, el nuevo proceso se crea dentro de espacios de nombres separados (user, pid y mount namespace).
- apport se conecta al socket unix /run/apport.socket en el espacio de nombres de puntos de montaje creado para el nuevo proceso y envía un descriptor de archivo para acceder al volcado de memoria.
Para obtener el identificador necesario para el nuevo proceso, coincidente con el identificador del proceso suid, se detiene el proceso suid con la señal SIGSTOP antes de enviar la señal SIGSEGV, y mientras está detenido, se inician ciclos de nuevos procesos hasta que se obtiene un PID con un número anterior cercano al del proceso suid. Después de ajustar la numeración del PID, se envían las señales SIGSEGV y SIGCONT al proceso suid, tras lo cual se envía SIGKILL y se reinician cíclicamente nuevos procesos para alcanzar el mismo PID que el del proceso suid.
En cuanto a systemd-coredump, por un lado, realizar un ataque contra él es más sencillo, ya que no es necesario reemplazar el proceso suid por un proceso en un espacio de usuario separado, solo es suficiente lograr la coincidencia de AT_UID y AT_EUID. Por otro lado, systemd-coredump está escrito en lenguaje C y se inicia con bastante rapidez, lo que da menos tiempo para el reemplazo, a diferencia de apport, que está escrito en Python y carga varios archivos pyc durante la inicialización. Este problema se resuelve añadiendo un retraso artificial a systemd-coredump: al invocar el archivo suid, se pasan un gran número de argumentos en la línea de comandos, lo que crea la demora necesaria que ocurre durante el análisis de /proc/pid/cmdline.
En el proceso de análisis de vulnerabilidades, los investigadores también descubrieron que systemd-coredump, al configurar la llamada, no especifica en /proc/sys/kernel/core_pattern la bandera «%d», lo que permite a un atacante provocar un cierre inesperado de procesos en segundo plano que se ejecutan con privilegios de root y que generan otros procesos cambiando el identificador de usuario a un usuario no privilegiado bajo el cual se lleva a cabo el ataque. Esta posibilidad permite llevar a cabo un ataque no solo en aplicaciones setuid, sino también en procesos como sshd-session (OpenSSH), sd-pam (systemd) y cron, para obtener datos confidenciales que permanecen en su memoria, como claves privadas, hashes de contraseñas de /etc/shadow, etiquetas canary de la pila y datos para eludir la aleatorización del espacio de direcciones (ASLR).
Se puede hacer seguimiento a la publicación de actualizaciones de paquetes en las distribuciones en las páginas: Debian, Ubuntu, RHEL, openSUSE, Fedora, Gentoo, Arch. Como solución temporal para bloquear las vulnerabilidades, se sugiere desactivar el guardado de core dumps para programas suid y procesos que reducen privilegios, estableciendo el parámetro /proc/sys/fs/suid_dumpable en 0. Para una eliminación completa del problema, se requieren modificaciones en el núcleo de Linux que implementen la capacidad de transmitir información sobre un proceso que ha finalizado inesperadamente a través del mecanismo pidfd (pidfd se asocia a procesos específicos y, a diferencia de pid, no se reasigna).
Fuente: opennet.ru
