Linux-MIPS Archive on lore.kernel.org
 help / Atom feed
* [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues
@ 2018-09-11 21:49 Dengcheng Zhu
  2018-09-11 21:49 ` [PATCH v5 1/5] MIPS: kexec: Mark CPU offline before disabling local IRQ Dengcheng Zhu
                   ` (5 more replies)
  0 siblings, 6 replies; 8+ messages in thread
From: Dengcheng Zhu @ 2018-09-11 21:49 UTC (permalink / raw)
  To: pburton, ralf; +Cc: linux-mips, rachel.mozes, Dengcheng Zhu

Hi Paul,

This is a rewrite of the series. Basically patches 1~3 address what we
dissussed so far. Now it allows both methods - shutting off the nonboot
CPUs and jumping to relocated_kexec_smp_wait on nonboot CPUs.

Caches are flushed before signaling reboot. CPUs are marked offline to
prevent getting IPIs. Note that this is done prior to disabling local IRQ.

Patch #4 is unchnaged. Patch #5 is the previous #6 -- I'm still putting
it in here with reasons mentioned in our discussion and in the patch
description.


Thanks,

Dengcheng Zhu (5):
  MIPS: kexec: Mark CPU offline before disabling local IRQ
  MIPS: kexec: Make a framework for both jumping and halting on nonboot
    CPUs
  MIPS: kexec: CPS systems to halt nonboot CPUs
  MIPS: kexec: Relax memory restriction
  MIPS: kexec: Use prepare method from Generic for UHI platforms

 arch/mips/Kconfig                     |   4 +
 arch/mips/cavium-octeon/smp.c         |   7 ++
 arch/mips/generic/Makefile            |   1 -
 arch/mips/generic/kexec.c             |  44 ---------
 arch/mips/include/asm/kexec.h         |  11 ++-
 arch/mips/include/asm/smp-ops.h       |   3 +
 arch/mips/include/asm/smp.h           |  16 ++++
 arch/mips/kernel/crash.c              |   7 +-
 arch/mips/kernel/machine_kexec.c      | 131 ++++++++++++++++++++++++--
 arch/mips/kernel/smp-bmips.c          |   7 ++
 arch/mips/kernel/smp-cps.c            |  80 +++++++++++-----
 arch/mips/loongson64/loongson-3/smp.c |   4 +
 12 files changed, 232 insertions(+), 83 deletions(-)
 delete mode 100644 arch/mips/generic/kexec.c

-- 
2.17.1

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH v5 1/5] MIPS: kexec: Mark CPU offline before disabling local IRQ
  2018-09-11 21:49 [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Dengcheng Zhu
@ 2018-09-11 21:49 ` Dengcheng Zhu
  2018-09-11 21:49 ` [PATCH v5 2/5] MIPS: kexec: Make a framework for both jumping and halting on nonboot CPUs Dengcheng Zhu
                   ` (4 subsequent siblings)
  5 siblings, 0 replies; 8+ messages in thread
From: Dengcheng Zhu @ 2018-09-11 21:49 UTC (permalink / raw)
  To: pburton, ralf; +Cc: linux-mips, rachel.mozes, Dengcheng Zhu

After changing CPU online status, it will not be sent any IPIs such as in
__flush_cache_all() on software coherency systems. Do this before disabling
local IRQ.

Signed-off-by: Dengcheng Zhu <dzhu@wavecomp.com>
---
 arch/mips/kernel/crash.c         | 3 +++
 arch/mips/kernel/machine_kexec.c | 3 +++
 2 files changed, 6 insertions(+)

diff --git a/arch/mips/kernel/crash.c b/arch/mips/kernel/crash.c
index d455363d51c3..4c07a43a3242 100644
--- a/arch/mips/kernel/crash.c
+++ b/arch/mips/kernel/crash.c
@@ -36,6 +36,9 @@ static void crash_shutdown_secondary(void *passed_regs)
 	if (!cpu_online(cpu))
 		return;
 
+	/* We won't be sent IPIs any more. */
+	set_cpu_online(cpu, false);
+
 	local_irq_disable();
 	if (!cpumask_test_cpu(cpu, &cpus_in_crash))
 		crash_save_cpu(regs, cpu);
diff --git a/arch/mips/kernel/machine_kexec.c b/arch/mips/kernel/machine_kexec.c
index 8b574bcd39ba..4b3726e4fe3a 100644
--- a/arch/mips/kernel/machine_kexec.c
+++ b/arch/mips/kernel/machine_kexec.c
@@ -118,6 +118,9 @@ machine_kexec(struct kimage *image)
 			*ptr = (unsigned long) phys_to_virt(*ptr);
 	}
 
+	/* Mark offline BEFORE disabling local irq. */
+	set_cpu_online(smp_processor_id(), false);
+
 	/*
 	 * we do not want to be bothered.
 	 */
-- 
2.17.1

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH v5 2/5] MIPS: kexec: Make a framework for both jumping and halting on nonboot CPUs
  2018-09-11 21:49 [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Dengcheng Zhu
  2018-09-11 21:49 ` [PATCH v5 1/5] MIPS: kexec: Mark CPU offline before disabling local IRQ Dengcheng Zhu
@ 2018-09-11 21:49 ` Dengcheng Zhu
  2018-12-27 20:02   ` Aurelien Jarno
  2018-09-11 21:49 ` [PATCH v5 3/5] MIPS: kexec: CPS systems to halt " Dengcheng Zhu
                   ` (3 subsequent siblings)
  5 siblings, 1 reply; 8+ messages in thread
From: Dengcheng Zhu @ 2018-09-11 21:49 UTC (permalink / raw)
  To: pburton, ralf; +Cc: linux-mips, rachel.mozes, Dengcheng Zhu

The existing implementation lets machine_kexec() CPU jump to reboot code
buffer, whereas other CPUs to relocated_kexec_smp_wait. The natural way to
bring up an SMP new kernel would be to let CPU0 do it while others being
halted. For those failing to do so, fall back to the jumping method.

Signed-off-by: Dengcheng Zhu <dzhu@wavecomp.com>
---
 arch/mips/cavium-octeon/smp.c         |  7 +++
 arch/mips/include/asm/kexec.h         |  5 +-
 arch/mips/include/asm/smp-ops.h       |  3 +
 arch/mips/include/asm/smp.h           | 16 +++++
 arch/mips/kernel/crash.c              |  4 +-
 arch/mips/kernel/machine_kexec.c      | 88 ++++++++++++++++++++++++---
 arch/mips/kernel/smp-bmips.c          |  7 +++
 arch/mips/loongson64/loongson-3/smp.c |  4 ++
 8 files changed, 124 insertions(+), 10 deletions(-)

diff --git a/arch/mips/cavium-octeon/smp.c b/arch/mips/cavium-octeon/smp.c
index 75e7c8625659..39f2a2ec1286 100644
--- a/arch/mips/cavium-octeon/smp.c
+++ b/arch/mips/cavium-octeon/smp.c
@@ -15,6 +15,7 @@
 #include <linux/sched/task_stack.h>
 #include <linux/init.h>
 #include <linux/export.h>
+#include <linux/kexec.h>
 
 #include <asm/mmu_context.h>
 #include <asm/time.h>
@@ -424,6 +425,9 @@ const struct plat_smp_ops octeon_smp_ops = {
 	.cpu_disable		= octeon_cpu_disable,
 	.cpu_die		= octeon_cpu_die,
 #endif
+#ifdef CONFIG_KEXEC
+	.kexec_nonboot_cpu	= kexec_nonboot_cpu_jump,
+#endif
 };
 
 static irqreturn_t octeon_78xx_reched_interrupt(int irq, void *dev_id)
@@ -501,6 +505,9 @@ static const struct plat_smp_ops octeon_78xx_smp_ops = {
 	.cpu_disable		= octeon_cpu_disable,
 	.cpu_die		= octeon_cpu_die,
 #endif
+#ifdef CONFIG_KEXEC
+	.kexec_nonboot_cpu	= kexec_nonboot_cpu_jump,
+#endif
 };
 
 void __init octeon_setup_smp(void)
diff --git a/arch/mips/include/asm/kexec.h b/arch/mips/include/asm/kexec.h
index 493a3cc7c39a..5eeb648c4e3a 100644
--- a/arch/mips/include/asm/kexec.h
+++ b/arch/mips/include/asm/kexec.h
@@ -39,11 +39,12 @@ extern unsigned long kexec_args[4];
 extern int (*_machine_kexec_prepare)(struct kimage *);
 extern void (*_machine_kexec_shutdown)(void);
 extern void (*_machine_crash_shutdown)(struct pt_regs *regs);
-extern void default_machine_crash_shutdown(struct pt_regs *regs);
+void default_machine_crash_shutdown(struct pt_regs *regs);
+void kexec_nonboot_cpu_jump(void);
+void kexec_reboot(void);
 #ifdef CONFIG_SMP
 extern const unsigned char kexec_smp_wait[];
 extern unsigned long secondary_kexec_args[4];
-extern void (*relocated_kexec_smp_wait) (void *);
 extern atomic_t kexec_ready_to_reboot;
 extern void (*_crash_smp_send_stop)(void);
 #endif
diff --git a/arch/mips/include/asm/smp-ops.h b/arch/mips/include/asm/smp-ops.h
index 53b2cb8e5966..b7123f9c0785 100644
--- a/arch/mips/include/asm/smp-ops.h
+++ b/arch/mips/include/asm/smp-ops.h
@@ -33,6 +33,9 @@ struct plat_smp_ops {
 	int (*cpu_disable)(void);
 	void (*cpu_die)(unsigned int cpu);
 #endif
+#ifdef CONFIG_KEXEC
+	void (*kexec_nonboot_cpu)(void);
+#endif
 };
 
 extern void register_smp_ops(const struct plat_smp_ops *ops);
diff --git a/arch/mips/include/asm/smp.h b/arch/mips/include/asm/smp.h
index 056a6bf13491..7990c1c70471 100644
--- a/arch/mips/include/asm/smp.h
+++ b/arch/mips/include/asm/smp.h
@@ -91,6 +91,22 @@ static inline void __cpu_die(unsigned int cpu)
 extern void play_dead(void);
 #endif
 
+#ifdef CONFIG_KEXEC
+static inline void kexec_nonboot_cpu(void)
+{
+	extern const struct plat_smp_ops *mp_ops;	/* private */
+
+	return mp_ops->kexec_nonboot_cpu();
+}
+
+static inline void *kexec_nonboot_cpu_func(void)
+{
+	extern const struct plat_smp_ops *mp_ops;	/* private */
+
+	return mp_ops->kexec_nonboot_cpu;
+}
+#endif
+
 /*
  * This function will set up the necessary IPIs for Linux to communicate
  * with the CPUs in mask.
diff --git a/arch/mips/kernel/crash.c b/arch/mips/kernel/crash.c
index 4c07a43a3242..2c7288041a99 100644
--- a/arch/mips/kernel/crash.c
+++ b/arch/mips/kernel/crash.c
@@ -46,7 +46,9 @@ static void crash_shutdown_secondary(void *passed_regs)
 
 	while (!atomic_read(&kexec_ready_to_reboot))
 		cpu_relax();
-	relocated_kexec_smp_wait(NULL);
+
+	kexec_reboot();
+
 	/* NOTREACHED */
 }
 
