我在写一个plugin程序中使用DLL方式,具体代码如下:
char file[1024];
memset(file, 0, 1024);
unsigned long nCookie = 0;
CString strTitle; GetModuleFileName(theApp.m_hInstance, file, 1024);//获得模块路径、文件名
HINSTANCE hInst = AfxGetResourceHandle();//在这行中断言失败 AfxSetResourceHandle(theApp.m_hInstance);//定位到插件DLL资源
strTitle.LoadString(IDS_TITLES);//获得资源
AfxSetResourceHandle(hInst);//重新定位会主应用程序资源望各位高手指点,解决后立即结贴,在线等

解决方案 »

  1.   

    该工程在Debug版本下断言失败,而在release版本运行正常~
      

  2.   

    在文件afxasert.cpp文件中的下面函数:BOOL AFXAPI AfxAssertFailedLine(LPCSTR lpszFileName, int nLine)
    {
    #ifndef _AFX_NO_DEBUG_CRT
    // we remove WM_QUIT because if it is in the queue then the message box
    // won't display
    MSG msg;
    BOOL bQuit = PeekMessage(&msg, NULL, WM_QUIT, WM_QUIT, PM_REMOVE);
    ////////这个函数调用中断言失败!
    BOOL bResult = _CrtDbgReport(_CRT_ASSERT, lpszFileName, nLine, NULL, NULL);
    if (bQuit)
    PostQuitMessage(msg.wParam);
    return bResult;
    #else
    TCHAR szMessage[_MAX_PATH*2]; // handle the (hopefully rare) case of AfxGetAllocState ASSERT
    if (InterlockedIncrement(&afxAssertReallyBusy) > 0)
    {
    // assume the debugger or auxiliary port
    wsprintf(szMessage, _T("Assertion Failed: File %hs, Line %d\n"),
    lpszFileName, nLine);
    OutputDebugString(szMessage);
    InterlockedDecrement(&afxAssertReallyBusy); // assert w/in assert (examine call stack to determine first one)
    AfxDebugBreak();
    return FALSE;
    } // check for special hook function (for testing diagnostics)
    _AFX_THREAD_STATE* pThreadState = AfxGetThreadState();
    InterlockedDecrement(&afxAssertReallyBusy);
    if (afxAssertFailedLine != NULL)
    return (*afxAssertFailedLine)(lpszFileName, nLine); // get app name or NULL if unknown (don't call assert)
    LPCTSTR lpszAppName = afxCurrentAppName;
    if (lpszAppName == NULL)
    lpszAppName = _T("<unknown application>"); // format message into buffer
    wsprintf(szMessage, _T("%s: File %hs, Line %d"),
    lpszAppName, lpszFileName, nLine); if (afxTraceEnabled)
    {
    // assume the debugger or auxiliary port
    TCHAR szT[_MAX_PATH*2 + 20];
    wsprintf(szT, _T("Assertion Failed: %s\n"), szMessage);
    OutputDebugString(szT);
    }
    if (InterlockedIncrement(&afxAssertBusy) > 0)
    {
    InterlockedDecrement(&afxAssertBusy); // assert within assert (examine call stack to determine first one)
    AfxDebugBreak();
    return FALSE;
    } // active popup window for the current thread
    HWND hWndParent = GetActiveWindow();
    if (hWndParent != NULL)
    hWndParent = GetLastActivePopup(hWndParent); // we remove WM_QUIT because if it is in the queue then the message box
    // won't display
    MSG msg;
    BOOL bQuit = ::PeekMessage(&msg, NULL, WM_QUIT, WM_QUIT, PM_REMOVE);
    // display the assert
    int nCode = ::MessageBox(hWndParent, szMessage, _T("Assertion Failed!"),
    MB_TASKMODAL|MB_ICONHAND|MB_ABORTRETRYIGNORE|MB_SETFOREGROUND);
    if (bQuit)
    PostQuitMessage(msg.wParam); // cleanup
    InterlockedDecrement(&afxAssertBusy); if (nCode == IDIGNORE)
    return FALSE;   // ignore if (nCode == IDRETRY)
    return TRUE;    // will cause AfxDebugBreak AfxAbort();     // should not return (but otherwise AfxDebugBreak)
    return TRUE;
    #endif // _AFX_NO_DEBUG_CRT
    }
      

  3.   

    _CrtDbgReport(_CRT_ASSERT, lpszFileName, nLine, NULL, NULL);
    函数无法单步跟踪,无源代码奇怪的是Release版本正常
      

  4.   

    AFX_MODULE_STATE* AFXAPI AfxGetModuleState()
    {
    _AFX_THREAD_STATE* pState = _afxThreadState;
    AFX_MODULE_STATE* pResult;
    if (pState->m_pModuleState != NULL)
    {
    // thread state's module state serves as override
    pResult = pState->m_pModuleState;
    }
    else
    {
    // otherwise, use global app state
    pResult = _afxBaseModuleState.GetData();
    }
    ASSERT(pResult != NULL);
    return pResult;
    }该函数可以正常返回,pResult非空
      

  5.   

    AfxGetResourceHandle似乎只用在DLL里
      

  6.   

    你贴的那个函数BOOL AFXAPI AfxAssertFailedLine(LPCSTR lpszFileName, int nLine)是用来确定哪个文件哪行出错的。错误应该在调这个函数之前的地方。我猜测错误是因为你的dll是在你的exe之前被加载,这个时候还没有ResourceHandle。
    你是不是把那些代码放到了DllMain中的某个地方。
    如果你是放在别处,比如某个函数,让exe来调用,就不会有问题了。