1
votes

I'm working on a sporadic production issue that's occurring within our 32 bit MFC VC2010 application. The application is running on Windows Server 2008 R2 Standard SP1 64-bit.

The issue is caused by a failure to create a CWnd derived class. When the failure occurs the AfxUnhookWindowCreate method returns false within CWnd::CreateEx. This is because the pThreadState->m_pWndInit variable is not NULL. It looks like _AfxCbtFilterHook should be setting this to NULL when HCBT_CREATEWND is hooked, but it appears this is not occurring. I've logged out the CREATESTRUCT and compared it to when the failure occurs vs. doesn't occur and the parameters are essentially the same.

Does anyone have ideas on what could cause this or how I could identify the cause? Thanks!

BOOL CWnd::CreateEx(DWORD dwExStyle, LPCTSTR lpszClassName,
LPCTSTR lpszWindowName, DWORD dwStyle,
int x, int y, int nWidth, int nHeight,
HWND hWndParent, HMENU nIDorHMenu, LPVOID lpParam)
{
...
if (!PreCreateWindow(cs))
{
    PostNcDestroy();
    return FALSE;
}

AfxHookWindowCreate(this);
HWND hWnd = ::AfxCtxCreateWindowEx(cs.dwExStyle, cs.lpszClass,
        cs.lpszName, cs.style, cs.x, cs.y, cs.cx, cs.cy,
        cs.hwndParent, cs.hMenu, cs.hInstance, cs.lpCreateParams);
...
if (!AfxUnhookWindowCreate())
    PostNcDestroy();        // cleanup if CreateWindowEx fails too soon
...

BOOL AFXAPI AfxUnhookWindowCreate()
{
_AFX_THREAD_STATE* pThreadState = _afxThreadState.GetData();
  #ifndef _AFXDLL
if (afxContextIsDLL && pThreadState->m_hHookOldCbtFilter != NULL)
{
    ::UnhookWindowsHookEx(pThreadState->m_hHookOldCbtFilter);
    pThreadState->m_hHookOldCbtFilter = NULL;
}
  #endif
if (pThreadState->m_pWndInit != NULL)
{
    pThreadState->m_pWndInit = NULL;
    return FALSE;   // was not successfully hooked
}
return TRUE;
}

LRESULT CALLBACK
_AfxCbtFilterHook(int code, WPARAM wParam, LPARAM lParam)
{
_AFX_THREAD_STATE* pThreadState = _afxThreadState.GetData();
if (code != HCBT_CREATEWND)
{
    // wait for HCBT_CREATEWND just pass others on...
    return CallNextHookEx(pThreadState->m_hHookOldCbtFilter, code,
        wParam, lParam);
}

 ...
        pThreadState->m_pWndInit = NULL;
1
sound like a threading issue :-) - Cheers and hth. - Alf
@user Are you calling CWnd::CreateEx from the main thread? - sashoalm
Yes, this is occurring on the main thread. Sometimes the window creates successfully and sometime it doesn't within the same process from the main thread. - user1707438
If you create a blank window (ie nothing else going on) do you have the same problem or is it something happening in the Window class itself causing the problem? - snowdude
Yes, it was still occurring with a blank CWnd. I tracked the problem down to a window procedure hook that shouldn't have been executing at this time. Thanks! - user1707438

1 Answers

1
votes

I tracked the problem down to a window procedure hook that shouldn't have been executing at this time.