opal.c (b746e3e01e70d23ef53dcde1203ab78a1b7ac514) | opal.c (6fcd6baa90aeec9dcbe30786e15c125bf50503b2) |
---|---|
1/* 2 * PowerNV OPAL high level interfaces 3 * 4 * Copyright 2011 IBM Corp. 5 * 6 * This program is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU General Public License 8 * as published by the Free Software Foundation; either version --- 22 unchanged lines hidden (view full) --- 31#include <linux/console.h> 32#include <linux/sched/debug.h> 33 34#include <asm/machdep.h> 35#include <asm/opal.h> 36#include <asm/firmware.h> 37#include <asm/mce.h> 38#include <asm/imc-pmu.h> | 1/* 2 * PowerNV OPAL high level interfaces 3 * 4 * Copyright 2011 IBM Corp. 5 * 6 * This program is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU General Public License 8 * as published by the Free Software Foundation; either version --- 22 unchanged lines hidden (view full) --- 31#include <linux/console.h> 32#include <linux/sched/debug.h> 33 34#include <asm/machdep.h> 35#include <asm/opal.h> 36#include <asm/firmware.h> 37#include <asm/mce.h> 38#include <asm/imc-pmu.h> |
39#include <asm/bug.h> |
|
39 40#include "powernv.h" 41 42/* /sys/firmware/opal */ 43struct kobject *opal_kobj; 44 45struct opal { 46 u64 base; --- 373 unchanged lines hidden (view full) --- 420 recovered = 0; 421 } else if (evt->disposition == MCE_DISPOSITION_RECOVERED) { 422 /* Platform corrected itself */ 423 recovered = 1; 424 } else if (evt->severity == MCE_SEV_FATAL) { 425 /* Fatal machine check */ 426 pr_err("Machine check interrupt is fatal\n"); 427 recovered = 0; | 40 41#include "powernv.h" 42 43/* /sys/firmware/opal */ 44struct kobject *opal_kobj; 45 46struct opal { 47 u64 base; --- 373 unchanged lines hidden (view full) --- 421 recovered = 0; 422 } else if (evt->disposition == MCE_DISPOSITION_RECOVERED) { 423 /* Platform corrected itself */ 424 recovered = 1; 425 } else if (evt->severity == MCE_SEV_FATAL) { 426 /* Fatal machine check */ 427 pr_err("Machine check interrupt is fatal\n"); 428 recovered = 0; |
428 } else if ((evt->severity == MCE_SEV_ERROR_SYNC) && 429 (user_mode(regs) && !is_global_init(current))) { | 429 } 430 431 if (!recovered && evt->severity == MCE_SEV_ERROR_SYNC) { |
430 /* | 432 /* |
431 * For now, kill the task if we have received exception when 432 * in userspace. | 433 * Try to kill processes if we get a synchronous machine check 434 * (e.g., one caused by execution of this instruction). This 435 * will devolve into a panic if we try to kill init or are in 436 * an interrupt etc. |
433 * 434 * TODO: Queue up this address for hwpoisioning later. | 437 * 438 * TODO: Queue up this address for hwpoisioning later. |
439 * TODO: This is not quite right for d-side machine 440 * checks ->nip is not necessarily the important 441 * address. |
|
435 */ | 442 */ |
436 _exception(SIGBUS, regs, BUS_MCEERR_AR, regs->nip); 437 recovered = 1; | 443 if ((user_mode(regs))) { 444 _exception(SIGBUS, regs, BUS_MCEERR_AR, regs->nip); 445 recovered = 1; 446 } else if (die_will_crash()) { 447 /* 448 * die() would kill the kernel, so better to go via 449 * the platform reboot code that will log the 450 * machine check. 451 */ 452 recovered = 0; 453 } else { 454 die("Machine check", regs, SIGBUS); 455 recovered = 1; 456 } |
438 } | 457 } |
458 |
|
439 return recovered; 440} 441 442void pnv_platform_error_reboot(struct pt_regs *regs, const char *msg) 443{ 444 /* 445 * This is mostly taken from kernel/panic.c, but tries to do 446 * relatively minimal work. Don't use delay functions (TB may --- 573 unchanged lines hidden --- | 459 return recovered; 460} 461 462void pnv_platform_error_reboot(struct pt_regs *regs, const char *msg) 463{ 464 /* 465 * This is mostly taken from kernel/panic.c, but tries to do 466 * relatively minimal work. Don't use delay functions (TB may --- 573 unchanged lines hidden --- |