Structured Exception Handling (C/C++)

Die strukturierte Ausnahmebehandlung (SEH) ist eine Microsoft-Erweiterung für C und C++ zur Behandlung bestimmter außergewöhnlicher Codesituationen, z. B. Hardwarefehler, ordnungsgemäß. Obwohl Windows und Microsoft C++ SEH unterstützen, empfehlen wir, die C++-Ausnahmebehandlung im C++-Code nach ISO-Standard zu verwenden. Es macht Ihren Code portierbarer und flexibler. Um jedoch vorhandenen Code oder für bestimmte Arten von Programmen zu Standard, müssen Sie möglicherweise weiterhin SEH verwenden.

Microsoft-spezifisch:

Grammatik

try-except-statement :
__try compound-statement __except ( filter-expression ) compound-statement

try-finally-statement :
__try compound-statement __finally compound-statement

Hinweise

Mit SEH können Sie sicherstellen, dass Ressourcen, z. B. Speicherblöcke und Dateien, ordnungsgemäß freigegeben werden, wenn die Ausführung unerwartet beendet wird. Sie können auch bestimmte Probleme behandeln, z. B. unzureichenden Arbeitsspeicher, indem Sie präzisen strukturierten Code verwenden, der nicht auf goto Anweisungen angewiesen ist, oder aufwendige Tests von Rückgabecodes.

Die try-except in diesem Artikel genannten Anweisungen und try-finally Anweisungen sind Microsoft-Erweiterungen für die Sprachen C und C++. Sie unterstützen SEH, indem es Anwendungen ermöglicht wird, die Steuerung eines Programms nach Ereignissen abzurufen, die andernfalls das Beenden der Ausführung zur Folge haben würden. Obwohl SEH mit C++-Quelldateien funktioniert, ist sie nicht ausdrücklich für C++ vorgesehen. Wenn Sie SEH in einem C++-Programm verwenden, das Sie mithilfe der /EHa Oder-Option /EHsc kompilieren, werden Destruktoren für lokale Objekte aufgerufen, andere Ausführungsverhalten sind jedoch möglicherweise nicht das, was Sie erwarten. Eine Abbildung finden Sie im Beispiel weiter unten in diesem Artikel. In den meisten Fällen wird anstelle von SEH empfohlen, die ISO-Standard-C ++-Ausnahmebehandlung zu verwenden. Mithilfe der C++-Ausnahmebehandlung können Sie eine bessere Portierbarkeit des Codes sicherstellen, und Sie können Ausnahmen jeglichen Typs behandeln.

Wenn Sie über C-Code verfügen, der SEH verwendet, können Sie ihn mit C++-Code kombinieren, der C++-Ausnahmebehandlung verwendet. Weitere Informationen finden Sie unter Behandeln strukturierter Ausnahmen in C++.

Es gibt zwei SEH-Mechanismen:

Diese beiden Arten von Handlern sind unterschiedlich, aber eng miteinander verbunden durch einen Prozess, der als Entspannen des Stapels bezeichnet wird. Wenn eine strukturierte Ausnahme auftritt, sucht Windows nach dem zuletzt installierten Ausnahmehandler, der derzeit aktiv ist. Beim Handler kann eine von drei Möglichkeiten auftreten:

  • Fehler beim Erkennen der Ausnahme und Übergeben des Steuerelements an andere Handler (EXCEPTION_CONTINUE_SEARCH).

  • Erkennen Sie die Ausnahme, schließen Sie sie aber (EXCEPTION_CONTINUE_EXECUTION).

  • Erkennen Sie die Ausnahme, und behandeln Sie sie (EXCEPTION_EXECUTE_HANDLER).

Der Ausnahmehandler, der die Ausnahme erkennt, befindet sich möglicherweise nicht in der Funktion, die bei Auftreten der Ausnahme ausgeführt wurde. Es kann sich in einer Funktion viel höher auf dem Stapel befinden. Die gegenwärtig ausgeführte Funktion sowie alle weiteren Funktionen im Stapelrahmen werden beendet. Während dieses Vorgangs wird der Stapel entwunden. Das heißt, lokale, nicht statische Variablen von beendeten Funktionen werden aus dem Stapel gelöscht.

Beim Entladen des Stapels ruft das Betriebssystem alle Beendigungshandler auf, die Sie für jede Funktion geschrieben haben. Durch die Verwendung eines Beendigungshandlers sauber Sie Ressourcen auf, die andernfalls aufgrund einer ungewöhnlichen Beendigung wieder geöffnet würden Standard. Wenn Sie einen kritischen Abschnitt eingegeben haben, können Sie ihn im Beendigungshandler beenden. Wenn das Programm heruntergefahren wird, können Sie andere Hausaufgaben ausführen, z. B. das Schließen und Entfernen temporärer Dateien.

Nächste Schritte

Beispiel

Wie bereits erwähnt, werden Destruktoren für lokale Objekte aufgerufen, wenn Sie SEH in einem C++-Programm verwenden und mithilfe der /EHa Option /EHsc kompilieren. Das Verhalten während der Ausführung ist jedoch möglicherweise nicht das, was Sie erwarten, wenn Sie auch C++-Ausnahmen verwenden. In diesem Beispiel werden diese Verhaltensunterschiede veranschaulicht.

#include <stdio.h>
#include <Windows.h>
#include <exception>

class TestClass
{
public:
    ~TestClass()
    {
        printf("Destroying TestClass!\n");
    }
};

__declspec(noinline) void TestCPPEX()
{
#ifdef CPPEX
    printf("Throwing C++ exception\n");
    throw std::exception("");
#else
    printf("Triggering SEH exception\n");
    volatile int *pInt = 0x00000000;
    *pInt = 20;
#endif
}

__declspec(noinline) void TestExceptions()
{
    TestClass d;
    TestCPPEX();
}

int main()
{
    __try
    {
        TestExceptions();
    }
    __except(EXCEPTION_EXECUTE_HANDLER)
    {
        printf("Executing SEH __except block\n");
    }

    return 0;
}

Wenn Sie /EHsc diesen Code kompilieren, aber das lokale Teststeuerelementmakro CPPEX nicht definiert ist, wird der TestClass Destruktor nicht ausgeführt. Die Ausgabe sieht wie folgt aus:

Triggering SEH exception
Executing SEH __except block

Wenn Sie /EHsc den Code kompilieren und CPPEX mithilfe /DCPPEX von Code definiert werden (sodass eine C++-Ausnahme ausgelöst wird), wird der TestClass Destruktor ausgeführt, und die Ausgabe sieht wie folgt aus:

Throwing C++ exception
Destroying TestClass!
Executing SEH __except block

Wenn Sie /EHa den Code kompilieren, wird vom TestClass Destruktor ausgeführt, ob eine Ausnahme mit einem C++ throw -Standardausdruck oder mit SEH ausgelöst wurde. Das heißt, ob CPPEX definiert ist oder nicht. Die Ausgabe sieht wie folgt aus:

Throwing C++ exception
Destroying TestClass!
Executing SEH __except block

Weitere Informationen finden Sie unter /EH (Ausnahmebehandlungsmodell).

ENDE der Microsoft-spezifischen Informationen

Siehe auch

Ausnahmenbehandlung
Schlüsselwörter
<exception>
Fehler- und Ausnahmebehandlung
Strukturierte Ausnahmebehandlung (Windows)