1 | // Reference to all sorts of information for exception handling.
|
---|
2 |
|
---|
3 | // C++ Interface to exception handlers.
|
---|
4 |
|
---|
5 | void * __cxa_allocate_exception(size_t thrown_size);
|
---|
6 | // Creates space for the exception.
|
---|
7 |
|
---|
8 | void __cxa_free_exception(void * thrown_exception);
|
---|
9 |
|
---|
10 | void __cxa_throw(void * thrown_exception, struct type_info * tinfo,
|
---|
11 | void (*dest)(void*));
|
---|
12 | // Throws the exception, is not supposed to return but ours should,
|
---|
13 | // to handle resumption exceptions.
|
---|
14 |
|
---|
15 | void __cxa_begin_catch(); -> void * __cxa_begin_catch(void * exceptionObject);
|
---|
16 | void __cxa_end_catch();
|
---|
17 | // Not sure, beginning and end of catch block maybe?
|
---|
18 |
|
---|
19 |
|
---|
20 | /* Unwind Module
|
---|
21 | * Full list: https://itanium-cxx-abi.github.io/cxx-abi/abi-eh.html
|
---|
22 | * Avaible at: /usr/lib/gcc/x86_64-linux-gnu/{5}/include/unwind.h
|
---|
23 | */
|
---|
24 |
|
---|
25 | typedef _Unwind_Reason_Code (*_Unwind_Personality_Fn)
|
---|
26 | (int, _Unwind_Action, _Unwind_Exception_Class,
|
---|
27 | struct _Unwind_Exception *, struct _Unwind_Context *);
|
---|
28 | /* Type of the personality function, which does not have a set name.
|
---|
29 | * So far `__gcfa_personality_v0` has been used.
|
---|
30 | * Called by _Unwind_RaiseException (called by __cxa_throw)
|
---|
31 | * or by _Unwind_ForcedUnwind's personality wrapper.
|
---|
32 | * Params:
|
---|
33 | * int version: Repersents unwind convention standard.
|
---|
34 | * _Unwind_Action actions: Set of actions, used as instructions.
|
---|
35 | * _Unwind_Exception_Class: 8-byte identifer: high 4 vendor, low 4 language.
|
---|
36 | * _Unwind_Exception unwind_exception: Pointer to exception data.
|
---|
37 | * _Unwind_Context context: Information on the current stack frame.
|
---|
38 | * Return:
|
---|
39 | * _Unwind_Reason_Code: Requests an action from the unwinder.
|
---|
40 | */
|
---|
41 |
|
---|
42 |
|
---|
43 | // _Unwind_Action flags (multiple may be set):
|
---|
44 | _UA_SEARCH_PHASE // Seaching for the handler
|
---|
45 | _UA_CLEANUP_PHASE // Cleanup until handler found.
|
---|
46 | _UA_HANDLER_FRAME // Previous search found handler here.
|
---|
47 | _UA_FORCE_UNWIND // Unwind, do not decide if we have reached the handler.
|
---|
48 | _UA_END_OF_STACK // We have reached the end of the stack.
|
---|
49 |
|
---|
50 |
|
---|
51 | // _Unwind_Reason_Code values (one may be selected):
|
---|
52 | _URC_NO_REASON // Containues force unwind.
|
---|
53 | _URC_FOREIGN_EXCEPTION_CAUGHT // Cross between runtime environments.
|
---|
54 | _URC_FATAL_PHASE2_ERROR // Error in cleanup, not otherwise defined. (Rare?)
|
---|
55 | _URC_FATAL_PHASE1_ERROR // Error in search, not otherwise defined.
|
---|
56 | _URC_NORMAL_STOP
|
---|
57 | _URC_END_OF_STACK // eos found before a handler.
|
---|
58 | _URC_HANDLER_FOUND // Just the signal (search?)
|
---|
59 | _URC_INSTALL_CONTEXT // Handler found, resume execution (cleanup?)
|
---|
60 | _URC_CONTINUE_UNWIND // No handler found (search&cleanup)
|
---|
61 |
|
---|
62 |
|
---|
63 | // Exception Header: (?)
|
---|
64 | typedef void (*_Unwind_Exception_Cleanup_Fn)
|
---|
65 | (_Unwind_Reason_Code reason, struct _Unwind_Exception *exc);
|
---|
66 |
|
---|
67 | struct _Unwind_Exception {
|
---|
68 | uint64 exception_class;
|
---|
69 | _Unwind_Exception_Cleanup_Fn exception_cleanup;
|
---|
70 | uint64 private_1; // Do not access.
|
---|
71 | uint64 private_2; // Do not access.
|
---|
72 | };
|
---|
73 |
|
---|
74 |
|
---|
75 | // There are two functions to access the unwind "operation".
|
---|
76 | // The standard exception handler, uses the personality function.
|
---|
77 | _Unwind_Reason_Code _Unwind_RaiseException(
|
---|
78 | struct _Unwind_Exception * exception_object);
|
---|
79 |
|
---|
80 | // Helper for force unwind.
|
---|
81 | typedef _Unwind_Reason_Code (*_Unwind_Stop_Fn)(
|
---|
82 | int version,
|
---|
83 | _Unwind_Action actions,
|
---|
84 | uint64 exceptionClass,
|
---|
85 | struct _Unwind_Exception * exceptionObject,
|
---|
86 | struct _Unwind_Context * context,
|
---|
87 | void * stop_parameter);
|
---|
88 |
|
---|
89 | // Special unwinder, wraps the personality function.
|
---|
90 | _Unwind_Reason_Code _Unwind_ForcedUnwind(
|
---|
91 | struct _Unwind_Exception * exception_object,
|
---|
92 | _Unwind_Stop_Fn stop,
|
---|
93 | void * stop_parameter);
|
---|
94 |
|
---|
95 | // Continues unwinding
|
---|
96 | void _Unwind_Resume(struct _Unwind_Exception * exception_object);
|
---|
97 | // Seems to be for finally and deconstrctors, not so much rethrow.
|
---|
98 | // However I haven't figured out the difference.
|
---|
99 |
|
---|
100 |
|
---|
101 | /* _Unwind Helper functions:
|
---|
102 | *
|
---|
103 | * _Unwind_GetLanguageSpecificData - LSDA (destructors and landing pads)
|
---|
104 | * _Unwind_GetRegionStart - Function pointer to current stack frame.
|
---|
105 | * _Unwind_GetIP - Get frame's instruction pointer
|
---|
106 | * This might be the actual function pointer or the call site up stack.
|
---|
107 | *
|
---|
108 | * All three have the same signature. */
|
---|
109 | uint64 _Unwind_Get*(struct _Unwind_Context * context);
|
---|
110 |
|
---|
111 | void _Unwind_SetIP(struct _Unwind_Context * context, uint64 new_value);
|
---|
112 | uint64 _Unwind_GetGR(struct _Unwind_Context * context, int index);
|
---|
113 | void _Unwind_SetGR(struct _Unwind_Context * <>, int index, uint64 <>);
|
---|
114 | // __builtin_eh_return_data_regno(^) ^=[0..3]? gives index.
|
---|
115 |
|
---|
116 | // Locally we also seem to have:
|
---|
117 | _Unwind_Word _Unwind_GetCFA (struct _Unwind_Context *);
|
---|
118 |
|
---|
119 | // GCC (Dwarf2 ?) Frame Layout Macros
|
---|
120 | // See: https://gcc.gnu.org/onlinedocs/gccint/Frame-Layout.html
|
---|
121 | // Include from: ???
|
---|
122 |
|
---|
123 | FIRST_PARAM_OFFSET(fundecl)
|
---|
124 | // Offset from argument pointer to first arguments address, or above that
|
---|
125 | // address if ARGS_GROW_DOWNWARD.
|
---|
126 |
|
---|
127 | ARG_POINTER_CFA_OFFSET(fundecl)
|
---|
128 | // Default: FIRST_PARM_OFFSET(fundecl) + crtl->args.pretend_args_size
|
---|