Module Name:    src
Committed By:   matt
Date:           Wed Jan 29 18:45:21 UTC 2014

Modified Files:
        src/sys/arch/arm/arm: syscall.c undefined.c
        src/sys/arch/arm/arm32: fault.c
        src/sys/arch/arm/include: locore.h

Log Message:
Add read_insn and read_thumb_insn inlines to hide the endianness of
instructions and use them as appropriate.


To generate a diff of this commit:
cvs rdiff -u -r1.58 -r1.59 src/sys/arch/arm/arm/syscall.c
cvs rdiff -u -r1.50 -r1.51 src/sys/arch/arm/arm/undefined.c
cvs rdiff -u -r1.92 -r1.93 src/sys/arch/arm/arm32/fault.c
cvs rdiff -u -r1.7 -r1.8 src/sys/arch/arm/include/locore.h

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

Modified files:

Index: src/sys/arch/arm/arm/syscall.c
diff -u src/sys/arch/arm/arm/syscall.c:1.58 src/sys/arch/arm/arm/syscall.c:1.59
--- src/sys/arch/arm/arm/syscall.c:1.58	Sun Aug 18 06:28:18 2013
+++ src/sys/arch/arm/arm/syscall.c	Wed Jan 29 18:45:21 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: syscall.c,v 1.58 2013/08/18 06:28:18 matt Exp $	*/
+/*	$NetBSD: syscall.c,v 1.59 2014/01/29 18:45:21 matt Exp $	*/
 
 /*-
  * Copyright (c) 2000, 2003 The NetBSD Foundation, Inc.
@@ -71,7 +71,7 @@
 
 #include <sys/param.h>
 
-__KERNEL_RCSID(0, "$NetBSD: syscall.c,v 1.58 2013/08/18 06:28:18 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: syscall.c,v 1.59 2014/01/29 18:45:21 matt Exp $");
 
 #include <sys/cpu.h>
 #include <sys/device.h>
@@ -148,14 +148,10 @@ swi_handler(trapframe_t *tf)
 	else
 #endif
 	{
-	/* XXX fuword? */
 #ifdef __PROG32
-		insn = *(uint32_t *)(tf->tf_pc - INSN_SIZE);
-#if defined(__ARMEB__) && defined(_ARM_ARCH_7)
-		insn = le32toh(insn);	/* BE armv7 insn are in LE */
-#endif
+		insn = read_insn(tf->tf_pc - INSN_SIZE, true);
 #else
-		insn = *(uint32_t *)((tf->tf_r15 & R15_PC) - INSN_SIZE);
+		insn = read_insn((tf->tf_r15 & R15_PC) - INSN_SIZE, true);
 #endif
 	}
 

Index: src/sys/arch/arm/arm/undefined.c
diff -u src/sys/arch/arm/arm/undefined.c:1.50 src/sys/arch/arm/arm/undefined.c:1.51
--- src/sys/arch/arm/arm/undefined.c:1.50	Sun Aug 18 08:08:15 2013
+++ src/sys/arch/arm/arm/undefined.c	Wed Jan 29 18:45:21 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: undefined.c,v 1.50 2013/08/18 08:08:15 matt Exp $	*/
+/*	$NetBSD: undefined.c,v 1.51 2014/01/29 18:45:21 matt Exp $	*/
 
 /*
  * Copyright (c) 2001 Ben Harris.
@@ -54,7 +54,7 @@
 #include <sys/kgdb.h>
 #endif
 
-__KERNEL_RCSID(0, "$NetBSD: undefined.c,v 1.50 2013/08/18 08:08:15 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: undefined.c,v 1.51 2014/01/29 18:45:21 matt Exp $");
 
 #include <sys/kmem.h>
 #include <sys/queue.h>
@@ -303,17 +303,10 @@ undefinedinstruction(trapframe_t *frame)
 
 #ifdef THUMB_CODE
 	if (frame->tf_spsr & PSR_T_bit) {
-		const uint16_t * const pc = (const uint16_t *)(fault_pc & ~1);
-		fault_instruction = pc[0];
-#if defined(__ARMEB__) && defined(_ARM_ARCH_7)
-		fault_instruction = le16toh(fault_instruction);
-#endif
+		fault_instruction = read_thumb_insn(fault_pc, user);
 		if (fault_instruction >= 0xe000) {
-			uint16_t tmp = pc[1];
-#if defined(__ARMEB__) && defined(_ARM_ARCH_7)
-			tmp = le16toh(tmp);
-#endif
-			fault_instruction = (fault_instruction << 16) | tmp;
+			fault_instruction = (fault_instruction << 16)
+			    | read_thumb_insn(fault_pc + 2, user);
 		}
 	}
 	else
@@ -342,11 +335,7 @@ undefinedinstruction(trapframe_t *frame)
 		 * the kernel is screwed up in which case it does
 		 * not really matter does it ?
 		 */
