Merkwürdiger Absturz bei MouseUp Funktion



  • Hallo Forum,
    ich habe einen merkwürdigen Fehler bei eine abgeleiteten Klasse CButton. In ihr wird die Funktion MouseUp überschieben:

    void CMyButton::OnLButtonUp(UINT nFlags, CPoint point){

    CButton::OnLButtonUp(nFlags, point);

    HWND hWnd = GetSafeHwnd();
    if (hWnd != INVALID_HANDLE_VALUE){
    usw....
    }

    Jetzt stelle ich fest dass beim Beenden der App. aus irgendeinem Grund die Message MouseUp (nicht immer) abgearbeitet wird und dadurch die OnLButtonUp Funktion aufgeruffen wird. Dieses führt zum Absturz in der GetSafeHwnd().
    Wenn ich den Fehler unter Debugger anschaue dann sehe ich "this" Zeiger mit einem Wert!=0 jedoch ungültig da die Memeber Variablen mit Fragezeichen gekezeichnet sind.

    Das ganze kann ich mir so erklären.
    Der Button wird über new angelegt und über Delete zerstört. Ich denke wenn der Button bereits zerstört ist aber noch etwas in der WinMsgQeuee für den Button vorhanden ist, dann wird die Funktion OnLButtonUp mit ungültigen "this" Zeiger aufgerufen.
    Aber vielleicht irre ich mich da auch?

    Ich habe jetzt zwei Möglichkeiten das Problem zu lösen. Die schöne ist es natürlich zu verstehen/finden woher die Nachricht kommt (wann, von wem) oder in der OnLButtonUp irgendwie den "this" Pointer nochmal prüffen.

    Könntet Ihr mir dazu paar Tips geben wie ich das Problem finden kann oder was ich in OnLButtonUp schreiben müsste?

    Gruss


  • Mod

    Schau doch erstmal nach woher die Nachricht aus Deinem Callstack kommt.
    Hast Du evtl. selber einmal LButtonUp an ein Fenster gesendet...

    Ansonsten ist der gezeigte Code Unfug INVALID_HANDLE_VALUE hat mit Fnestern nichts zu tun und ist -1!

    Ein Fenster, dass nicht existiert liefert 0/NULL bei GetSafeHWnd.



  • Die Nachricht kommt aus:

    mfc80ud.dll!CWnd::GetSafeHwnd()

    my.dll!CMyButton::OnLButtonUp(unsigned int nFlags=0, CPoint point={...})

    mfc80ud.dll!CWnd::OnWndMsg(unsigned int message=514, unsigned int wParam=0, long lParam=2162765, long * pResult=0x0018f9a0)

    mfc80ud.dll!CWnd::WindowProc(unsigned int message=514, unsigned int wParam=0, long lParam=2162765)

    mfc80ud.dll!AfxCallWndProc(CWnd * pWnd=0x06d01e40, HWND__ * hWnd=0x000709d4, unsigned int nMsg=514, unsigned int wParam=0, long lParam=2162765)

    mfc80ud.dll!AfxWndProc(HWND__ * hWnd=0x000709d4, unsigned int nMsg=514, unsigned int wParam=0, long lParam=2162765)

    mfc80ud.dll!AfxWndProcBase(HWND__ * hWnd=0x000709d4, unsigned int nMsg=514, unsigned int wParam=0, long lParam=2162765)

    Das ist aber der Ausbauer. Frühere Callstack Ausgabe ist die WM_Quit Massage.

    Mir ist etwas weiter aufgefallen:

    Wird die CMyButton::OnLButtonUp Funktion ausgeführt dann wird in ihr die CButton::OnLButtonUp(nFlags, point); aufgeruffen. Hierbei wird ein Modale Dialog angezeigt und der Folgecode in der CMyButton::OnLButtonUp NICHT weiter ausgeführt solange bis der Dialog geschlossen wird. Das Öffnen des Dialoges wird aus der WM_COMMAND Message Funktion in anderen My Klasse ausgeführt.
    Ist es so dass beim CButton::OnLButtonUp Funktionen weitere Messages ausgelöst werden und wie (Post oder Send)? Wo kann man dieses Nachschauen welche noch?

    Jetzt habe ich natürlich weitere Vermuttung.
    Da die Ausführung an der CButton::OnLButtonUp unterbrochen wird solange ein Dialog ansteht, wird beim beenden erst der "delete" ausgeführt und dann der Rest der CMyButton::OnLButtonUp. Damit würde ich verstehen dass es doch keine weitere Nachricht kommt aber der "this" Zeiger danach ungültig ist.



  • Nochmal zum meinem Problem.

    Dieses steht fest:

    - In eine CMyButton::OnLButtonUp Funktion wird die CButton::OnLButtonUp und dann Stück weitere Code

    void CMyButton::OnLButtonUp(UINT nFlags, CPoint point){
    CButton::OnLButtonUp(nFlags, point);
    HWND hWnd = GetSafeHwnd();
    usw....
    }

    - Beim Betätigen des Button wird von Windows eine WM_COMMAND Nachricht an übergeordente Klasse gesendet aus CButton::OnLButtonUp; aufrufes.

    - Übergeordente Klase stellt in dem WM_COMMAND Handler ein Dialog dar (DoModal),
    was wiederum der restliche code:

    HWND hWnd = GetSafeHwnd();
    usw....

    erst nicht ausgeführt wird.(Erst beim Beenden des Dialoges)

    Jetzt kommt der Teil den ich nicht ganz verstanden habe.
    Was passiert hier an der Stelle "DoModal"?
    Eigentlich dachte ich an eine quasi Endlosschleife aber stimmen kann es nicht denn wenn ich von externen Tool meine App beenden will, dann kommt die Message zum WinApp in die CMyApp::PreTraslateMassge.
    Ich dachte dann in die CMyApp::PreTraslateMassge die WM_CLOSE Message abzufangen und den Dialog über EndDialog zu beenden (was auch funktioniert) aber auch dann wird nach Endmodal nicht sofort der restliche Code in CMyButton::OnLButtonUp ausgeführt.


Log in to reply