Source-Changes-HG archive

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

[src/netbsd-6]: src/sys/arch/sparc64/sparc64 Pull up following revision(s) (r...



details:   https://anonhg.NetBSD.org/src/rev/1be06fed56cf
branches:  netbsd-6
changeset: 773946:1be06fed56cf
user:      riz <riz%NetBSD.org@localhost>
date:      Wed Mar 21 16:10:21 2012 +0000

description:
Pull up following revision(s) (requested by mrg in ticket #131):
        sys/arch/sparc64/sparc64/trap.c: revision 1.170
        sys/arch/sparc64/sparc64/trap.c: revision 1.171
        sys/arch/sparc64/sparc64/locore.s: revision 1.341
port the corrected ECC error handling code from freebsd.  i noticed my U10
took one of these and then hang.  it shouldn't hang, there's a 'sir' here that
doesn't seem to reset properly.  oh well.
tested by simulated a trap via 'ta 0x10' and considering that the same, but
it hasn't been tested against a real ECC error yet.
count ECC corrected traps with evcnt(9).

diffstat:

 sys/arch/sparc64/sparc64/locore.s |   6 +-
 sys/arch/sparc64/sparc64/trap.c   |  62 +++++++++++++++++++++++++++++++++++++-
 2 files changed, 63 insertions(+), 5 deletions(-)

diffs (142 lines):

diff -r f1fe38143255 -r 1be06fed56cf sys/arch/sparc64/sparc64/locore.s
--- a/sys/arch/sparc64/sparc64/locore.s Wed Mar 21 16:07:11 2012 +0000
+++ b/sys/arch/sparc64/sparc64/locore.s Wed Mar 21 16:10:21 2012 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: locore.s,v 1.338.8.1 2012/03/05 20:59:25 sborrill Exp $        */
+/*     $NetBSD: locore.s,v 1.338.8.2 2012/03/21 16:10:21 riz Exp $     */
 
 /*
  * Copyright (c) 2006-2010 Matthew R. Green
@@ -491,7 +491,7 @@
        VTRAP(0x060, interrupt_vector); ! 060 = interrupt vector
        TRAP(T_PA_WATCHPT)              ! 061 = physical address data watchpoint
        TRAP(T_VA_WATCHPT)              ! 062 = virtual address data watchpoint
-       UTRAP(T_ECCERR)                 ! We'll implement this one later
+       TRAP(T_ECCERR)                  ! 063 = corrected ECC error
 ufast_IMMU_miss:                       ! 064 = fast instr access MMU miss
        ldxa    [%g0] ASI_IMMU_8KPTR, %g2 ! Load IMMU 8K TSB pointer
 #ifdef NO_TSB
@@ -727,7 +727,7 @@
        VTRAP(0x060, interrupt_vector); ! 060 = interrupt vector
        TRAP(T_PA_WATCHPT)              ! 061 = physical address data watchpoint
        TRAP(T_VA_WATCHPT)              ! 062 = virtual address data watchpoint
-       UTRAP(T_ECCERR)                 ! We'll implement this one later
+       TRAP(T_ECCERR)                  ! 063 = corrected ECC error
 kfast_IMMU_miss:                       ! 064 = fast instr access MMU miss
        ldxa    [%g0] ASI_IMMU_8KPTR, %g2 ! Load IMMU 8K TSB pointer
 #ifdef NO_TSB
diff -r f1fe38143255 -r 1be06fed56cf sys/arch/sparc64/sparc64/trap.c
--- a/sys/arch/sparc64/sparc64/trap.c   Wed Mar 21 16:07:11 2012 +0000
+++ b/sys/arch/sparc64/sparc64/trap.c   Wed Mar 21 16:10:21 2012 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: trap.c,v 1.168 2011/07/30 19:29:12 martin Exp $ */
+/*     $NetBSD: trap.c,v 1.168.8.1 2012/03/21 16:10:21 riz Exp $ */
 
 /*
  * Copyright (c) 1996-2002 Eduardo Horvath.  All rights reserved.
@@ -50,7 +50,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: trap.c,v 1.168 2011/07/30 19:29:12 martin Exp $");
+__KERNEL_RCSID(0, "$NetBSD: trap.c,v 1.168.8.1 2012/03/21 16:10:21 riz Exp $");
 
 #include "opt_ddb.h"
 #include "opt_multiprocessor.h"
@@ -94,6 +94,8 @@
 #include <machine/svr4_32_machdep.h>
 #endif
 
+#include <sparc64/sparc64/cache.h>
+
 #include <sparc/fpu/fpu_extern.h>
 
 #ifndef offsetof
@@ -159,6 +161,10 @@
 #define Debugger()
 #endif
 
+struct evcnt ecc_corrected =
+        EVCNT_INITIALIZER(EVCNT_TYPE_MISC,0,"ECC","corrected");
+EVCNT_ATTACH_STATIC(ecc_corrected);
+
 /*
  * Initial FPU state is all registers == all 1s, everything else == all 0s.
  * This makes every floating point register a signalling NaN, with sign bit
@@ -371,6 +377,7 @@
        u_long sfsr);
 void text_access_error(struct trapframe64 *, unsigned int, vaddr_t, u_long,
        vaddr_t, u_long);
+void ecc_corrected_error(unsigned int type, vaddr_t pc);
 
 #ifdef DEBUG
 void print_trapframe(struct trapframe64 *);
@@ -540,6 +547,9 @@
                        /* Enable the FPU */
                        tf->tf_tstate |= TSTATE_PEF;
                        return;
+               } else if (type == T_ECCERR) {
+                       ecc_corrected_error(type, pc);
+                       return;
                }
                goto dopanic;
        }