-
-		fault_instruction = *(const uint32_t *)fault_pc;
-#if defined(__ARMEB__) && defined(_ARM_ARCH_7)
-		fault_instruction = le32toh(fault_instruction);
-#endif
+		fault_instruction = read_insn(fault_pc, user);
 	}
 
 	/* Update vmmeter statistics */

Index: src/sys/arch/arm/arm32/fault.c
diff -u src/sys/arch/arm/arm32/fault.c:1.92 src/sys/arch/arm/arm32/fault.c:1.93
--- src/sys/arch/arm/arm32/fault.c:1.92	Sat Jan 11 17:32:20 2014
+++ src/sys/arch/arm/arm32/fault.c	Wed Jan 29 18:45:21 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: fault.c,v 1.92 2014/01/11 17:32:20 matt Exp $	*/
+/*	$NetBSD: fault.c,v 1.93 2014/01/29 18:45:21 matt Exp $	*/
 
 /*
  * Copyright 2003 Wasabi Systems, Inc.
@@ -81,7 +81,7 @@
 #include "opt_kgdb.h"
 
 #include <sys/types.h>
-__KERNEL_RCSID(0, "$NetBSD: fault.c,v 1.92 2014/01/11 17:32:20 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: fault.c,v 1.93 2014/01/29 18:45:21 matt Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -168,8 +168,23 @@ static const struct data_abort data_abor
 #endif
 
 static inline void
-call_trapsignal(struct lwp *l, ksiginfo_t *ksi)
+call_trapsignal(struct lwp *l, const struct trapframe *tf, ksiginfo_t *ksi)
 {
+	if (l->l_proc->p_pid == 1 || cpu_printfataltraps) {
+		printf("%d.%d(%s): trap: signo=%d code=%d addr=%p trap=%#x\n",
+		    l->l_proc->p_pid, l->l_lid, l->l_proc->p_comm,
+		    ksi->ksi_signo, ksi->ksi_code, ksi->ksi_addr,
+		    ksi->ksi_trap);
+		printf("r0=%08x r1=%08x r2=%08x r3=%08x\n",
+		    tf->tf_r0, tf->tf_r1, tf->tf_r2, tf->tf_r3);
+		printf("r4=%08x r5=%08x r6=%08x r7=%08x\n",
+		    tf->tf_r4, tf->tf_r5, tf->tf_r6, tf->tf_r7);
+		printf("r8=%08x r9=%08x rA=%08x rB=%08x\n",
+		    tf->tf_r8, tf->tf_r9, tf->tf_r10, tf->tf_r11);
+		printf("ip=%08x sp=%08x lr=%08x pc=%08x spsr=%08x\n",
+		    tf->tf_r12, tf->tf_usr_sp, tf->tf_usr_lr, tf->tf_pc,
+		    tf->tf_spsr);
+	}
 
 	TRAPSIGNAL(l, ksi);
 }
@@ -360,7 +375,7 @@ data_abort_handler(trapframe_t *tf)
 	if (!user && (va >= VM_MIN_KERNEL_ADDRESS ||
 	    (va < VM_MIN_ADDRESS && vector_page == ARM_VECTORS_LOW)) &&
 	    __predict_true((pcb->pcb_onfault == NULL ||
-	     (ReadWord(tf->tf_pc) & 0x05200000) != 0x04200000))) {
+	     (read_insn(tf->tf_pc, false) & 0x05200000) != 0x04200000))) {
 		map = kernel_map;
 
 		/* Was the fault due to the FPE/IPKDB ? */
