[libunwind] r276625 - [libunwind][ARM] Add support for Thumb1 targets

Oliver Stannard via cfe-commits cfe-commits at lists.llvm.org
Mon Jul 25 02:21:56 PDT 2016


Author: olista01
Date: Mon Jul 25 04:21:56 2016
New Revision: 276625

URL: http://llvm.org/viewvc/llvm-project?rev=276625&view=rev
Log:
[libunwind][ARM] Add support for Thumb1 targets

The Thumb1 version of the code for saving and restoring the unwind
context has a few bugs which prevent it from working:
* It uses the STM instruction without writeback, which is not valid for Thumb1
  (It was introduced in Thumb2).
* It only saves/restores the low 8 registers, the sp and the lr, so if a
  program uses r8-r12 they will not be correctly restored when throwing an
  exception.

There aren't currently any Thumb1 build-bots to test this, but we have
been successfully running the libc++abi and libc++ test suites on
Cortex-M0 models, as well as some other test suites that use C++
exceptions on a downstream version of libunwind with this patch applied.

Differential Revision: https://reviews.llvm.org/D22292


Modified:
    libunwind/trunk/src/UnwindRegistersRestore.S
    libunwind/trunk/src/UnwindRegistersSave.S

Modified: libunwind/trunk/src/UnwindRegistersRestore.S
URL: http://llvm.org/viewvc/llvm-project/libunwind/trunk/src/UnwindRegistersRestore.S?rev=276625&r1=276624&r2=276625&view=diff
==============================================================================
--- libunwind/trunk/src/UnwindRegistersRestore.S (original)
+++ libunwind/trunk/src/UnwindRegistersRestore.S Mon Jul 25 04:21:56 2016
@@ -322,9 +322,18 @@ DEFINE_LIBUNWIND_PRIVATE_FUNCTION(_ZN9li
 @
   .p2align 2
 DEFINE_LIBUNWIND_PRIVATE_FUNCTION(_ZN9libunwind13Registers_arm20restoreCoreAndJumpToEv)
-#if !defined(__ARM_ARCH_ISA_ARM)
-  ldr r2, [r0, #52]
-  ldr r3, [r0, #60]
+#if !defined(__ARM_ARCH_ISA_ARM) && __ARM_ARCH_ISA_THUMB == 1
+  @ r8-r11: ldm into r1-r4, then mov to r8-r11
+  adds r0, #0x20
+  ldm r0!, {r1-r4}
+  subs r0, #0x30
+  mov r8, r1
+  mov r9, r2
+  mov r10, r3
+  mov r11, r4
+  @ r12 does not need loading, it it the intra-procedure-call scratch register
+  ldr r2, [r0, #0x34]
+  ldr r3, [r0, #0x3c]
   mov sp, r2
   mov lr, r3         @ restore pc into lr
   ldm r0, {r0-r7}

Modified: libunwind/trunk/src/UnwindRegistersSave.S
URL: http://llvm.org/viewvc/llvm-project/libunwind/trunk/src/UnwindRegistersSave.S?rev=276625&r1=276624&r2=276625&view=diff
==============================================================================
--- libunwind/trunk/src/UnwindRegistersSave.S (original)
+++ libunwind/trunk/src/UnwindRegistersSave.S Mon Jul 25 04:21:56 2016
@@ -309,13 +309,24 @@ DEFINE_LIBUNWIND_FUNCTION(unw_getcontext
 @
   .p2align 2
 DEFINE_LIBUNWIND_FUNCTION(unw_getcontext)
-#if !defined(__ARM_ARCH_ISA_ARM)
-  stm r0, {r0-r7}
+#if !defined(__ARM_ARCH_ISA_ARM) && __ARM_ARCH_ISA_THUMB == 1
+  stm r0!, {r0-r7}
+  mov r1, r8
+  mov r2, r9
+  mov r3, r10
+  stm r0!, {r1-r3}
+  mov r1, r11
   mov r2, sp
   mov r3, lr
-  str r2, [r0, #52]
-  str r3, [r0, #56]
-  str r3, [r0, #60]  @ store return address as pc
+  str r1, [r0, #0]   @ r11
+  @ r12 does not need storing, it it the intra-procedure-call scratch register
+  str r2, [r0, #8]   @ sp
+  str r3, [r0, #12]  @ lr
+  str r3, [r0, #16]  @ store return address as pc
+  @ T1 does not have a non-cpsr-clobbering register-zeroing instruction.
+  @ It is safe to use here though because we are about to return, and cpsr is
+  @ not expected to be preserved.
+  movs r0, #0        @ return UNW_ESUCCESS
 #else
   @ 32bit thumb-2 restrictions for stm:
   @ . the sp (r13) cannot be in the list
@@ -324,13 +335,6 @@ DEFINE_LIBUNWIND_FUNCTION(unw_getcontext
   str sp, [r0, #52]
   str lr, [r0, #56]
   str lr, [r0, #60]  @ store return address as pc
-#endif
-#if __ARM_ARCH_ISA_THUMB == 1
-  @ T1 does not have a non-cpsr-clobbering register-zeroing instruction.
-  @ It is safe to use here though because we are about to return, and cpsr is
-  @ not expected to be preserved.
-  movs r0, #0        @ return UNW_ESUCCESS
-#else
   mov r0, #0         @ return UNW_ESUCCESS
 #endif
   JMP(lr)




More information about the cfe-commits mailing list