Cómo las señales * nix le permiten leer la memoria de otros procesos

Hay una cosa * nix muy antigua y arraigada llamada "señales" . La idea detrás de estas primitivas es muy simple: implementar un software análogo de interrupciones. Los diferentes procesos pueden enviarse señales entre sí y a sí mismos, conociendo el ID de proceso (pid) del destinatario. El proceso de recepción es libre de asignar una función de manejo de señales que se llamará automáticamente cuando se reciba, o ignorarla usando una máscara especial, o confiar en el comportamiento predeterminado. Hasta ahora tan bueno.



Comportamiento predeterminado al recibir una señal ... ¿Qué significan estas palabras tranquilizadoras? No es lo que esperabas, seguro. La wiki dice que los 28 manejadores de señales predeterminados (¡hay otros!) Son los siguientes: 2 se ignoran, 4 hacen que el proceso se detenga, 1 para continuar, 11 para terminar, 10 para terminar con un volcado de memoria. ¡Eso es interesante! Entonces, la situación es la siguiente: incluso si su programa no menciona señales de ninguna manera en el código fuente, de hecho las usa, y de una manera muy dramática.



De ahora en adelante, tendremos que profundizar más. ¿Quién puede enviar señales y a quién? La wiki dice: "Un proceso (o un usuario de un shell) con un UID efectivo distinto de 0 (el UID de superusuario) solo puede enviar señales a procesos con el mismo UID". Entonces, si ejecuta 100 programas, cualquiera de ellos puede eliminar fácilmente todos estos 100 programas usando la API del sistema, incluso si todos los programas (excepto el asesino) no mencionaron señales de ninguna manera en su código fuente. Si trabajó con la cuenta raíz, entonces no importa en absoluto quién inició ciertos procesos, aún puede finalizarlos fácilmente. Por supuesto, es posible encontrar el pid de un proceso particular y ejecutar su "asesinato por contrato", pero es aún más fácil matar a todos los que pueden ser simplemente pid-s de fuerza bruta.



“Espera, espera, no conduzcas a los caballos. ¡Mencionaste que las señales se pueden procesar e ignorar! " - Escucho la voz de mi lector. ¿Qué dirá Vicki? "Para el manejo alternativo de todas las señales excepto SIGKILL y SIGSTOP, un proceso puede asignar su propio controlador o ignorar su ocurrencia modificando su máscara de señal". Observamos las acciones predeterminadas al recibir estas señales y vemos: "Terminación del proceso", "Terminación del proceso". Resulta que podemos realizar estas dos acciones siempre que, en principio, sea posible enviar señales SIGKILL y SIGSTOP a la víctima. "La única excepción es un proceso con pid 1 (init), que puede ignorar o manejar cualquier señal, incluyendo KILL y STOP".Es posible que ni siquiera podamos matar uno de los procesos más importantes del sistema como root, pero de manera amistosa, esto requiere investigación adicional.



Bueno, el panorama se ha vuelto un poco más positivo, pero sigue siendo sombrío. Si inicia un proceso, se garantiza que puede finalizar y detener un montón de otros procesos. Cuando se cumple una condición muy simple, "los desarrolladores del proceso de recepción se olvidaron de ignorar o manejar de alguna manera una de las muchas otras señales", la aplicación maníaca podrá hacer que el proceso termine con un volcado de memoria o continuar el proceso después de detenerse. Si los desarrolladores de la aplicación receptora han colgado sus controladores en algunas señales, puede intentar interferir con el funcionamiento de esta aplicación enviándole señales. Este último es un tema para una discusión separada, porque debido a la ejecución asincrónica de los controladores, las carreras y el comportamiento indefinido son posibles ...



“El razonamiento abstracto es muy bueno, pero acerquémonos a los detalles”, me dirá un lector exigente. ¡Está bien, no hay problema! Cualquier usuario de * nix está familiarizado con un programa como bash. Este programa se viene desarrollando desde hace casi 30 años y tiene toda una montaña de posibilidades. ¡Vamos a llenarla de claridad y obtener algo delicioso de su memoria!



Saco mi Ubuntu 16.04.2 de casa de pierna ancha y ejecuto dos copias de bash 4.3.46 en él. En uno de ellos, ejecutaré un comando hipotético con datos secretos: export password = SECRET. Olvidémonos por un momento del archivo con el historial de comandos, en el que también estaría escrita la contraseña. En la misma ventana, escriba el comando ps para averiguar el pid de este proceso, digamos, 3580.



Sin cerrar la primera ventana, pasemos a la segunda. El comando ps en él dará otro pid de esta instancia de bash, digamos, 5378. Solo para mayor claridad, es desde este segundo bash que enviaremos una señal al primer comando kill -SIGFPE 3580. Sí, querido lector, esto es un completo absurdo: el proceso 2 no dice nada relacionado con para procesar 1, que en este mismo proceso 1 ocurrió una operación aritmética errónea. Aparece la siguiente ventana en la pantalla: La







