El equipo responsable de shell32.dll recibió un informe de errores que atribuía a esa biblioteca una serie reiterada de cierres inesperados en un programa de terceros. El análisis de los volcados de memoria reveló una traza característica: un bucle interminable de marcos de pila que alternaban entre RtlLookupFunctionEntry, RtlDispatchException y KiUserExceptionDispatch. Esa pauta describe una espiral recursiva de manejo de excepciones: una excepción original llegaba al kernel, este no podía resolverla en modo kernel y la devolvía al modo usuario; al buscar qué controlador ejecutar se generaba una nueva excepción y el ciclo se repetía hasta agotar la pila y terminar el proceso.
Examinando el fondo de la pila, el origen del problema se situaba en la rutina DLL_PROCESS_DETACH de shell32, concretamente en la destrucción de un objeto wil::details::string_maker dentro de ucrtbase. La excepción primaria era un acceso no ejecutable en la dirección 0x7ff9fcba0af0, correspondiente a combase!CoTaskMemFree. La paradoja es que el depurador informaba de que el módulo combase.dll ya no estaba cargado en memoria: la región aparecía como MEM_FREE y sin ninguna protección de página.
El artículo recorre paso a paso cómo usar comandos como .exr, .cxr, dps y !address para reconstruir la excepción original a partir de la pila y confirmar que el módulo ya no residía en el proceso cuando shell32 intentó llamarlo durante la finalización del proceso. Se trata de una guía práctica para depurar cierres anómalos en Windows provocados por llamadas a código de DLL que ya han sido descargadas, un escenario poco frecuente pero destructivo.
