From: Takenori Nagano Subject: [PATCH] Add dump_after_notifier sysctl Patch-mainline: never References: 265764 This patch adds dump_after_notifier sysctl to execute kdump after the notifier call chain. This basically makes it possible to execute KDB before kdump. Signed-off-by: Takenori Nagano Acked-by: Bernhard Walle --- include/linux/kexec.h | 2 ++ include/linux/sysctl.h | 1 + kernel/kexec.c | 29 +++++++++++++++++++++++++++++ kernel/panic.c | 5 ++++- kernel/sysctl_check.c | 1 + 5 files changed, 37 insertions(+), 1 deletion(-) --- a/include/linux/kexec.h +++ b/include/linux/kexec.h @@ -158,6 +158,7 @@ unsigned long paddr_vmcoreinfo_note(void extern struct kimage *kexec_image; extern struct kimage *kexec_crash_image; +extern int dump_after_notifier; #ifndef kexec_flush_icache_page #define kexec_flush_icache_page(page) @@ -212,5 +213,6 @@ struct pt_regs; struct task_struct; static inline void crash_kexec(struct pt_regs *regs) { } static inline int kexec_should_crash(struct task_struct *p) { return 0; } +#define dump_after_notifier 0 #endif /* CONFIG_KEXEC */ #endif /* LINUX_KEXEC_H */ --- a/include/linux/sysctl.h +++ b/include/linux/sysctl.h @@ -162,6 +162,7 @@ enum KERN_MAX_LOCK_DEPTH=74, KERN_NMI_WATCHDOG=75, /* int: enable/disable nmi watchdog */ KERN_PANIC_ON_NMI=76, /* int: whether we will panic on an unrecovered */ + KERN_DUMP_AFTER_NOTIFIER=78, /* int: kdump after panic_notifier (SUSE only) */ KERN_PANIC_ON_IO_NMI=79, /* int: whether we will panic on an io NMI */ }; --- a/kernel/kexec.c +++ b/kernel/kexec.c @@ -31,6 +31,7 @@ #include #include #include +#include #include #include @@ -46,6 +47,7 @@ /* Per cpu memory for storing cpu states in case of system crash. */ note_buf_t* crash_notes; +int dump_after_notifier; /* vmcoreinfo stuff */ static unsigned char vmcoreinfo_data[VMCOREINFO_BYTES]; @@ -1152,6 +1154,30 @@ void crash_save_cpu(struct pt_regs *regs final_note(buf); } +#ifdef CONFIG_SYSCTL +static ctl_table dump_after_notifier_table[] = { + { + .ctl_name = KERN_DUMP_AFTER_NOTIFIER, + .procname = "dump_after_notifier", + .data = &dump_after_notifier, + .maxlen = sizeof(int), + .mode = 0644, + .proc_handler = &proc_dointvec, + }, + { .ctl_name = 0 } +}; + +static ctl_table kexec_sys_table[] = { + { + .ctl_name = CTL_KERN, + .procname = "kernel", + .mode = 0555, + .child = dump_after_notifier_table, + }, + { .ctl_name = 0 } +}; +#endif + static int __init crash_notes_memory_init(void) { /* Allocate memory for saving cpu registers. */ @@ -1161,6 +1187,9 @@ static int __init crash_notes_memory_ini " states failed\n"); return -ENOMEM; } +#ifdef CONFIG_SYSCTL + register_sysctl_table(kexec_sys_table); +#endif return 0; } module_init(crash_notes_memory_init) --- a/kernel/panic.c +++ b/kernel/panic.c @@ -87,7 +87,8 @@ NORET_TYPE void panic(const char * fmt, * everything else. * Do we want to call this before we try to display a message? */ - crash_kexec(NULL); + if (!dump_after_notifier) + crash_kexec(NULL); /* * Note smp_send_stop is the usual smp shutdown function, which @@ -98,6 +99,8 @@ NORET_TYPE void panic(const char * fmt, atomic_notifier_call_chain(&panic_notifier_list, 0, buf); + crash_kexec(NULL); + bust_spinlocks(0); if (!panic_blink) --- a/kernel/sysctl_check.c +++ b/kernel/sysctl_check.c @@ -106,6 +106,7 @@ static const struct trans_ctl_table tran { KERN_PANIC_ON_NMI, "panic_on_unrecovered_nmi" }, { KERN_PANIC_ON_IO_NMI, "panic_on_io_nmi" }, { KERN_SETUID_DUMPABLE, "suid_dumpable" }, + { KERN_DUMP_AFTER_NOTIFIER, "dump_after_notifier" }, {} };