Crafter.Build/tests/WasmExceptions/fixture/main.cpp

46 lines
1.3 KiB
C++
Raw Normal View History

// SPDX-License-Identifier: LGPL-3.0-only
// SPDX-FileCopyrightText: Copyright (C) 2026 Catcrafts®
import std;
// jump.c, compiled as C.
extern "C" std::int32_t JumpRoundTrip();
namespace {
std::int32_t unwound = 0;
struct Guard {
~Guard() { ++unwound; }
};
void Throw(std::int32_t depth) {
Guard guard;
if (depth == 0) throw std::runtime_error("thrown in wasm");
Throw(depth - 1);
}
}
int main(int argc, char** argv) {
// With an argument, nothing catches: the run has to fail.
if (argc > 1) Throw(0);
try {
Throw(3);
} catch (const std::runtime_error& e) {
std::println("caught: {} after {} destructors", e.what(), unwound);
}
try {
const std::vector<std::int32_t> empty;
std::println("unreachable: {}", empty.at(1));
} catch (const std::out_of_range&) {
std::println("caught: out_of_range from libc++");
}
// vector::at throws from a header, compiled into this unit; stoi throws
// inside libc++.a, which therefore has to be the exception-enabled one.
try {
std::println("unreachable: {}", std::stoi("not a number"));
} catch (const std::invalid_argument&) {
std::println("caught: invalid_argument from inside libc++");
}
std::println("longjmp came back with {}", JumpRoundTrip());
return 0;
}