diff --git a/arch/mips/kernel/machine_kexec.c b/arch/mips/kernel/machine_kexec.c
index 4b3726e4fe3a..c63c1f52d1c5 100644
--- a/arch/mips/kernel/machine_kexec.c
+++ b/arch/mips/kernel/machine_kexec.c
@@ -19,15 +19,19 @@ extern const size_t relocate_new_kernel_size;
 extern unsigned long kexec_start_address;
 extern unsigned long kexec_indirection_page;
 
-int (*_machine_kexec_prepare)(struct kimage *) = NULL;
-void (*_machine_kexec_shutdown)(void) = NULL;
-void (*_machine_crash_shutdown)(struct pt_regs *regs) = NULL;
+static unsigned long reboot_code_buffer;
+
 #ifdef CONFIG_SMP
-void (*relocated_kexec_smp_wait) (void *);
+static void (*relocated_kexec_smp_wait)(void *);
+
 atomic_t kexec_ready_to_reboot = ATOMIC_INIT(0);
 void (*_crash_smp_send_stop)(void) = NULL;
 #endif
 
+int (*_machine_kexec_prepare)(struct kimage *) = NULL;
+void (*_machine_kexec_shutdown)(void) = NULL;
+void (*_machine_crash_shutdown)(struct pt_regs *regs) = NULL;
+
 static void kexec_image_info(const struct kimage *kimage)
 {
 	unsigned long i;
@@ -51,10 +55,16 @@ static void kexec_image_info(const struct kimage *kimage)
 int
 machine_kexec_prepare(struct kimage *kimage)
 {
+#ifdef CONFIG_SMP
+	if (!kexec_nonboot_cpu_func())
+		return -EINVAL;
+#endif
+
 	kexec_image_info(kimage);
 
 	if (_machine_kexec_prepare)
 		return _machine_kexec_prepare(kimage);
+
 	return 0;
 }
 
@@ -63,11 +73,41 @@ machine_kexec_cleanup(struct kimage *kimage)
 {
 }
 
+#ifdef CONFIG_SMP
+static void kexec_shutdown_secondary(void *param)
+{
+	int cpu = smp_processor_id();
+
+	if (!cpu_online(cpu))
+		return;
+
+	/* We won't be sent IPIs any more. */
+	set_cpu_online(cpu, false);
+
+	local_irq_disable();
+	while (!atomic_read(&kexec_ready_to_reboot))
+		cpu_relax();
+
+	kexec_reboot();
+
+	/* NOTREACHED */
+}
+#endif
+
 void
 machine_shutdown(void)
 {
 	if (_machine_kexec_shutdown)
 		_machine_kexec_shutdown();
+
+#ifdef CONFIG_SMP
+	smp_call_function(kexec_shutdown_secondary, NULL, 0);
+
+	while (num_online_cpus() > 1) {
+		cpu_relax();
+		mdelay(1);
+	}
+#endif
 }
 
 void
@@ -79,12 +119,45 @@ machine_crash_shutdown(struct pt_regs *regs)
 		default_machine_crash_shutdown(regs);
 }
 
