void nautilus_machine_check(unsigned long vector, unsigned long la_ptr, struct pt_regs *regs) { char *mchk_class; /* Now for some analysis. Machine checks fall into two classes -- those picked up by the system, and those picked up by the CPU. Add to that the two levels of severity - correctable or not. */ if (vector == SCB_Q_SYSMCHK && ((IRONGATE0->dramms & 0x300) == 0x300)) { unsigned long nmi_ctl; /* Clear ALI NMI */ nmi_ctl = inb(0x61); nmi_ctl |= 0x0c; outb(nmi_ctl, 0x61); nmi_ctl &= ~0x0c; outb(nmi_ctl, 0x61); /* Write again clears error bits. */ IRONGATE0->stat_cmd = IRONGATE0->stat_cmd & ~0x100; mb(); IRONGATE0->stat_cmd; /* Write again clears error bits. */ IRONGATE0->dramms = IRONGATE0->dramms; mb(); IRONGATE0->dramms; draina(); wrmces(0x7); mb(); return; } if (vector == SCB_Q_SYSERR) mchk_class = "Correctable"; else if (vector == SCB_Q_SYSMCHK) mchk_class = "Fatal"; else { ev6_machine_check(vector, la_ptr, regs); return; } printk(KERN_CRIT "NAUTILUS Machine check 0x%lx " "[%s System Machine Check (NMI)]\n", vector, mchk_class); naut_sys_machine_check(vector, la_ptr, regs); /* Tell the PALcode to clear the machine check */ draina(); wrmces(0x7); mb(); }
void nautilus_machine_check(unsigned long vector, unsigned long la_ptr) { char *mchk_class; /* */ if (vector == SCB_Q_SYSMCHK && ((IRONGATE0->dramms & 0x300) == 0x300)) { unsigned long nmi_ctl; /* */ nmi_ctl = inb(0x61); nmi_ctl |= 0x0c; outb(nmi_ctl, 0x61); nmi_ctl &= ~0x0c; outb(nmi_ctl, 0x61); /* */ IRONGATE0->stat_cmd = IRONGATE0->stat_cmd & ~0x100; mb(); IRONGATE0->stat_cmd; /* */ IRONGATE0->dramms = IRONGATE0->dramms; mb(); IRONGATE0->dramms; draina(); wrmces(0x7); mb(); return; } if (vector == SCB_Q_SYSERR) mchk_class = "Correctable"; else if (vector == SCB_Q_SYSMCHK) mchk_class = "Fatal"; else { ev6_machine_check(vector, la_ptr); return; } printk(KERN_CRIT "NAUTILUS Machine check 0x%lx " "[%s System Machine Check (NMI)]\n", vector, mchk_class); naut_sys_machine_check(vector, la_ptr, get_irq_regs()); /* */ draina(); wrmces(0x7); mb(); }
static int __init mcpcia_probe_hose(int h) { int cpu = smp_processor_id(); int mid = MCPCIA_HOSE2MID(h); unsigned int pci_rev; /* Gotta be REAL careful. If hose is absent, we get an mcheck. */ mb(); mb(); draina(); wrmces(7); mcheck_expected(cpu) = 2; /* indicates probing */ mcheck_taken(cpu) = 0; mcheck_extra(cpu) = mid; mb(); /* Access the bus revision word. */ pci_rev = *(vuip)MCPCIA_REV(mid); mb(); mb(); /* magic */ if (mcheck_taken(cpu)) { mcheck_taken(cpu) = 0; pci_rev = 0xffffffff; mb(); } mcheck_expected(cpu) = 0; mb(); return (pci_rev >> 16) == PCI_CLASS_BRIDGE_HOST; }
static void mikasa_apecs_machine_check(unsigned long vector, unsigned long la_ptr) { #define MCHK_NO_DEVSEL 0x205U #define MCHK_NO_TABT 0x204U struct el_common *mchk_header; unsigned int code; mchk_header = (struct el_common *)la_ptr; /* Clear the error before any reporting. */ mb(); mb(); /* magic */ draina(); apecs_pci_clr_err(); wrmces(0x7); mb(); code = mchk_header->code; process_mcheck_info(vector, la_ptr, "MIKASA APECS", (mcheck_expected(0) && (code == MCHK_NO_DEVSEL || code == MCHK_NO_TABT))); }
void polaris_machine_check(unsigned long vector, unsigned long la_ptr, struct pt_regs * regs) { /* Clear the error before any reporting. */ mb(); mb(); draina(); polaris_pci_clr_err(); wrmces(0x7); mb(); process_mcheck_info(vector, la_ptr, regs, "POLARIS", mcheck_expected(0)); }
void mcpcia_machine_check(unsigned long vector, unsigned long la_ptr, struct pt_regs * regs) { struct el_common *mchk_header; struct el_MCPCIA_uncorrected_frame_mcheck *mchk_logout; unsigned int cpu = smp_processor_id(); int expected; mchk_header = (struct el_common *)la_ptr; mchk_logout = (struct el_MCPCIA_uncorrected_frame_mcheck *)la_ptr; expected = mcheck_expected(cpu); mb(); mb(); /* magic */ draina(); switch (expected) { case 0: { /* FIXME: how do we figure out which hose the error was on? */ struct pci_controler *hose; for (hose = hose_head; hose; hose = hose->next) mcpcia_pci_clr_err(MCPCIA_HOSE2MID(hose->index)); break; } case 1: mcpcia_pci_clr_err(mcheck_extra(cpu)); break; default: /* Otherwise, we're being called from mcpcia_probe_hose and there's no hose clear an error from. */ break; } wrmces(0x7); mb(); process_mcheck_info(vector, la_ptr, regs, "MCPCIA", expected != 0); if (!expected && vector != 0x620 && vector != 0x630) { mcpcia_print_uncorrectable(mchk_logout); mcpcia_print_system_area(la_ptr); } }
void ev6_machine_check(u64 vector, u64 la_ptr) { struct el_common *mchk_header = (struct el_common *)la_ptr; /* * Sync the processor */ mb(); draina(); /* * Parse the logout frame without printing first. If the only error(s) * found are have a disposition of "dismiss", then just dismiss them * and don't print any message */ if (ev6_process_logout_frame(mchk_header, 0) != MCHK_DISPOSITION_DISMISS) { char *saved_err_prefix = err_print_prefix; err_print_prefix = KERN_CRIT; /* * Either a nondismissable error was detected or no * recognized error was detected in the logout frame * -- report the error in either case */ printk("%s*CPU %s Error (Vector 0x%x) reported on CPU %d:\n", err_print_prefix, (vector == SCB_Q_PROCERR)?"Correctable":"Uncorrectable", (unsigned int)vector, (int)smp_processor_id()); ev6_process_logout_frame(mchk_header, 1); dik_show_regs(get_irq_regs(), NULL); err_print_prefix = saved_err_prefix; } /* * Release the logout frame */ wrmces(0x7); mb(); }
void ev7_machine_check(u64 vector, u64 la_ptr, struct pt_regs *regs) { /* * Sync the processor */ mb(); draina(); /* * Parse the logout frame without printing first. If the only error(s) * found are have a disposition of "dismiss", then just dismiss them * and don't print any message */ printk("%sEV7 MACHINE CHECK vector %lx\n", err_print_prefix, vector); /* * Release the logout frame */ wrmces(0x7); mb(); }
void polaris_machine_check(unsigned long vector, unsigned long la_ptr, struct pt_regs * regs) { struct el_common *mchk_header; struct el_POLARIS_sysdata_mcheck *mchk_sysdata; mchk_header = (struct el_common *)la_ptr; mchk_sysdata = (struct el_POLARIS_sysdata_mcheck *)(la_ptr+mchk_header->sys_offset); #if 0 DBG_MCK(("polaris_machine_check: vector=0x%lx la_ptr=0x%lx\n", vector, la_ptr)); DBG_MCK(("\t\t pc=0x%lx size=0x%x procoffset=0x%x sysoffset 0x%x\n", regs->pc, mchk_header->size, mchk_header->proc_offset, mchk_header->sys_offset)); DBG_MCK(("polaris_machine_check: expected %d status 0x%lx\n", POLARIS_mcheck_expected, mchk_sysdata->psc_status)); #endif #ifdef DEBUG_MCHECK_DUMP { unsigned long *ptr; int i; ptr = (unsigned long *)la_ptr; for (i = 0; i < mchk_header->size / sizeof(long); i += 2) { printk(" +%lx %lx %lx\n", i*sizeof(long), ptr[i], ptr[i+1]); } } #endif /* DEBUG_MCHECK_DUMP */ /* * Check if machine check is due to a badaddr() and if so, * ignore the machine check. */ mb(); mb(); if (POLARIS_mcheck_expected) { DBG_MCK(("POLARIS machine check expected\n")); POLARIS_mcheck_expected = 0; POLARIS_mcheck_taken = 1; mb(); mb(); draina(); polaris_pci_clr_err(); wrmces(0x7); mb(); } #if 1 else { printk("POLARIS machine check NOT expected\n") ; DBG_MCK(("polaris_machine_check: vector=0x%lx la_ptr=0x%lx\n", vector, la_ptr)); DBG_MCK(("\t\t pc=0x%lx size=0x%x procoffset=0x%x sysoffset 0x%x\n", regs->pc, mchk_header->size, mchk_header->proc_offset, mchk_header->sys_offset)); POLARIS_mcheck_expected = 0; POLARIS_mcheck_taken = 1; mb(); mb(); draina(); polaris_pci_clr_err(); wrmces(0x7); mb(); } #endif }