1 //===- llvm/unittest/Support/CrashRecoveryTest.cpp ------------------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 #include "llvm/Support/Compiler.h"
10 #include "llvm/Support/CrashRecoveryContext.h"
11 #include "gtest/gtest.h"
14 #define WIN32_LEAN_AND_MEAN
20 using namespace llvm::sys
;
22 static int GlobalInt
= 0;
23 static void nullDeref() { *(volatile int *)0x10 = 0; }
24 static void incrementGlobal() { ++GlobalInt
; }
25 static void llvmTrap() { LLVM_BUILTIN_TRAP
; }
27 TEST(CrashRecoveryTest
, Basic
) {
28 llvm::CrashRecoveryContext::Enable();
30 EXPECT_TRUE(CrashRecoveryContext().RunSafely(incrementGlobal
));
31 EXPECT_EQ(1, GlobalInt
);
32 EXPECT_FALSE(CrashRecoveryContext().RunSafely(nullDeref
));
33 EXPECT_FALSE(CrashRecoveryContext().RunSafely(llvmTrap
));
36 struct IncrementGlobalCleanup
: CrashRecoveryContextCleanup
{
37 IncrementGlobalCleanup(CrashRecoveryContext
*CRC
)
38 : CrashRecoveryContextCleanup(CRC
) {}
39 virtual void recoverResources() { ++GlobalInt
; }
44 TEST(CrashRecoveryTest
, Cleanup
) {
45 llvm::CrashRecoveryContext::Enable();
48 CrashRecoveryContext CRC
;
49 CRC
.registerCleanup(new IncrementGlobalCleanup(&CRC
));
50 EXPECT_TRUE(CRC
.RunSafely(noop
));
52 EXPECT_EQ(1, GlobalInt
);
56 CrashRecoveryContext CRC
;
57 CRC
.registerCleanup(new IncrementGlobalCleanup(&CRC
));
58 EXPECT_FALSE(CRC
.RunSafely(nullDeref
));
60 EXPECT_EQ(1, GlobalInt
);
64 static void raiseIt() {
65 RaiseException(123, EXCEPTION_NONCONTINUABLE
, 0, NULL
);
68 TEST(CrashRecoveryTest
, RaiseException
) {
69 llvm::CrashRecoveryContext::Enable();
70 EXPECT_FALSE(CrashRecoveryContext().RunSafely(raiseIt
));
73 static void outputString() {
74 OutputDebugStringA("output for debugger\n");
77 TEST(CrashRecoveryTest
, CallOutputDebugString
) {
78 llvm::CrashRecoveryContext::Enable();
79 EXPECT_TRUE(CrashRecoveryContext().RunSafely(outputString
));