【问题标题】:How do I know the .exe that loaded my dll is about to exit?我怎么知道加载我的 dll 的 .exe 即将退出?
【发布时间】:2010-12-07 19:18:09
【问题描述】:

我有一个 dll,它实际上是一个注册的 com 服务,然后被另一个 .exe 进程加载。我希望当用户退出 .exe 以在为时已晚之前从我的 dll 中执行一些资源关闭步骤。我试图从我的 DLL 的 DllMain 中截取 DLLPROCESSSDETACH 或 DLLTHREADDETACH 但似乎当它到达那里时,已经为时已晚,因为我的 DLL 启动的线程(我需要执行关闭步骤)已经停止了?!当然,我不控制 .exe 代码,否则我会从那里调用一个调用以在它退出之前执行那些干净的关闭步骤。我只能处理 DLL 本身。似乎也没有调用 DllCanUnloadNow 或 DllUnregisterServer。

有没有人可以解决这种情况?

非常感谢您的任何意见。

【问题讨论】:

    标签: windows com dll exit


    【解决方案1】:

    你可以用dtor写一个静态对象,一旦服务退出并且cruntime即将卸载,dtor就会被调用。

    struct CDtorMyDll
    {
      ~CDtorMyDll
      {
        // do cleanup stuff here.
      }
    };
    
    static CDtorMyDll dtorMyDll;
    

    【讨论】:

      【解决方案2】:

      愚蠢的问题:为什么你需要运行你创建的线程?无论如何,它们都会被销毁,并且进程使用的所有资源都会被清理干净。

      话虽如此,如果您的对象确实是 COM 对象,您可以在 DllCanUnloadNow 调用中添加代码以检测您的对象是否有任何未完成的实例,如果没有,则清理您的资源。如果进程泄漏对您的对象的引用或不调用 CoUninitialize,这将不起作用,但如果托管您的对象的进程遵循规则,它会让您有机会在进程关闭之前进行清理。

      【讨论】:

        【解决方案3】:

        尝试通过 DllMain 或析构函数执行此操作会导致异常,因为 DLL 本身将处于奇怪的状态(阅读 Raymond Chen 关于 DllMain 的所有文章,您会看到)。

        这里真正的解决方案是在进程退出之前调用显式的 MyDllInitialize() 和 MyDllTeardown() 函数。

        【讨论】:

          猜你喜欢
          • 2011-09-06
          • 1970-01-01
          • 2010-10-12
          • 2012-12-10
          • 1970-01-01
          • 2011-08-30
          • 2021-08-24
          • 2013-07-28
          • 1970-01-01
          相关资源
          最近更新 更多