Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/hppa/hppa Deal with unaligned DIR32 relocs as found...



details:   https://anonhg.NetBSD.org/src/rev/4944952fb6c5
branches:  trunk
changeset: 326521:4944952fb6c5
user:      skrll <skrll%NetBSD.org@localhost>
date:      Sat Feb 01 08:05:51 2014 +0000

description:
Deal with unaligned DIR32 relocs as found in debug information.

diffstat:

 sys/arch/hppa/hppa/kobj_machdep.c |  35 ++++++++++++++++++++++++++++++++---
 1 files changed, 32 insertions(+), 3 deletions(-)

diffs (63 lines):

diff -r 6008f1402ab6 -r 4944952fb6c5 sys/arch/hppa/hppa/kobj_machdep.c
--- a/sys/arch/hppa/hppa/kobj_machdep.c Sat Feb 01 01:34:01 2014 +0000
+++ b/sys/arch/hppa/hppa/kobj_machdep.c Sat Feb 01 08:05:51 2014 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: kobj_machdep.c,v 1.13 2013/11/16 17:18:42 skrll Exp $  */
+/*     $NetBSD: kobj_machdep.c,v 1.14 2014/02/01 08:05:51 skrll Exp $  */
 
 /*-
  * Copyright (c) 2008 The NetBSD Foundation, Inc.
@@ -52,7 +52,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: kobj_machdep.c,v 1.13 2013/11/16 17:18:42 skrll Exp $");
+__KERNEL_RCSID(0, "$NetBSD: kobj_machdep.c,v 1.14 2014/02/01 08:05:51 skrll Exp $");
 
 #define        ELFSIZE         ARCH_ELFSIZE
 
@@ -97,6 +97,35 @@
         return R(x + RND(constant)) + (constant - RND(constant));
 }
 
+/*
+ * It is possible for the compiler to emit relocations for unaligned data.
+ * We handle this situation with these inlines.
+ */
+#define        RELOC_ALIGNED_P(x) \
+       (((uintptr_t)(x) & (sizeof(void *) - 1)) == 0)
+
+static inline Elf_Addr
+load_ptr(void *where)
+{
+       if (__predict_true(RELOC_ALIGNED_P(where)))
+               return *(Elf_Addr *)where;
+       else {
+               Elf_Addr res;
+
+               (void)memcpy(&res, where, sizeof(res));
+               return res;
+       }
+}
+
+static inline void
+store_ptr(void *where, Elf_Addr val)
+{
+       if (__predict_true(RELOC_ALIGNED_P(where)))
+               *(Elf_Addr *)where = val;
+       else
+               (void)memcpy(where, &val, sizeof(val));
+}
+
 int
 kobj_reloc(kobj_t ko, uintptr_t relocbase, const void *data,
     bool isrela, bool local)
@@ -185,7 +214,7 @@
        case R_TYPE(PCREL32):
        case R_TYPE(PLABEL32):
        case R_TYPE(SEGREL32):
-               *where = value;
+               store_ptr(where, value);
                break;
 
        case R_TYPE(DIR14R):



Home | Main Index | Thread Index | Old Index