[libunwind] Handle G in personality string
Tested with the following program:
```
static volatile int* x = nullptr;
void throws() __attribute__((noinline)) {
if (getpid() == 0)
return;
throw "error";
}
void maybe_throws() __attribute__((noinline)) {
volatile int y = 1;
x = &y;
throws();
y = 2;
}
int main(int argc, char** argv) {
int y;
try {
maybe_throws();
} catch (const char* e) {
//printf("Caught\n");
}
y = *x;
printf("%d\n", y); // should be MTE failure.
return 0;
}
```
Built using `clang++ -c -O2 -target aarch64-linux -fexceptions -march=armv8-a+memtag -fsanitize=memtag-heap,memtag-stack`
Currently only Android implements runtime support for MTE stack tagging.
Without this change, we crash on `__cxa_get_globals` when trying to catch
the exception (because the stack frame __cxa_get_globals frame will fail due
to tags left behind on the stack). With this change, we crash on the `y = *x;`
as expected, because the stack frame has been untagged, but the pointer hasn't.
Reviewed By: #libunwind, compnerd, MaskRay
Differential Revision: https://reviews.llvm.org/D128998
NOKEYCHECK=True
GitOrigin-RevId: a3153381af48b2e704750255a704748a13c4c4de
diff --git a/src/libunwind.cpp b/src/libunwind.cpp
index 3f9e051..292544d 100644
--- a/src/libunwind.cpp
+++ b/src/libunwind.cpp
@@ -181,6 +181,15 @@
}
_LIBUNWIND_WEAK_ALIAS(__unw_step, unw_step)
+// Move cursor to next frame and for stage2 of unwinding.
+// This resets MTE tags of tagged frames to zero.
+extern "C" _LIBUNWIND_HIDDEN int __unw_step_stage2(unw_cursor_t *cursor) {
+ _LIBUNWIND_TRACE_API("__unw_step_stage2(cursor=%p)",
+ static_cast<void *>(cursor));
+ AbstractUnwindCursor *co = (AbstractUnwindCursor *)cursor;
+ return co->step(true);
+}
+
/// Get unwind info at cursor position in stack frame.
_LIBUNWIND_HIDDEN int __unw_get_proc_info(unw_cursor_t *cursor,
unw_proc_info_t *info) {