annotate libcxxabi/test/forced_unwind1.pass.cpp @ 207:2e18cbf3894f

LLVM12
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Tue, 08 Jun 2021 06:07:14 +0900 (2021-06-07)
parents
children 5f17cb93ff66
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
207
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
1 //===----------------------------------------------------------------------===//
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
2 //
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
4 // See https://llvm.org/LICENSE.txt for license information.
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
6 //
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
7 //===----------------------------------------------------------------------===//
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
8
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
9 // _Unwind_ForcedUnwind raised exception can be caught by catch (...) and be
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
10 // rethrown. If not rethrown, exception_cleanup will be called.
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
11
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
12 // UNSUPPORTED: no-exceptions, c++03
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
13
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
14 // These tests fail on previously released dylibs, investigation needed.
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
15 // XFAIL: use_system_cxx_lib && x86_64-apple-macosx10.15
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
16 // XFAIL: use_system_cxx_lib && x86_64-apple-macosx10.14
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
17 // XFAIL: use_system_cxx_lib && x86_64-apple-macosx10.13
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
18 // XFAIL: use_system_cxx_lib && x86_64-apple-macosx10.12
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
19 // XFAIL: use_system_cxx_lib && x86_64-apple-macosx10.11
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
20 // XFAIL: use_system_cxx_lib && x86_64-apple-macosx10.10
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
21 // XFAIL: use_system_cxx_lib && x86_64-apple-macosx10.9
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
22
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
23 #include <stdlib.h>
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
24 #include <string.h>
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
25 #include <unwind.h>
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
26 #include <tuple>
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
27 #include <__cxxabi_config.h>
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
28
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
29 #if defined(_LIBCXXABI_ARM_EHABI)
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
30 int main(int, char**) {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
31 return 0;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
32 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
33 #else
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
34 static int bits = 0;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
35
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
36 struct C {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
37 int bit;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
38 C(int b) : bit(b) {}
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
39 ~C() { bits |= bit; }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
40 };
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
41
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
42 template <typename T>
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
43 struct Stop;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
44
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
45 template <typename R, typename... Args>
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
46 struct Stop<R (*)(Args...)> {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
47 // The third argument of _Unwind_Stop_Fn is uint64_t in Itanium C++ ABI/LLVM
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
48 // libunwind while _Unwind_Exception_Class in libgcc.
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
49 typedef typename std::tuple_element<2, std::tuple<Args...>>::type type;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
50
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
51 static _Unwind_Reason_Code stop(int, _Unwind_Action actions, type,
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
52 struct _Unwind_Exception*,
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
53 struct _Unwind_Context*, void*) {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
54 if (actions & _UA_END_OF_STACK)
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
55 abort();
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
56 return _URC_NO_REASON;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
57 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
58 };
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
59
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
60 static void cleanup(_Unwind_Reason_Code, struct _Unwind_Exception* exc) {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
61 bits |= 8;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
62 delete exc;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
63 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
64
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
65 static void forced_unwind() {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
66 _Unwind_Exception* exc = new _Unwind_Exception;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
67 exc->exception_class = 0;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
68 exc->exception_cleanup = cleanup;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
69 _Unwind_ForcedUnwind(exc, Stop<_Unwind_Stop_Fn>::stop, 0);
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
70 abort();
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
71 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
72
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
73 static void test() {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
74 try {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
75 C four(4);
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
76 try {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
77 C one(1);
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
78 forced_unwind();
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
79 } catch (...) {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
80 bits |= 2;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
81 throw;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
82 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
83 } catch (int) {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
84 } catch (...) {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
85 // __cxa_end_catch calls cleanup.
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
86 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
87 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
88
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
89 int main(int, char**) {
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
90 test();
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
91 return bits != 15;
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
92 }
Shinji KONO <kono@ie.u-ryukyu.ac.jp>
parents:
diff changeset
93 #endif