std::longjmp
| Definiert im Header <csetjmp>
|
||
void longjmp( std::jmp_buf env, int status );
|
(bis C++17) | |
[[noreturn]] void longjmp( std::jmp_buf env, int status );
|
(seit C++17) | |
Lädt den Ausführungskontext env , der durch einen vorherigen Aufruf von setjmp gespeichert wurde. Diese Funktion kehrt nicht zurück. Die Kontrolle wird an die Aufrufstelle des Makros setjmp übergeben, das env eingerichtet hat. Dieses setjmp gibt dann den Wert zurück, der als status übergeben wurde.
Wenn die Funktion, die setjmp aufgerufen hat, beendet wurde, ist das Verhalten undefiniert (mit anderen Worten, es sind nur lange Sprünge den Aufrufstapel hinauf erlaubt).
Zusätzliche Einschränkungen in C++
Zusätzlich zu C
longjmp
hat C++
std::longjmp
eingeschränktere Verhaltensweisen.
Wenn das Ersetzen von
std::longjmp
durch
throw
und
setjmp
durch
catch
einen
nicht-trivialen Destruktor
für ein automatisches Objekt aufrufen würde, ist das Verhalten eines solchen
std::longjmp
undefiniert.
|
Das Verhalten ist undefiniert, wenn
|
(since C++20) |
Parameter
| env | - | Variable, die auf den durch setjmp gespeicherten Programmausführungszustand verweist |
| status | - | Der von setjmp zurückzugebende Wert. Wenn dieser gleich 0 ist, wird stattdessen 1 verwendet |
Hinweise
std::longjmp
ist der Mechanismus, der in C verwendet wird, um unerwartete Fehlerzustände zu behandeln, bei denen die Funktion nicht sinnvoll zurückkehren kann. C++ verwendet dafür im Allgemeinen
Exception-Handling
.
Beispiel
#include <array> #include <cmath> #include <csetjmp> #include <cstdlib> #include <format> #include <iostream> std::jmp_buf solver_error_handler; std::array<double, 2> solve_quadratic_equation(double a, double b, double c) { const double discriminant = b * b - 4.0 * a * c; if (discriminant < 0) std::longjmp(solver_error_handler, true); // Zum Fehlerbehandler springen const double delta = std::sqrt(discriminant) / (2.0 * a); const double argmin = -b / (2.0 * a); return {argmin - delta, argmin + delta}; } void show_quadratic_equation_solution(double a, double b, double c) { std::cout << std::format("Löse {}x² + {}x + {} = 0...\n", a, b, c); auto [x_0, x_1] = solve_quadratic_equation(a, b, c); std::cout << std::format("x₁ = {}, x₂ = {}\n\n", x_0, x_1); } int main() { if (setjmp(solver_error_handler)) { // Fehlerbehandler für den Löser std::cout << "Keine reelle Lösung\n"; return EXIT_FAILURE; } for (auto [a, b, c] : {std::array{1, -3, 2}, {2, -3, -2}, {1, 2, 3}}) show_quadratic_equation_solution(a, b, c); return EXIT_SUCCESS; }
Ausgabe:
Löse 1x² + -3x + 2 = 0... x₁ = 1, x₂ = 2 Löse 2x² + -3x + -2 = 0... x₁ = -0.5, x₂ = 2 Löse 1x² + 2x + 3 = 0... Keine reelle Lösung
Fehlerberichte
Die folgenden verhaltensändernden Fehlerberichte wurden rückwirkend auf zuvor veröffentlichte C++-Standards angewendet.
| DR | Angewendet auf | Verhalten wie veröffentlicht | Korrektes Verhalten |
|---|---|---|---|
| LWG 619 | C++98 | die Formulierung der zusätzlichen Einschränkungen in C++ war vage | die Formulierung verbessert |
| LWG 894 | C++98 |
das Verhalten war undefiniert, wenn das Ersetzen
std::longjmp
durch
throw
und
setjmp
durch
catch ein automatisches Objekt zerstören würde |
das Verhalten ist nur undefiniert
wenn ein nicht-trivialer Destruktor für ein automatisches Objekt aufgerufen wird |
Siehe auch
|
speichert den Kontext
(Funktionsmakro) |
|
|
C-Dokumentation
für
longjmp
|
|