@@ -855,6 +865,9 @@
                ksi.ksi_code = FPE_INTOVF;
                ksi.ksi_addr = (void *)pc;
                break;
+       case T_ECCERR:
+               ecc_corrected_error(type, pc);
+               break;
        }
        if (sig != 0) {
                ksi.ksi_signo = sig;
@@ -1622,3 +1635,48 @@
        }
 #endif
 }
+
+/*
+ * Handle an ECC corrected event.
+ */
+void
+ecc_corrected_error(unsigned int type, vaddr_t pc)
+{
+       uint64_t eeer, afar, afsr;
+       char buf[128];
+       int s;
+
+       /* Clear the error */
+       eeer = ldxa(0, ASI_ERROR_EN_REG);
+       s = intr_disable();
+       stxa(0, ASI_ERROR_EN_REG,
+           eeer & ~(P_EER_NCEEN | P_EER_CEEN));
+       membar_Sync();
+       intr_restore(s);
+
+       /* Flush the caches in order ensure no corrupt data got installed. */
+       blast_dcache();
+       blast_icache();
+
+#if 0
+       /* Ensure the caches are still turned on (should be). */
+       cache_enable(PCPU_GET(impl));
+#endif
+
+       /* Grab the current AFSR/AFAR, and clear the error from the AFSR. */
+       afar = ldxa(0, ASI_AFAR);
+       afsr = ldxa(0, ASI_AFSR);
+       s = intr_disable();
+       stxa(0, ASI_AFSR, ldxa(0, ASI_AFSR));
+       membar_Sync();
+       intr_restore(s);
+       ecc_corrected.ev_count++;
+       snprintb(buf, sizeof(buf), AFSR_BITS, afsr);
+       printf("corrected ECC error: pc %p afsr %"PRIx64" (%s) addr %"PRIx64"\n", (void *)pc, afsr, buf, afar);
+
+       /* Turn (non-)correctable error reporting back on. */
+       s = intr_disable();
+       stxa(0, ASI_ERROR_EN_REG, eeer);
+       membar_Sync();
+       intr_restore(s);
+}



Home | Main Index | Thread Index | Old Index