-typedef void (*noretfun_t)(void) __noreturn;
+void kexec_nonboot_cpu_jump(void)
+{
+	local_flush_icache_range((unsigned long)relocated_kexec_smp_wait,
+				 reboot_code_buffer + relocate_new_kernel_size);
+
+	relocated_kexec_smp_wait(NULL);
+}
+
+void kexec_reboot(void)
+{
+	void (*do_kexec)(void) __noreturn;
+
+#ifdef CONFIG_SMP
+	if (smp_processor_id() > 0) {
+		/*
+		 * Instead of cpu_relax() or wait, this is needed for kexec
+		 * smp reboot. Kdump usually doesn't require an smp new
+		 * kernel, but kexec may do.
+		 */
+		kexec_nonboot_cpu();
+
+		/* NOTREACHED */
+	}
+#endif
+
+	/*
+	 * Make sure we get correct instructions written by the
+	 * machine_kexec() CPU.
+	 */
+	local_flush_icache_range(reboot_code_buffer,
+				 reboot_code_buffer + relocate_new_kernel_size);
+
+	do_kexec = (void *)reboot_code_buffer;
+	do_kexec();
+}
 
 void
 machine_kexec(struct kimage *image)
 {
-	unsigned long reboot_code_buffer;
 	unsigned long entry;
 	unsigned long *ptr;
 
@@ -128,6 +201,7 @@ machine_kexec(struct kimage *image)
 
 	printk("Will call new kernel at %08lx\n", image->start);
 	printk("Bye ...\n");
+	/* Make reboot code buffer available to the boot CPU. */
 	__flush_cache_all();
 #ifdef CONFIG_SMP
 	/* All secondary cpus now may jump to kexec_wait cycle */
@@ -136,5 +210,5 @@ machine_kexec(struct kimage *image)
 	smp_wmb();
 	atomic_set(&kexec_ready_to_reboot, 1);
 #endif
-	((noretfun_t) reboot_code_buffer)();
+	kexec_reboot();
 }
diff --git a/arch/mips/kernel/smp-bmips.c b/arch/mips/kernel/smp-bmips.c
index 159e83add4bb..76fae9b79f13 100644
--- a/arch/mips/kernel/smp-bmips.c
+++ b/arch/mips/kernel/smp-bmips.c
@@ -25,6 +25,7 @@
 #include <linux/linkage.h>
 #include <linux/bug.h>
 #include <linux/kernel.h>
+#include <linux/kexec.h>
 
 #include <asm/time.h>
 #include <asm/pgtable.h>
