Module Name:    src
Committed By:   joerg
Date:           Sun May 11 02:07:35 UTC 2014

Modified Files:
        src/sys/lib/libunwind: Registers.hpp unwind_registers.S

Log Message:
Support DWARFish unwind for ARM.


To generate a diff of this commit:
cvs rdiff -u -r1.15 -r1.16 src/sys/lib/libunwind/Registers.hpp
cvs rdiff -u -r1.12 -r1.13 src/sys/lib/libunwind/unwind_registers.S

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/lib/libunwind/Registers.hpp
diff -u src/sys/lib/libunwind/Registers.hpp:1.15 src/sys/lib/libunwind/Registers.hpp:1.16
--- src/sys/lib/libunwind/Registers.hpp:1.15	Sat Apr 26 23:17:38 2014
+++ src/sys/lib/libunwind/Registers.hpp	Sun May 11 02:07:35 2014
@@ -240,21 +240,24 @@ enum {
   DWARF_ARM32_R0 = 0,
   DWARF_ARM32_R15 = 15,
   DWARF_ARM32_SPSR = 128,
-  DWARF_ARM32_D0 = 256,		// VFP-v3/Neon
+  DWARF_ARM32_OLD_S0 = 64,
+  DWARF_ARM32_OLD_S31 = 91,
+  DWARF_ARM32_D0 = 256,
   DWARF_ARM32_D31 = 287,
   REGNO_ARM32_R0 = 0,
   REGNO_ARM32_SP = 13,
   REGNO_ARM32_R15 = 15,
   REGNO_ARM32_SPSR = 16,
-  REGNO_ARM32_D0 = 0,
-  REGNO_ARM32_D31 = 31,
+  REGNO_ARM32_D0 = 17,
+  REGNO_ARM32_D15 = 32,
+  REGNO_ARM32_D31 = 48,
 };
 
 class Registers_arm32 {
 public:
   enum {
     LAST_REGISTER = REGNO_ARM32_D31,
-    LAST_RESTORE_REG = REGNO_ARM32_SPSR,
+    LAST_RESTORE_REG = REGNO_ARM32_D31,
     RETURN_OFFSET = 0,
   };
 
@@ -263,15 +266,19 @@ public:
   static int dwarf2regno(int num) {
     if (num >= DWARF_ARM32_R0 && num <= DWARF_ARM32_R15)
       return REGNO_ARM32_R0 + (num - DWARF_ARM32_R0);
-    if (num >= DWARF_ARM32_D0 && num <= DWARF_ARM32_D31)
-      return REGNO_ARM32_D0 + (num - DWARF_ARM32_D0);
     if (num == DWARF_ARM32_SPSR)
       return REGNO_ARM32_SPSR;
+    if (num >= DWARF_ARM32_D0 && num <= DWARF_ARM32_D31)
+      return REGNO_ARM32_D0 + (num - DWARF_ARM32_D0);
+    if (num >= DWARF_ARM32_OLD_S0 && num <= DWARF_ARM32_OLD_S31) {
+      assert(num % 2 == 0);
+      return REGNO_ARM32_D0 + (num - DWARF_ARM32_OLD_S0) / 2;
+    }
     return LAST_REGISTER + 1;
   }
 
   bool validRegister(int num) const {
-    return num >= 0 && num <= LAST_RESTORE_REG;
+    return num >= 0 && num <= REGNO_ARM32_SPSR;
   }
 
   uint64_t getRegister(int num) const {
@@ -297,14 +304,28 @@ public:
   }
 
   void copyFloatVectorRegister(int num, uint64_t addr_) {
+    if (num <= REGNO_ARM32_D15) {
+      if ((flags & 1) == 0) {
+        lazyVFP1();
+        flags |= 1;
+      }
+    } else {
+      if ((flags & 2) == 0) {
+        lazyVFP3();
+        flags |= 2;
+      }
+    }
     const void *addr = reinterpret_cast<const void *>(addr_);
     memcpy(fpreg + (num - REGNO_ARM32_D0), addr, sizeof(fpreg[0]));
   }
 
+  __dso_hidden void lazyVFP1();
+  __dso_hidden void lazyVFP3();
   __dso_hidden void jumpto() const __dead;
 
 private:
   uint32_t reg[REGNO_ARM32_SPSR + 1];
+  uint32_t flags;
   uint64_t fpreg[32];
 };
 
@@ -930,7 +951,7 @@ typedef Registers_x86 NativeUnwindRegist
 typedef Registers_x86_64 NativeUnwindRegisters;
 #elif __powerpc__
 typedef Registers_ppc32 NativeUnwindRegisters;
-#elif __arm__ && !defined(__ARM_EABI__)
+#elif __arm__
 typedef Registers_arm32 NativeUnwindRegisters;
 #elif __vax__
 typedef Registers_vax NativeUnwindRegisters;

Index: src/sys/lib/libunwind/unwind_registers.S
diff -u src/sys/lib/libunwind/unwind_registers.S:1.12 src/sys/lib/libunwind/unwind_registers.S:1.13
--- src/sys/lib/libunwind/unwind_registers.S:1.12	Sat Apr 26 20:15:48 2014
+++ src/sys/lib/libunwind/unwind_registers.S	Sun May 11 02:07:35 2014
@@ -269,20 +269,44 @@ ENTRY(_ZNK7_Unwind15Registers_ppc326jump
 	bctr
 #endif
 
-#if defined(__arm__) && !defined(__ARM_EABI__)
+#if defined(__arm__)
+	.fpu vfpv3
 	.hidden _ZN7_Unwind15Registers_arm32C1Ev
 ENTRY(_ZN7_Unwind15Registers_arm32C1Ev)
 	stmia	r0, {r0-r14}
-
 	str	lr, [r0, #60]	/* PC */
 	mrs	r1, cpsr
 	str	r1, [r0, #64]	/* CPSR */
-
+	mov	r1, #0
+	str	r1, [r0, #68]
 	RET
 END(_ZN7_Unwind15Registers_arm32C1Ev)
 
+	.hidden _ZN7_Unwind15Registers_arm328lazyVFP1Ev
+ENTRY(_ZN7_Unwind15Registers_arm328lazyVFP1Ev)
+	add	r0, #72
+	vstmia	r0, {d0-d15}
+END(_ZN7_Unwind15Registers_arm328lazyVFP1Ev)
+
+	.hidden _ZN7_Unwind15Registers_arm328lazyVFP3Ev
+ENTRY(_ZN7_Unwind15Registers_arm328lazyVFP3Ev)
+	add	r0, #200
+	vstmia	r0, {d16-d31}
+END(_ZN7_Unwind15Registers_arm328lazyVFP3Ev)
+
 	.hidden _ZNK7_Unwind15Registers_arm326jumptoEv
 ENTRY(_ZNK7_Unwind15Registers_arm326jumptoEv)
+	ldrb	r1, [r0, #68]
+	tst	r1, #1
+	beq	.Lnovfp1
+	add	r2, r0, #72
+	vldmia	r2, {d0-d15}
+.Lnovfp1:
+	tst	r1, #2
+	beq	.Lnovfp3
+	add	r2, r0, #200
+	vldmia	r2, {d16-d31}
+.Lnovfp3:
 	ldr	r1, [r0, #64]
 	msr	cpsr_sxc, r1
 	ldmia	r0, {r0-r15}

Reply via email to