2010-08-20 7 views
5

Ich habe einen unbehandelten Ausnahme-Handler. Es zeigt eine nette GUI und ermöglicht Benutzern, einen Fehlerbericht zu senden. Benutzer können sogar ihren Namen, ihre Telefonnummer und andere Dinge hinterlassen, und unsere Support-Abteilung ruft sie zurück. Funktioniert gut, sieht gut aus, macht Kunden weniger wütend. In der Theorie sowieso.Wie suspendiere ich alle Threads, nachdem mein Programm abstürzt?

Das Problem ist, dass meine Anwendung Hintergrundthreads verwendet, und die Threads scheinen nicht zu kümmern, wenn eine Ausnahme, sagen wir, der GUI-Thread (was Sinn macht), und einfach ihre Arbeit fortsetzen. Dies führt schließlich dazu, dass ein WER-Dialog erscheint, wenn der Benutzer mein benutzerdefiniertes Exception-Handler-Fenster lange genug offen lässt, so dass es aussieht, als wäre der Fehler-Handler selbst abgestürzt.

Ich habe keinen Zugriff auf die Thread-Objekte im Bereich des Ausnahmebehandlers, so dass ich sie nicht unterbrechen kann. Das globale Zugreifen auf Thread-Objekte ist ebenfalls keine Lösung. Meine Problemumgehung für den Moment besteht darin, in meinem Exception-Handler so etwas wie Globals.Crashed = true; zu verwenden und meine Thread-Methoden diese Eigenschaft bei jeder Schleifeniteration überprüfen zu lassen. Nicht perfekt, aber es minimiert den Schaden.

Kennt jemand eine weniger-hacky Methode? Ist meine Vorgehensweise falsch? Muss ich es wie WER machen und ein externes Programm starten, das das Hauptprogramm aussetzt und die Fehler-UI anzeigt?

+0

Wenn dieser Trick gut genug funktioniert, würde ich dabei bleiben. – FrustratedWithFormsDesigner

Antwort

5

Wenn Sie eine unbehandelte, unbekannte Ausnahme haben, können Sie davon ausgehen, dass ALLES passiert ist und dass Ihr Programm nicht einmal die einfachste Sache machen kann. Betrachten wir z.B. Wenn Sie den gesamten verfügbaren Speicher verbraucht haben, können Sie den Fehlerbericht auch nicht senden, da wahrscheinlich Speicher zugewiesen werden muss.

Ein guter Ansatz ist es, eine separate kleine Anwendung schreiben, die nur die Fehlerberichterstattung tut. Diese Anwendung kann die Details aufnehmen, die aus einer Datei gemeldet werden sollen. Auf diese Weise würde Ihr unbekannter Ausnahmebehandler:

  • Dump die Informationen in eine Datei im Temp-Verzeichnis.
  • Starten Sie die Fehlerberichterstattungs-App mit dem Dateinamen als Argument.
  • Beenden Sie den fehlerhaften Prozess, bevor es etwas Dummes tut.

Die temporäre Datei sollte von der Fehlerberichterstattungsanwendung entfernt werden.

+0

Das klingt wie der beste Ansatz . Vielen Dank. –

0

Sie könnten alle Ihre Threads in einem globalen Collection-Objekt verfolgen, so dass es beim Ausführen des Handlers einfach durch das Collection-Objekt iterieren und die Threads dort abbrechen kann.

+0

Ich denke, es gab eine Diskussion in der letzten Woche, die sich mit diesem Thema befasst hat. Lassen Sie mich sehen, ob ich diesen Link finden kann ... Ok, hier ist es: http://StackOverflow.com/Questions/3480451/Time-limiting-A-method-in-C – FrustratedWithFormsDesigner

0

Werfen Sie einen Blick auf den Code in dieser Frage, Suspend Process in C#, müssen Sie es zwicken, um nicht Ihren GUI-Thread und alle, die nicht im Hintergrund gestartet sind, die Sie gestartet haben, aber es sollte den Trick tun . Die bessere Option besteht jedoch darin, zu versuchen, Ihre Fehlerbericht-GUI als separaten Prozess zu starten, indem Sie ihr alle erforderlichen Informationen übermitteln und dann den ursprünglichen Prozess von Ihrem unbehandelten Ausnahmebehandler abbrechen, anstatt alles zuzulassen ein möglicherweise korrupter Zustand.