anomalía deseada ocurrió con la creación de un volcado de memoria, es decir, bash no parece procesar o ignorar esta señal. Buscando en Google dónde debería buscar el vertedero, encontré una respuesta detallada ( uno , dos). En mi Ubuntu, la situación es la siguiente: si una aplicación del paquete estándar falla debido a una señal diferente a SIGABRT, entonces el volcado se transfiere al programa Apport. ¡Este es solo nuestro caso! Este programa ensambla un archivo con información de diagnóstico y muestra la ventana que se muestra arriba. El sitio web oficial afirma con orgullo: “Apport recopila datos potencialmente confidenciales, como volcados de memoria, seguimientos de pila y archivos de registro. Pueden contener contraseñas, números de tarjetas de crédito, números de serie y otro material privado ". Bueno, bueno, me pregunto dónde tenemos este archivo. Sí, /var/crash/_bin_bash.1000.crash. Llevemos su contenido a la carpeta somedir: apport-unpack /var/crash/_bin_bash.1000.crash somedir. Además de varias pequeñas cosas poco interesantes, habrá un codiciado volcado de memoria llamado CoreDump.



¡Aquí está, el momento de la verdad! Busquemos en este archivo la cadena de contraseña y veamos qué nos resulta interesante como respuesta. Comando de CoreDump de cadenas | grep contraseña recordará al hacker olvidadizo que la contraseña es SECRETA. ¡Maravilloso!



Hice lo mismo con mi editor de texto favorito, gedit, comenzando a escribir en el búfer y luego a leerlo del volcado. ¡No hay problema! En ese momento, Vicki le susurró al oído en forma de advertencia: "A veces (por ejemplo, para programas ejecutados en nombre del superusuario), no se crea un volcado de memoria por razones de seguridad". Entonces, vamos a comprobar ... Al recibir una señal del root bash, el segundo root bash falló con la creación de un volcado de memoria, pero debido a los permisos (-rw-r ----- con el propietario del root) ya no es tan fácil de leer como los anteriores propiedad de mi cuenta de usuario. Bueno, si el programa asesino hipotético logró enviar una señal desde el UID del superusuario, entonces puede tocar tal volcado.



El lector meticuloso puede comentar: "Fue muy fácil para usted encontrar los datos que buscaba en el mar de basura". Es cierto, pero estoy seguro: si sabes qué tipo de pez quieres pescar y dónde nada, entonces encontrarlo en las redes de basura debería ser realista casi siempre. Por ejemplo, nadie se molesta en descargar un paquete con información de depuración para un programa bloqueado y averiguar el contenido de las variables de interés en GDB mediante la depuración post-mortem.



Todo esto puede parecer bastante inofensivo, pero en realidad no lo es. Todas las acciones que describí podrían realizarse fácilmente mediante un programa o script que se ejecute en modo de usuario, sin mencionar un nivel de acceso más privilegiado. La conclusión es que un ejecutable malicioso puede fácilmente dividir programas a derecha e izquierda y, a menudo, también leer libremente toda su memoria. ¡Aquí están las señales y los informes de errores! Estoy seguro de que en otras plataformas * nix y con otros programas de destinatarios la situación es similar, pero por supuesto no lo comprobaré.



Puede surgir la objeción: el malware puede simplemente usar las herramientas de depuración para extraer datos interesantes de la aplicación. Realmente es. Entonces, ¿por qué es esta publicación? Mi punto es este: lo primero que me viene a la mente cuando se trata de detener el robo de datos de las aplicaciones son las limitaciones de las herramientas de depuración. Seguramente las herramientas antivirus detectan el uso de ptrace () en primer lugar; este es un evento muy sospechoso. Las señales son otro asunto completamente diferente. Un proceso envía a otro una señal estándar, ¿y qué? A primera vista, este es un evento completamente normal. Pero, como ya hemos visto, esto puede llevar a una terminación anormal de la aplicación, creando un volcado de núcleo en alguna carpeta, de la que se puede intentar sacarlo.



Cuando intenté abrir la página de inicio de sesión de vk.com y volcar Firefox con la misma señal fatal, se bloqueó, pero llamó a su controlador de volcado. Los volcados en el complicado formato de minivolcado se guardan en ~ / .mozilla / firefox / Crash Reports / {pendientes o enviados} y requieren una mayor investigación. Esto es lo que encontrará si, en la ventana de configuración, haga clic en "Más información" frente a la marca de verificación (el texto a continuación se solía colgar en www.mozilla.org/ru/privacy/firefox/#crash-reporter ):







« Mozilla Firefox. , Firefox, , URL- , . , , . crash-stats.mozilla.com. . .»Rara vez hay algo realmente sabroso en las URL, pero si los volcados contienen contraseñas o cookies es una buena pregunta.



Con esta nota misteriosa e intrigante, terminaré. Recibí una señal que olvidé procesar explícitamente.



PD: escribí un programa simple con un controlador de señal SIGUSR1: imprime la cadena "1" en la pantalla, ingresa un bucle sin fin. Tenía la esperanza de que si envía la señal SIGUSR1 muchas veces a este programa, el controlador será llamado muchas veces, lo que provocará un desbordamiento de pila. Desafortunadamente para mí, solo se llamó una vez al controlador. Bien, escribamos un manejador similar para la señal SIGUSR2 y enviemos dos señales diferentes con la esperanza de que esto descargue a la víctima ... Por desgracia, tampoco ayudó: cada manejador fue llamado solo una vez. ¡Desbordado, desbordado, pero no desbordado!



PD 2. En el mundo de Windows hay una especie de señales: mensajes que se pueden enviar a Windows . ¡Es muy probable que también se puedan usar para divertirse y obtener ganancias!



El original fue publicado en mi blog 05.05.17.



All Articles