Seguridad de la biblioteca de vínculos dinámicos
Cuando una aplicación carga dinámicamente una biblioteca de vínculos dinámicos sin especificar un nombre de ruta de acceso completo, Windows intenta buscar el archivo DLL buscando un conjunto bien definido de directorios en un orden determinado, como se describe en Orden de búsqueda de la biblioteca de vínculos dinámicos. Si un atacante obtiene el control de uno de los directorios de la ruta de búsqueda dll, puede colocar una copia malintencionada del archivo DLL en ese directorio. Esto se denomina a veces un ataque de carga previa de DLL o un ataque de plantación binaria. Si el sistema no encuentra una copia legítima del archivo DLL antes de buscar en el directorio en peligro, carga el archivo DLL malintencionado. Si la aplicación se ejecuta con privilegios de administrador, el atacante puede tener éxito en la elevación de privilegios local.
Por ejemplo, supongamos que una aplicación está diseñada para cargar un archivo DLL desde el directorio actual del usuario y no se encuentra correctamente si no se encuentra el archivo DLL. La aplicación llama a LoadLibrary con solo el nombre del archivo DLL, lo que hace que el sistema busque el archivo DLL. Suponiendo que el modo de búsqueda dll segura está habilitado y la aplicación no usa un orden de búsqueda alternativo, el sistema busca directorios en el orden siguiente:
- Directorio desde el que se cargó la aplicación.
- Directorio del sistema.
- Directorio del sistema de 16 bits.
- El directorio de Windows.
- El directorio actual.
- Los directorios que aparecen en la variable de entorno PATH.
Continuando con el ejemplo, un atacante con conocimiento de la aplicación obtiene el control del directorio actual y coloca una copia malintencionada del archivo DLL en ese directorio. Cuando la aplicación emite la llamada a LoadLibrary , el sistema busca el archivo DLL, busca la copia malintencionada del archivo DLL en el directorio actual y la carga. A continuación, la copia malintencionada del archivo DLL se ejecuta dentro de la aplicación y obtiene los privilegios del usuario.
Los desarrolladores pueden ayudar a proteger sus aplicaciones frente a ataques de precarga de DLL siguiendo estas directrices:
Siempre que sea posible, especifique una ruta de acceso completa al usar las funciones LoadLibrary, LoadLibraryEx, CreateProcess o ShellExecute .
Use las marcas de LOAD_LIBRARY_SEARCH con la función LoadLibraryEx o use estas marcas con la función SetDefaultDllDirectories para establecer un orden de búsqueda DLL para un proceso y, a continuación, use las funciones AddDllDirectory o SetDllDirectory para modificar la lista. Para más información, vea Orden de búsqueda de las bibliotecas de vínculos dinámicos.
Windows 7, Windows Server 2008 R2, Windows Vista y Windows Server 2008: Estas marcas y funciones están disponibles en sistemas con KB2533623 instalado.
En los sistemas con KB2533623 instalado, use las marcas de LOAD_LIBRARY_SEARCH con la función LoadLibraryEx o use estas marcas con la función SetDefaultDllDirectories para establecer un orden de búsqueda dll para un proceso y, a continuación, use las funciones AddDllDirectory o SetDllDirectory para modificar la lista. Para más información, vea Orden de búsqueda de las bibliotecas de vínculos dinámicos.
Considere la posibilidad de usar el redireccionamiento de DLL o un manifiesto para asegurarse de que la aplicación usa el archivo DLL correcto.
Al usar el orden de búsqueda estándar, asegúrese de que el modo de búsqueda dll seguro está habilitado. Esto coloca el directorio actual del usuario más adelante en el orden de búsqueda, lo que aumenta las posibilidades de que Windows encuentre una copia legítima del archivo DLL antes de una copia malintencionada. El modo de búsqueda de DLL seguro está habilitado de forma predeterminada a partir de Windows XP con Service Pack 2 (SP2) y se controla mediante el valor del registro SafeDllSearchMode de HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\. Para más información, vea Orden de búsqueda de las bibliotecas de vínculos dinámicos.
Considere la posibilidad de quitar el directorio actual de la ruta de acceso de búsqueda estándar llamando a SetDllDirectory con una cadena vacía (""). Esto debe hacerse una vez al principio de la inicialización del proceso, no antes y después de las llamadas a LoadLibrary. Tenga en cuenta que SetDllDirectory afecta a todo el proceso y que varios subprocesos que llaman a SetDllDirectory con valores diferentes pueden provocar un comportamiento indefinido. Si la aplicación carga archivos DLL de terceros, pruebe cuidadosamente para identificar las incompatibilidades.
No use la función SearchPath para recuperar una ruta de acceso a un archivo DLL para una llamada a LoadLibrary posterior a menos que esté habilitado el modo de búsqueda de procesos seguros. Cuando el modo de búsqueda de procesos seguros no está habilitado, la función SearchPath usa un orden de búsqueda diferente al de LoadLibrary y es probable que primero busque el directorio actual del usuario para el archivo DLL especificado. Para habilitar el modo de búsqueda de procesos seguros para la función SearchPath , use la función SetSearchPathMode con BASE_SEARCH_PATH_ENABLE_SAFE_SEARCHMODE. Esto mueve el directorio actual al final de la lista de búsqueda de SearchPath durante la vida útil del proceso. Tenga en cuenta que el directorio actual no se quita de la ruta de búsqueda, por lo que si el sistema no encuentra una copia legítima del archivo DLL antes de llegar al directorio actual, la aplicación sigue siendo vulnerable. Al igual que con SetDllDirectory, la llamada a SetSearchPathMode debe realizarse al principio de la inicialización del proceso y afecta a todo el proceso. Si la aplicación carga archivos DLL de terceros, pruebe cuidadosamente para identificar las incompatibilidades.
No realice suposiciones sobre la versión del sistema operativo basada en una llamada LoadLibrary que busque un archivo DLL. Si la aplicación se ejecuta en un entorno en el que el archivo DLL no está presente legítimamente, pero una copia malintencionada del archivo DLL se encuentra en la ruta de búsqueda, se puede cargar la copia malintencionada del archivo DLL. En su lugar, use las técnicas recomendadas que se describen en Obtención de la versión del sistema.
La herramienta Monitor de procesos se puede usar para ayudar a identificar las operaciones de carga de DLL que podrían ser vulnerables. La herramienta Monitor de procesos se puede descargar desde https://technet.microsoft.com/sysinternals/bb896645.aspx.
En el procedimiento siguiente se describe cómo usar el Monitor de procesos para examinar las operaciones de carga de DLL en la aplicación.
Para usar el Monitor de procesos para examinar las operaciones de carga de DLL en la aplicación
- Inicie el Monitor de procesos.
- En el Monitor de procesos, incluya los siguientes filtros:
- La operación es CreateFile
- La operación es LoadImage
- La ruta de acceso contiene .cpl
- La ruta de acceso contiene .dll
- La ruta de acceso contiene .drv
- La ruta de acceso contiene .exe
- La ruta de acceso contiene .ocx
- La ruta de acceso contiene .scr
- La ruta de acceso contiene .sys
- Excluya los siguientes filtros:
- Nombre del proceso es procmon.exe
- Nombre del proceso es Procmon64.exe
- Nombre del proceso es System
- La operación comienza con IRP_MJ_
- La operación comienza con FASTIO_
- El resultado es SUCCESS
- La ruta de acceso finaliza con pagefile.sys
- Intente iniciar la aplicación con el directorio actual establecido en un directorio específico. Por ejemplo, haga doble clic en un archivo con una extensión cuyo controlador de archivos esté asignado a la aplicación.
- Compruebe la salida del Monitor de procesos en busca de rutas de acceso sospechosas, como una llamada al directorio actual para cargar un archivo DLL. Este tipo de llamada podría indicar una vulnerabilidad en la aplicación.