1

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;
user1707438
  • 81
  • 1
  • 6

1 Answers1

1

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

user1707438
  • 81
  • 1
  • 6
  • This was a long time ago, but do you remember how you managed to find the offending hook? I'm having the same problem. – benrules2 May 18 '16 at 17:23
  • This specific issue turned out to be due to the Windows 64 bit stack limitation. The hook wasn't being unhooked as it should have been. I searched for SetWindowsHookEx calls to find the code that created the hook. The following article has more information on the limitation: https://support.microsoft.com/en-us/kb/2664641 – user1707438 May 22 '16 at 13:38