@@ -423,6 +424,9 @@ const struct plat_smp_ops bmips43xx_smp_ops = {
 	.cpu_disable		= bmips_cpu_disable,
 	.cpu_die		= bmips_cpu_die,
 #endif
+#ifdef CONFIG_KEXEC
+	.kexec_nonboot_cpu	= kexec_nonboot_cpu_jump,
+#endif
 };
 
 const struct plat_smp_ops bmips5000_smp_ops = {
@@ -437,6 +441,9 @@ const struct plat_smp_ops bmips5000_smp_ops = {
 	.cpu_disable		= bmips_cpu_disable,
 	.cpu_die		= bmips_cpu_die,
 #endif
+#ifdef CONFIG_KEXEC
+	.kexec_nonboot_cpu	= kexec_nonboot_cpu_jump,
+#endif
 };
 
 #endif /* CONFIG_SMP */
diff --git a/arch/mips/loongson64/loongson-3/smp.c b/arch/mips/loongson64/loongson-3/smp.c
index fea95d003269..3da1a7890ab9 100644
--- a/arch/mips/loongson64/loongson-3/smp.c
+++ b/arch/mips/loongson64/loongson-3/smp.c
@@ -21,6 +21,7 @@
 #include <linux/sched/task_stack.h>
 #include <linux/smp.h>
 #include <linux/cpufreq.h>
+#include <linux/kexec.h>
 #include <asm/processor.h>
 #include <asm/time.h>
 #include <asm/clock.h>
@@ -749,4 +750,7 @@ const struct plat_smp_ops loongson3_smp_ops = {
 	.cpu_disable = loongson3_cpu_disable,
 	.cpu_die = loongson3_cpu_die,
 #endif
+#ifdef CONFIG_KEXEC
+	.kexec_nonboot_cpu = kexec_nonboot_cpu_jump,
+#endif
 };
-- 
2.17.1

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH v5 3/5] MIPS: kexec: CPS systems to halt nonboot CPUs
  2018-09-11 21:49 [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Dengcheng Zhu
  2018-09-11 21:49 ` [PATCH v5 1/5] MIPS: kexec: Mark CPU offline before disabling local IRQ Dengcheng Zhu
  2018-09-11 21:49 ` [PATCH v5 2/5] MIPS: kexec: Make a framework for both jumping and halting on nonboot CPUs Dengcheng Zhu
@ 2018-09-11 21:49 ` " Dengcheng Zhu
  2018-09-11 21:49 ` [PATCH v5 4/5] MIPS: kexec: Relax memory restriction Dengcheng Zhu
                   ` (2 subsequent siblings)
  5 siblings, 0 replies; 8+ messages in thread
From: Dengcheng Zhu @ 2018-09-11 21:49 UTC (permalink / raw)
  To: pburton, ralf; +Cc: linux-mips, rachel.mozes, Dengcheng Zhu

Share code between play_dead() and cps_kexec_nonboot_cpu(). Register the
latter to mp_ops for kexec.

Signed-off-by: Dengcheng Zhu <dzhu@wavecomp.com>
---
 arch/mips/kernel/smp-cps.c | 80 ++++++++++++++++++++++++++------------
 1 file changed, 55 insertions(+), 25 deletions(-)

diff --git a/arch/mips/kernel/smp-cps.c b/arch/mips/kernel/smp-cps.c
index 03f1026ad148..faccfa4b280b 100644
--- a/arch/mips/kernel/smp-cps.c
+++ b/arch/mips/kernel/smp-cps.c
@@ -398,6 +398,55 @@ static void cps_smp_finish(void)
 	local_irq_enable();
 }
 
+#if defined(CONFIG_HOTPLUG_CPU) || defined(CONFIG_KEXEC)
+
+enum cpu_death {
+	CPU_DEATH_HALT,
+	CPU_DEATH_POWER,
+};
+
+static void cps_shutdown_this_cpu(enum cpu_death death)
+{
+	unsigned int cpu, core, vpe_id;
+
+	cpu = smp_processor_id();
+	core = cpu_core(&cpu_data[cpu]);
+
+	if (death == CPU_DEATH_HALT) {
+		vpe_id = cpu_vpe_id(&cpu_data[cpu]);
+
+		pr_debug("Halting core %d VP%d\n", core, vpe_id);
+		if (cpu_has_mipsmt) {
+			/* Halt this TC */
+			write_c0_tchalt(TCHALT_H);
+			instruction_hazard();
+		} else if (cpu_has_vp) {
+			write_cpc_cl_vp_stop(1 << vpe_id);
+
+			/* Ensure that the VP_STOP register is written */
+			wmb();
+		}
+	} else {
+		pr_debug("Gating power to core %d\n", core);
+		/* Power down the core */
+		cps_pm_enter_state(CPS_PM_POWER_GATED);
+	}
+}
+
+#ifdef CONFIG_KEXEC
+
+static void cps_kexec_nonboot_cpu(void)
+{
+	if (cpu_has_mipsmt || cpu_has_vp)
+		cps_shutdown_this_cpu(CPU_DEATH_HALT);
+	else
+		cps_shutdown_this_cpu(CPU_DEATH_POWER);
+}
+
+#endif /* CONFIG_KEXEC */
+
+#endif /* CONFIG_HOTPLUG_CPU || CONFIG_KEXEC */
+
 #ifdef CONFIG_HOTPLUG_CPU
 
 static int cps_cpu_disable(void)
@@ -421,19 +470,15 @@ static int cps_cpu_disable(void)
 }
 
 static unsigned cpu_death_sibling;
-static enum {
-	CPU_DEATH_HALT,
-	CPU_DEATH_POWER,
-} cpu_death;
+static enum cpu_death cpu_death;
 
 void play_dead(void)
 {
-	unsigned int cpu, core, vpe_id;
+	unsigned int cpu;
 
 	local_irq_disable();
 	idle_task_exit();
 	cpu = smp_processor_id();
-	core = cpu_core(&cpu_data[cpu]);
 	cpu_death = CPU_DEATH_POWER;
 
 	pr_debug("CPU%d going offline\n", cpu);
@@ -456,25 +501,7 @@ void play_dead(void)
 	/* This CPU has chosen its way out */
 	(void)cpu_report_death();
 
-	if (cpu_death == CPU_DEATH_HALT) {
-		vpe_id = cpu_vpe_id(&cpu_data[cpu]);
-
-		pr_debug("Halting core %d VP%d\n", core, vpe_id);
-		if (cpu_has_mipsmt) {
-			/* Halt this TC */
-			write_c0_tchalt(TCHALT_H);
-			instruction_hazard();
-		} else if (cpu_has_vp) {
-			write_cpc_cl_vp_stop(1 << vpe_id);
-
-			/* Ensure that the VP_STOP register is written */
-			wmb();
-		}
-	} else {
-		pr_debug("Gating power to core %d\n", core);
-		/* Power down the core */
-		cps_pm_enter_state(CPS_PM_POWER_GATED);
-	}
+	cps_shutdown_this_cpu(cpu_death);
 
 	/* This should never be reached */
 	panic("Failed to offline CPU %u", cpu);
@@ -593,6 +620,9 @@ static const struct plat_smp_ops cps_smp_ops = {
 	.cpu_disable		= cps_cpu_disable,
 	.cpu_die		= cps_cpu_die,
 #endif
+#ifdef CONFIG_KEXEC
+	.kexec_nonboot_cpu	= cps_kexec_nonboot_cpu,
+#endif
 };
 
 bool mips_cps_smp_in_use(void)
-- 
2.17.1

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH v5 4/5] MIPS: kexec: Relax memory restriction
  2018-09-11 21:49 [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Dengcheng Zhu
                   ` (2 preceding siblings ...)
  2018-09-11 21:49 ` [PATCH v5 3/5] MIPS: kexec: CPS systems to halt " Dengcheng Zhu
@ 2018-09-11 21:49 ` Dengcheng Zhu
  2018-09-11 21:49 ` [PATCH v5 5/5] MIPS: kexec: Use prepare method from Generic for UHI platforms Dengcheng Zhu
  2018-09-23  0:23 ` [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Paul Burton
  5 siblings, 0 replies; 8+ messages in thread
From: Dengcheng Zhu @ 2018-09-11 21:49 UTC (permalink / raw)
  To: pburton, ralf; +Cc: linux-mips, rachel.mozes, Dengcheng Zhu

We can rely on the system kernel and the dump capture kernel themselves in
memory usage.

Being restrictive with 512MB limit may cause kexec tool failure on some
platforms.

Tested-by: Rachel Mozes <rachel.mozes@intel.com>
Reported-by: Rachel Mozes <rachel.mozes@intel.com>
Signed-off-by: Dengcheng Zhu <dzhu@wavecomp.com>
---
 arch/mips/include/asm/kexec.h | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/arch/mips/include/asm/kexec.h b/arch/mips/include/asm/kexec.h
index 5eeb648c4e3a..40795ca89961 100644
--- a/arch/mips/include/asm/kexec.h
+++ b/arch/mips/include/asm/kexec.h
@@ -12,11 +12,11 @@
 #include <asm/stacktrace.h>
 
 /* Maximum physical address we can use pages from */
-#define KEXEC_SOURCE_MEMORY_LIMIT (0x20000000)
+#define KEXEC_SOURCE_MEMORY_LIMIT (-1UL)
 /* Maximum address we can reach in physical address mode */
-#define KEXEC_DESTINATION_MEMORY_LIMIT (0x20000000)
+#define KEXEC_DESTINATION_MEMORY_LIMIT (-1UL)
  /* Maximum address we can use for the control code buffer */
-#define KEXEC_CONTROL_MEMORY_LIMIT (0x20000000)
+#define KEXEC_CONTROL_MEMORY_LIMIT (-1UL)
 /* Reserve 3*4096 bytes for board-specific info */
 #define KEXEC_CONTROL_PAGE_SIZE (4096 + 3*4096)
 
-- 
2.17.1

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH v5 5/5] MIPS: kexec: Use prepare method from Generic for UHI platforms
  2018-09-11 21:49 [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Dengcheng Zhu
                   ` (3 preceding siblings ...)
  2018-09-11 21:49 ` [PATCH v5 4/5] MIPS: kexec: Relax memory restriction Dengcheng Zhu
@ 2018-09-11 21:49 ` Dengcheng Zhu
  2018-09-23  0:23 ` [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Paul Burton
  5 siblings, 0 replies; 8+ messages in thread
From: Dengcheng Zhu @ 2018-09-11 21:49 UTC (permalink / raw)
  To: pburton, ralf; +Cc: linux-mips, rachel.mozes, Dengcheng Zhu

Out-of-tree platforms may not be based on Generic as shown in customer
communication. Share the prepare method with all using UHI boot protocol,
and put into machine_kexec.c.

The benefit is that, when having kexec_args related problems, developers
will naturally look into machine_kexec.c, where "CONFIG_UHI_BOOT" will be
found, prompting them to add "select UHI_BOOT" to the platform Kconfig. It
would otherwise require a lot debugging or online searching to be aware
that the solution is in Generic code.

Tested-by: Rachel Mozes <rachel.mozes@intel.com>
Reported-by: Rachel Mozes <rachel.mozes@intel.com>
Signed-off-by: Dengcheng Zhu <dzhu@wavecomp.com>
---
 arch/mips/Kconfig                |  4 +++
 arch/mips/generic/Makefile       |  1 -
 arch/mips/generic/kexec.c        | 44 --------------------------------
 arch/mips/kernel/machine_kexec.c | 42 +++++++++++++++++++++++++++++-
 4 files changed, 45 insertions(+), 46 deletions(-)
 delete mode 100644 arch/mips/generic/kexec.c

diff --git a/arch/mips/Kconfig b/arch/mips/Kconfig
index 35511999156a..71afb3593cb6 100644
--- a/arch/mips/Kconfig
+++ b/arch/mips/Kconfig
@@ -132,6 +132,7 @@ config MIPS_GENERIC
 	select USB_UHCI_BIG_ENDIAN_DESC if CPU_BIG_ENDIAN
 	select USB_UHCI_BIG_ENDIAN_MMIO if CPU_BIG_ENDIAN
 	select USE_OF
+	select UHI_BOOT
 	help
 	  Select this to build a kernel which aims to support multiple boards,
 	  generally using a flattened device tree passed from the bootloader
@@ -2898,6 +2899,9 @@ config USE_OF
 	select OF_EARLY_FLATTREE
 	select IRQ_DOMAIN
 
+config UHI_BOOT
+	bool
+
 config BUILTIN_DTB
 	bool
 
diff --git a/arch/mips/generic/Makefile b/arch/mips/generic/Makefile
index d03a36f869a4..181aa1335419 100644
--- a/arch/mips/generic/Makefile
+++ b/arch/mips/generic/Makefile
@@ -15,5 +15,4 @@ obj-y += proc.o
 obj-$(CONFIG_YAMON_DT_SHIM)		+= yamon-dt.o
 obj-$(CONFIG_LEGACY_BOARD_SEAD3)	+= board-sead3.o
 obj-$(CONFIG_LEGACY_BOARD_OCELOT)	+= board-ocelot.o
-obj-$(CONFIG_KEXEC)			+= kexec.o
 obj-$(CONFIG_VIRT_BOARD_RANCHU)		+= board-ranchu.o
diff --git a/arch/mips/generic/kexec.c b/arch/mips/generic/kexec.c
deleted file mode 100644
index 1ca409f58929..000000000000
--- a/arch/mips/generic/kexec.c
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright (C) 2016 Imagination Technologies
- * Author: Marcin Nowakowski <marcin.nowakowski@mips.com>
- *
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation; either version 2 of the License, or (at your
- * option) any later version.
- */
-
-#include <linux/kexec.h>
-#include <linux/libfdt.h>
-#include <linux/uaccess.h>
-
-static int generic_kexec_prepare(struct kimage *image)
-{
-	int i;
-
-	for (i = 0; i < image->nr_segments; i++) {
-		struct fdt_header fdt;
-
-		if (image->segment[i].memsz <= sizeof(fdt))
-			continue;
-
-		if (copy_from_user(&fdt, image->segment[i].buf, sizeof(fdt)))
-			continue;
-
-		if (fdt_check_header(&fdt))
-			continue;
-
-		kexec_args[0] = -2;
-		kexec_args[1] = (unsigned long)
-			phys_to_virt((unsigned long)image->segment[i].mem);
-		break;
-	}
-	return 0;
-}
-
-static int __init register_generic_kexec(void)
-{
-	_machine_kexec_prepare = generic_kexec_prepare;
-	return 0;
-}
-arch_initcall(register_generic_kexec);
diff --git a/arch/mips/kernel/machine_kexec.c b/arch/mips/kernel/machine_kexec.c
index c63c1f52d1c5..93b8353eece4 100644
--- a/arch/mips/kernel/machine_kexec.c
+++ b/arch/mips/kernel/machine_kexec.c
@@ -9,6 +9,7 @@
 #include <linux/kexec.h>
 #include <linux/mm.h>
 #include <linux/delay.h>
+#include <linux/libfdt.h>
 
 #include <asm/cacheflush.h>
 #include <asm/page.h>
@@ -28,7 +29,6 @@ atomic_t kexec_ready_to_reboot = ATOMIC_INIT(0);
 void (*_crash_smp_send_stop)(void) = NULL;
 #endif
 
-int (*_machine_kexec_prepare)(struct kimage *) = NULL;
 void (*_machine_kexec_shutdown)(void) = NULL;
 void (*_machine_crash_shutdown)(struct pt_regs *regs) = NULL;
 
@@ -52,6 +52,46 @@ static void kexec_image_info(const struct kimage *kimage)
 	}
 }
 
+#ifdef CONFIG_UHI_BOOT
+
+static int uhi_machine_kexec_prepare(struct kimage *kimage)
+{
+	int i;
+
+	/*
+	 * In case DTB file is not passed to the new kernel, a flat device
+	 * tree will be created by kexec tool. It holds modified command
+	 * line for the new kernel.
+	 */
+	for (i = 0; i < kimage->nr_segments; i++) {
+		struct fdt_header fdt;
+
+		if (kimage->segment[i].memsz <= sizeof(fdt))
+			continue;
+
+		if (copy_from_user(&fdt, kimage->segment[i].buf, sizeof(fdt)))
+			continue;
+
+		if (fdt_check_header(&fdt))
+			continue;
+
+		kexec_args[0] = -2;
+		kexec_args[1] = (unsigned long)
+			phys_to_virt((unsigned long)kimage->segment[i].mem);
+		break;
+	}
+
+	return 0;
+}
+
+int (*_machine_kexec_prepare)(struct kimage *) = uhi_machine_kexec_prepare;
+
+#else
+
+int (*_machine_kexec_prepare)(struct kimage *) = NULL;
+
+#endif /* CONFIG_UHI_BOOT */
+
 int
 machine_kexec_prepare(struct kimage *kimage)
 {
-- 
2.17.1

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues
  2018-09-11 21:49 [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Dengcheng Zhu
                   ` (4 preceding siblings ...)
  2018-09-11 21:49 ` [PATCH v5 5/5] MIPS: kexec: Use prepare method from Generic for UHI platforms Dengcheng Zhu
@ 2018-09-23  0:23 ` Paul Burton
  5 siblings, 0 replies; 8+ messages in thread
From: Paul Burton @ 2018-09-23  0:23 UTC (permalink / raw)
  To: Dengcheng Zhu; +Cc: Paul Burton, ralf, linux-mips, rachel.mozes

Hi Dengcheng,

On Tue, Sep 11, 2018 at 02:49:19PM -0700, Dengcheng Zhu wrote:
> This is a rewrite of the series. Basically patches 1~3 address what we
> dissussed so far. Now it allows both methods - shutting off the nonboot
> CPUs and jumping to relocated_kexec_smp_wait on nonboot CPUs.
> 
> Caches are flushed before signaling reboot. CPUs are marked offline to
> prevent getting IPIs. Note that this is done prior to disabling local IRQ.
> 
> Patch #4 is unchnaged. Patch #5 is the previous #6 -- I'm still putting
> it in here with reasons mentioned in our discussion and in the patch
> description.

Thanks for putting in the time & effort to address my concerns :)

I've applied the series to mips-next for 4.20, with a minor tweak to
patch 2 fixing CONFIG_SMP=n builds.

Paul

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH v5 2/5] MIPS: kexec: Make a framework for both jumping and halting on nonboot CPUs
  2018-09-11 21:49 ` [PATCH v5 2/5] MIPS: kexec: Make a framework for both jumping and halting on nonboot CPUs Dengcheng Zhu
@ 2018-12-27 20:02   ` Aurelien Jarno
  0 siblings, 0 replies; 8+ messages in thread
From: Aurelien Jarno @ 2018-12-27 20:02 UTC (permalink / raw)
  To: Dengcheng Zhu; +Cc: pburton, ralf, linux-mips, rachel.mozes

On 2018-09-11 14:49, Dengcheng Zhu wrote:
> The existing implementation lets machine_kexec() CPU jump to reboot code
> buffer, whereas other CPUs to relocated_kexec_smp_wait. The natural way to
> bring up an SMP new kernel would be to let CPU0 do it while others being
> halted. For those failing to do so, fall back to the jumping method.
> 
> Signed-off-by: Dengcheng Zhu <dzhu@wavecomp.com>
> ---
>  arch/mips/cavium-octeon/smp.c         |  7 +++
>  arch/mips/include/asm/kexec.h         |  5 +-
>  arch/mips/include/asm/smp-ops.h       |  3 +
>  arch/mips/include/asm/smp.h           | 16 +++++
>  arch/mips/kernel/crash.c              |  4 +-
>  arch/mips/kernel/machine_kexec.c      | 88 ++++++++++++++++++++++++---
>  arch/mips/kernel/smp-bmips.c          |  7 +++
>  arch/mips/loongson64/loongson-3/smp.c |  4 ++
>  8 files changed, 124 insertions(+), 10 deletions(-)
> 

[ snip ]

> diff --git a/arch/mips/include/asm/kexec.h b/arch/mips/include/asm/kexec.h
> index 493a3cc7c39a..5eeb648c4e3a 100644
> --- a/arch/mips/include/asm/kexec.h
> +++ b/arch/mips/include/asm/kexec.h
> @@ -39,11 +39,12 @@ extern unsigned long kexec_args[4];
>  extern int (*_machine_kexec_prepare)(struct kimage *);
>  extern void (*_machine_kexec_shutdown)(void);
>  extern void (*_machine_crash_shutdown)(struct pt_regs *regs);
> -extern void default_machine_crash_shutdown(struct pt_regs *regs);
> +void default_machine_crash_shutdown(struct pt_regs *regs);
> +void kexec_nonboot_cpu_jump(void);
> +void kexec_reboot(void);
>  #ifdef CONFIG_SMP
>  extern const unsigned char kexec_smp_wait[];
>  extern unsigned long secondary_kexec_args[4];
> -extern void (*relocated_kexec_smp_wait) (void *);
>  extern atomic_t kexec_ready_to_reboot;
>  extern void (*_crash_smp_send_stop)(void);
>  #endif

[ snip ]

> diff --git a/arch/mips/kernel/machine_kexec.c b/arch/mips/kernel/machine_kexec.c
> index 4b3726e4fe3a..c63c1f52d1c5 100644
> --- a/arch/mips/kernel/machine_kexec.c
> +++ b/arch/mips/kernel/machine_kexec.c
> @@ -19,15 +19,19 @@ extern const size_t relocate_new_kernel_size;
>  extern unsigned long kexec_start_address;
>  extern unsigned long kexec_indirection_page;
>  
> -int (*_machine_kexec_prepare)(struct kimage *) = NULL;
> -void (*_machine_kexec_shutdown)(void) = NULL;
> -void (*_machine_crash_shutdown)(struct pt_regs *regs) = NULL;
> +static unsigned long reboot_code_buffer;
> +
>  #ifdef CONFIG_SMP
> -void (*relocated_kexec_smp_wait) (void *);
> +static void (*relocated_kexec_smp_wait)(void *);
> +
>  atomic_t kexec_ready_to_reboot = ATOMIC_INIT(0);
>  void (*_crash_smp_send_stop)(void) = NULL;
>  #endif

The above changes broke kexec support on Octeon, as
relocated_kexec_smp_wait() is still called from octeon_kexec_smp_down():

|   gcc-8 -Wp,-MD,arch/mips/cavium-octeon/.setup.o.d  -nostdinc -isystem /usr/lib/gcc/mips-linux-gnu/8/include -I/<<PKGBUILDDIR>>/arch/mips/include -I./arch/mips/include/generated  -I/<<PKGBUILDDIR>>/include -I./include -I/<<PKGBUILDDIR>>/arch/mips/include/uapi -I./arch/mips/include/generated/uapi -I/<<PKGBUILDDIR>>/include/uapi -I./include/generated/uapi -include /<<PKGBUILDDIR>>/include/linux/kconfig.h -include /<<PKGBUILDDIR>>/include/linux/compiler_types.h  -I/<<PKGBUILDDIR>>/arch/mips/cavium-octeon -Iarch/mips/cavium-octeon -D__KERNEL__ -DVMLINUX_LOAD_ADDRESS=0xffffffff81100000 -DDATAOFFSET=0 -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -fshort-wchar -Werror-implicit-function-declaration -Wno-format-security -std=gnu89 -fno-PIE -DCC_HAVE_ASM_GOTO -mmcount-ra-address -DKBUILD_MCOUNT_RA_ADDRESS -mno-check-zero-division -mabi=64 -G 0 -mno-abicalls -fno-pic -pipe -msoft-float -DGAS_HAS_SET_HARDFLOAT -Wa,-msoft-float -ffreestanding -fno-stack-chec
 k -march=octeon -Wa,--trap -Wa,-mfix-cn63xxp1 -DTOOLCHAIN_SUPPORTS_VIRT -DTOOLCHAIN_SUPPORTS_XPA -DTOOLCHAIN_SUPPORTS_CRC -DTOOLCHAIN_SUPPORTS_DSP  -I/<<PKGBUILDDIR>>/arch/mips/include/asm/mach-cavium-octeon  -I/<<PKGBUILDDIR>>/arch/mips/include/asm/mach-generic -msym32 -DKBUILD_64BIT_SYM32 -fno-asynchronous-unwind-tables -fno-delete-null-pointer-checks -Wno-frame-address -Wno-format-truncation -Wno-format-overflow -Wno-int-in-bool-context -O2 --param=allow-store-data-races=0 -Wframe-larger-than=2048 -fstack-protector-strong -Wno-unused-but-set-variable -Wno-unused-const-variable -fno-var-tracking-assignments -g -pg -Wdeclaration-after-statement -Wvla -Wno-pointer-sign -Wno-stringop-truncation -fno-strict-overflow -fno-merge-all-constants -fmerge-constants -fno-stack-check -fconserve-stack -Werror=implicit-int -Werror=strict-prototypes -Werror=date-time -Werror=incompatible-pointer-types -Werror=designated-init -fmacro-prefix-map=/<<PKGBUILDDIR>>/= -Wno-packed-not-aligned   -fdebug-
 prefix-map=/<<PKGBUILDDIR>>=. -DKBUILD_BASENAME='"setup"' -DKBUILD_MODNAME='"setup"' -c -o arch/mips/cavium-octeon/.tmp_setup.o /<<PKGBUILDDIR>>/arch/mips/cavium-octeon/setup.c
| /<<PKGBUILDDIR>>/arch/mips/cavium-octeon/setup.c: In function 'octeon_kexec_smp_down':
| /<<PKGBUILDDIR>>/arch/mips/cavium-octeon/setup.c:99:2: error: implicit declaration of function 'relocated_kexec_smp_wait'; did you mean 'octeon_kexec_smp_down'? [-Werror=implicit-function-declaration]
|   relocated_kexec_smp_wait(NULL);
|   ^~~~~~~~~~~~~~~~~~~~~~~~
|   octeon_kexec_smp_down
| 
| cc1: some warnings being treated as errors
| make[7]: *** [/<<PKGBUILDDIR>>/scripts/Makefile.build:296: arch/mips/cavium-octeon/setup.o] Error 1
| make[6]: *** [/<<PKGBUILDDIR>>/scripts/Makefile.build:521: arch/mips/cavium-octeon] Error 2

Regards,
Aurelien

-- 
Aurelien Jarno                          GPG: 4096R/1DDD8C9B
aurelien@aurel32.net                 http://www.aurel32.net

^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, back to index

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2018-09-11 21:49 [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Dengcheng Zhu
2018-09-11 21:49 ` [PATCH v5 1/5] MIPS: kexec: Mark CPU offline before disabling local IRQ Dengcheng Zhu
2018-09-11 21:49 ` [PATCH v5 2/5] MIPS: kexec: Make a framework for both jumping and halting on nonboot CPUs Dengcheng Zhu
2018-12-27 20:02   ` Aurelien Jarno
2018-09-11 21:49 ` [PATCH v5 3/5] MIPS: kexec: CPS systems to halt " Dengcheng Zhu
2018-09-11 21:49 ` [PATCH v5 4/5] MIPS: kexec: Relax memory restriction Dengcheng Zhu
2018-09-11 21:49 ` [PATCH v5 5/5] MIPS: kexec: Use prepare method from Generic for UHI platforms Dengcheng Zhu
2018-09-23  0:23 ` [PATCH v5 0/5] MIPS: kexec/kdump: Fix smp reboot and other issues Paul Burton

Linux-MIPS Archive on lore.kernel.org

Archives are clonable:
	git clone --mirror https://lore.kernel.org/linux-mips/0 linux-mips/git/0.git

	# If you have public-inbox 1.1+ installed, you may
	# initialize and index your mirror using the following commands:
	public-inbox-init -V2 linux-mips linux-mips/ https://lore.kernel.org/linux-mips \
		linux-mips@vger.kernel.org linux-mips@archiver.kernel.org
	public-inbox-index linux-mips


Newsgroup available over NNTP:
	nntp://nntp.lore.kernel.org/org.kernel.vger.linux-mips


AGPL code for this site: git clone https://public-inbox.org/ public-inbox