@@ -402,7 +417,7 @@ data_abort_handler(trapframe_t *tf)
 #ifdef THUMB_CODE
 		/* Fast track the ARM case.  */
 		if (__predict_false(tf->tf_spsr & PSR_T_bit)) {
-			u_int insn = fusword((void *)(tf->tf_pc & ~1));
+			u_int insn = read_thumb_insn(tf->tf_pc, user);
 			u_int insn_f8 = insn & 0xf800;
 			u_int insn_fe = insn & 0xfe00;
 
@@ -421,7 +436,7 @@ data_abort_handler(trapframe_t *tf)
 		else
 #endif
 		{
-			u_int insn = ReadWord(tf->tf_pc);
+			u_int insn = read_insn(tf->tf_pc, user);
 
 			if (((insn & 0x0c100000) == 0x04000000) || /* STR[B] */
 			    ((insn & 0x0e1000b0) == 0x000000b0) || /* STR[HD]*/
@@ -499,21 +514,7 @@ data_abort_handler(trapframe_t *tf)
 	UVMHIST_LOG(maphist, " <- error (%d)", error, 0, 0, 0);
 
 do_trapsignal:
-	if (l->l_proc->p_pid == 1 || cpu_printfataltraps) {
-		printf("%d.%d(%s): trap: signo=%d code=%d addr=%p trap=%#x\n",
-		     l->l_proc->p_pid, l->l_lid, l->l_proc->p_comm,
-		     ksi.ksi_signo, ksi.ksi_code, ksi.ksi_addr, ksi.ksi_trap);
-		printf("r0=%08x r1=%08x r2=%08x r3=%08x\n",
-		    tf->tf_r0, tf->tf_r1, tf->tf_r2, tf->tf_r3);
-		printf("r4=%08x r5=%08x r6=%08x r7=%08x\n",
-		    tf->tf_r4, tf->tf_r5, tf->tf_r6, tf->tf_r7);
-		printf("r8=%08x r9=%08x rA=%08x rB=%08x\n",
-		    tf->tf_r8, tf->tf_r9, tf->tf_r10, tf->tf_r11);
-		printf("ip=%08x sp=%08x lr=%08x pc=%08x spsr=%08x\n",
-		    tf->tf_r12, tf->tf_usr_sp, tf->tf_usr_lr, tf->tf_pc,
-		    tf->tf_spsr);
-	}
-	call_trapsignal(l, &ksi);
+	call_trapsignal(l, tf, &ksi);
 out:
 	/* If returning to user mode, make sure to invoke userret() */
 	if (user)
@@ -880,7 +881,7 @@ prefetch_abort_handler(trapframe_t *tf)
 	ksi.ksi_trap = fault_pc;
 
 do_trapsignal:
-	call_trapsignal(l, &ksi);
+	call_trapsignal(l, tf, &ksi);
 
 out:
 	KASSERT(!TRAP_USERMODE(tf) || (tf->tf_spsr & IF32_bits) == 0);

Index: src/sys/arch/arm/include/locore.h
diff -u src/sys/arch/arm/include/locore.h:1.7 src/sys/arch/arm/include/locore.h:1.8
--- src/sys/arch/arm/include/locore.h:1.7	Sat Jan 11 17:32:20 2014
+++ src/sys/arch/arm/include/locore.h	Wed Jan 29 18:45:20 2014
@@ -170,6 +170,42 @@ extern bool cpu_armv6_p;
 #define	CPU_IS_ARMV6_P()		true
 #endif
 
+/*
+ * User by the fault code to read the current instruction.
+ */
+static inline uint32_t
+read_insn(vaddr_t va, bool user_p)
+{
+	uint32_t insn;
+	if (user_p) {
+		__asm __volatile("ldrt %0, [%1]" : "=&r"(insn) : "r"(va));
+	} else {
+		insn = *(const uint32_t *)va;
+	}
+#if defined(__ARMEB__) && defined(_ARM_ARCH_7)
+	insn = bswap32(insn);
+#endif
+	return insn;
+}
+
+/*
+ * User by the fault code to read the current thumb instruction.
+ */
+static inline uint32_t
+read_thumb_insn(vaddr_t va, bool user_p)
+{
+	va &= ~1;
+	uint32_t insn;
+	if (user_p) {
+		__asm __volatile("ldrht %0, [%1]" : "=&r"(insn) : "r"(va));
+	} else {
+		insn = *(const uint16_t *)va;
+	}
+#if defined(__ARMEB__) && defined(_ARM_ARCH_7)
+	insn = bswap16(insn);
+#endif
+	return insn;
+}
 
 /*
  * Random cruft

Reply via email to