Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 22 Jun 2016 12:05:08 +0000 (UTC)
From:      Andrew Turner <andrew@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r302084 - head/sys/arm64/arm64
Message-ID:  <201606221205.u5MC58Dc086057@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: andrew
Date: Wed Jun 22 12:05:08 2016
New Revision: 302084
URL: https://svnweb.freebsd.org/changeset/base/302084

Log:
  Fix a race when the hardware has raised an exception with an unknown or
  uncategorised reason. We need to read the fault address register before
  enabling interrupts as the interrupt handler may cause this register to
  change.
  
  Approved by:	re (marius, kib)
  Obtained from:	ABT Systems Ltd
  Sponsored by:	The FreeBSD Foundation

Modified:
  head/sys/arm64/arm64/trap.c

Modified: head/sys/arm64/arm64/trap.c
==============================================================================
--- head/sys/arm64/arm64/trap.c	Wed Jun 22 11:45:30 2016	(r302083)
+++ head/sys/arm64/arm64/trap.c	Wed Jun 22 12:05:08 2016	(r302084)
@@ -313,13 +313,11 @@ do_el1h_sync(struct trapframe *frame)
  * instruction results in an exception with an unknown reason.
  */
 static void
-el0_excp_unknown(struct trapframe *frame)
+el0_excp_unknown(struct trapframe *frame, uint64_t far)
 {
 	struct thread *td;
-	uint64_t far;
 
 	td = curthread;
-	far = READ_SPECIALREG(far_el1);
 	call_trapsignal(td, SIGILL, ILL_ILLTRP, (void *)far);
 	userret(td, frame);
 }
@@ -342,6 +340,7 @@ do_el0_sync(struct trapframe *frame)
 	esr = READ_SPECIALREG(esr_el1);
 	exception = ESR_ELx_EXCEPTION(esr);
 	switch (exception) {
+	case EXCP_UNKNOWN:
 	case EXCP_INSN_ABORT_L:
 	case EXCP_DATA_ABORT_L:
 	case EXCP_DATA_ABORT:
@@ -371,7 +370,7 @@ do_el0_sync(struct trapframe *frame)
 		data_abort(frame, esr, far, 1);
 		break;
 	case EXCP_UNKNOWN:
-		el0_excp_unknown(frame);
+		el0_excp_unknown(frame, far);
 		break;
 	case EXCP_SP_ALIGN:
 		call_trapsignal(td, SIGBUS, BUS_ADRALN, (void *)frame->tf_sp);



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201606221205.u5MC58Dc086057>