Commit 56d1a0a4 authored by Dai Xin's avatar Dai Xin Committed by guzitao
Browse files

sw64: implement the reset hooks for general platforms

Sunway inclusion
category: feature
bugzilla: https://gitee.com/openeuler/kernel/issues/I5XTK7



--------------------------------

Signed-off-by: default avatarDai Xin <daixin@wxiat.com>
Reviewed-by: default avatarHe Sheng <hesheng@wxiat.com>
Signed-off-by: default avatarGu Zitao <guzitao@wxiat.com>
parent 77ba5038
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -17,7 +17,7 @@ obj-y := entry.o fpu.o traps.o process.o sys_sw64.o irq.o \
	    irq_sw64.o signal.o setup.o ptrace.o time.o \
	    systbls.o dup_print.o tc.o timer.o \
	    insn.o early_init.o topology.o cacheinfo.o \
	    vdso.o vdso/ hmcall.o stacktrace.o idle.o
	    vdso.o vdso/ hmcall.o stacktrace.o idle.o reset.o

obj-$(CONFIG_ACPI) += acpi.o
obj-$(CONFIG_SMP)	+= smp.o
+0 −65
Original line number Diff line number Diff line
@@ -6,7 +6,6 @@
#include <linux/sched/debug.h>
#include <linux/ptrace.h>
#include <linux/elfcore.h>
#include <linux/reboot.h>
#include <linux/slab.h>
#include <linux/random.h>

@@ -15,70 +14,6 @@

#include "proto.h"

/*
 * Power off function, if any
 */
void (*pm_power_off)(void) = machine_power_off;
EXPORT_SYMBOL(pm_power_off);

struct halt_info {
	int mode;
	char *restart_cmd;
};

static void common_shutdown_1(void *generic_ptr)
{
	struct halt_info *how = (struct halt_info *)generic_ptr;
	int cpuid __maybe_unused = smp_processor_id();

	/* No point in taking interrupts anymore. */
	local_irq_disable();

#ifdef CONFIG_SMP
	/* Secondaries halt here. */
	if (cpuid != 0) {
		set_cpu_present(cpuid, false);
		set_cpu_possible(cpuid, false);

		if (is_in_guest()) {
			hcall(HCALL_SET_CLOCKEVENT, 0, 0, 0);
			while (1)
				asm("nop");
		} else
			asm("halt");
	}
#endif
	if (sw64_platform->kill_arch)
		sw64_platform->kill_arch(how->mode);
}

static void common_shutdown(int mode, char *restart_cmd)
{
	struct halt_info args;

	args.mode = mode;
	args.restart_cmd = restart_cmd;
	on_each_cpu(common_shutdown_1, &args, 0);
}

void machine_restart(char *restart_cmd)
{
	common_shutdown(LINUX_REBOOT_CMD_RESTART, restart_cmd);
}


void machine_halt(void)
{
	common_shutdown(LINUX_REBOOT_CMD_HALT, NULL);
}


void machine_power_off(void)
{
	common_shutdown(LINUX_REBOOT_CMD_POWER_OFF, NULL);
}


/*
 * Re-start a thread when doing execve()
 */
+98 −0
Original line number Diff line number Diff line
// SPDX-License-Identifier: GPL-2.0
/*
 * Copyright (C) 2020-2022 Sunway Technology Corporation Limited
 */
#include <linux/acpi.h>
#include <linux/console.h>
#include <linux/delay.h>
#include <linux/efi.h>
#include <linux/export.h>
#include <linux/kernel.h>
#include <linux/pci.h>
#include <linux/pm.h>
#include <linux/reboot.h>
#include <linux/types.h>

#include <acpi/reboot.h>
#include <asm/idle.h>

static void default_halt(void)
{
	local_irq_disable();

	pr_notice("\n\n** You can safely turn off the power now **\n\n");

	while (true)
		arch_cpu_idle();
}

static void default_poweroff(void)
{
	/* No point in taking interrupts anymore. */
	local_irq_disable();
#ifdef CONFIG_EFI
	efi.reset_system(EFI_RESET_SHUTDOWN, EFI_SUCCESS, 0, NULL);
#endif
	while (true)
		arch_cpu_idle();
}

static void default_restart(void)
{
	/* No point in taking interrupts anymore. */
	local_irq_disable();

#ifdef CONFIG_EFI
	if (efi_capsule_pending(NULL))
		efi_reboot(REBOOT_WARM, NULL);
	else
		efi_reboot(REBOOT_COLD, NULL);
#endif

	while (true)
		arch_cpu_idle();
}

void (*pm_restart)(void);

void (*pm_power_off)(void);

void (*pm_halt)(void);

void machine_halt(void)
{
#ifdef CONFIG_SMP
	preempt_disable();
	smp_send_stop();
#endif
	pm_halt();
}

void machine_power_off(void)
{
#ifdef CONFIG_SMP
	preempt_disable();
	smp_send_stop();
#endif
	pm_power_off();
}

void machine_restart(char *command)
{
#ifdef CONFIG_SMP
	preempt_disable();
	smp_send_stop();
#endif
	do_kernel_restart(command);
	pm_restart();
}

static int __init sw64_reboot_setup(void)
{
	pm_restart = default_restart;
	pm_power_off = default_poweroff;
	pm_halt = default_halt;

	return 0;
}
arch_initcall(sw64_reboot_setup);