Hi all,
I am working on an object-oriented wrapper class hierarchy for the Win32 GUI API.
I have been experiencing strange behavior after I implemented mix-in classes providing window text wrapper functions.
This is what my hierarchy looks like now:
[Base class : Window] --virtual--> UserWindow --------------> Frame (Inherits HasText and Window) --> MainFrame
+-----------virtual--> HasText (mix in class)------^
Window defines a static Base_WndProc procedure which process WM_NCCREATE and sets the window's user data to the classes this pointer. It then does this->WndProc, where this->WndProc is a virtual WndProc function which takes a this pointer.
The this pointer is sent to Base_WndProc by means of the lpCreateParams member of the CREATESTRUCT structure.
This worked fine, until I changed Frame to inherit UserWindow and HasText. Then, the vtable of the MainFrame object seemed to have been corrupted or something. Base_WndProc is called correctly, and then retrieves the correct this pointer.
The problem occurs here :
1 2 3 4
|
CREATESTRUCT* cs=(CREATESTRUCT*)lParam;
Window* pWindow=(Window*)cs->lpCreateParams;
SetWindowLongPtr(hWnd, GWL_USERDATA, (LONG)pWindow);
return pWindow->WndProc(hWnd, uMsg, wParam, lParam); // Dereferencing of NULL pointer occurs (vtable entry = 0)
|
In my WinMain, the calling code:
1 2 3 4 5 6 7 8 9
|
MainFrame frm;
frm.WndProc(NULL, NULL, NULL, NULL); // succeeds in calling MainFrame::WndProc
Window* pw=(Window*)&frm;
CREATESTRUCT cs;
cs.lpCreateParams=(void*)pw;
Window::Base_WndProc(NULL, WM_NCCREATE, NULL, (LPARAM)&cs); // succeeds in calling MainFrame::WndProc
frm.Register();
frm.Create(320, 200); // CreateWindowProc fails to call MainFrame::WndProc.
frm.Show(SW_SHOWDEFAULT);
|
This debugging information might help :
http://pastebin.com/h3NzqPiP
And the source is here :
https://github.com/zsteve/hard86/tree/master/src/interface/win32/generic/src
This problem involves window, userwindow, frame, main.cpp/h