// SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
/*
 * skiboot C entry point
 *
 * Copyright 2013-2019 IBM Corp.
 */

#include <skiboot.h>
#include <slw.h>
#include <psi.h>
#include <chiptod.h>
#include <nx.h>
#include <cpu.h>
#include <processor.h>
#include <xscom.h>
#include <opal.h>
#include <opal-msg.h>
#include <elf.h>
#include <elf-abi.h>
#include <io.h>
#include <cec.h>
#include <device.h>
#include <pci.h>
#include <lpc.h>
#include <i2c.h>
#include <chip.h>
#include <interrupts.h>
#include <mem_region.h>
#include <trace.h>
#include <console.h>
#include <fsi-master.h>
#include <centaur.h>
#include <ocmb.h>
#include <libfdt/libfdt.h>
#include <timer.h>
#include <ipmi.h>
#include <sensor.h>
#include <xive.h>
#include <nvram.h>
#include <vas.h>
#include <libstb/secureboot.h>
#include <libstb/trustedboot.h>
#include <phys-map.h>
#include <imc.h>
#include <dts.h>
#include <dio-p9.h>
#include <sbe-p9.h>
#include <debug_descriptor.h>
#include <occ.h>
#include <opal-dump.h>
#include <xscom-p9-regs.h>
#include <xscom-p10-regs.h>

enum proc_gen proc_gen;
unsigned int pcie_max_link_speed;
bool pci_tracing;
bool verbose_eeh;
extern const char version[];

static uint64_t kernel_entry;
static size_t kernel_size;
static bool kernel_32bit;

/* We backup the previous vectors here before copying our own */
static uint8_t old_vectors[EXCEPTION_VECTORS_END];

#ifdef DEBUG
#define DEBUG_STR "-debug"
#else
#define DEBUG_STR ""
#endif

#ifdef SKIBOOT_GCOV
void skiboot_gcov_done(void);
#endif

struct debug_descriptor debug_descriptor = {
	.eye_catcher	= "OPALdbug",
	.version	= CPU_TO_BE32(DEBUG_DESC_VERSION),
	.state_flags	= 0,
	.memcons_phys	= 0, /* cpu_to_be64(&memcons) can't init constant */
	.trace_mask	= 0, /* All traces disabled by default */
	/* console log level:
	 *   high 4 bits in memory, low 4 bits driver (e.g. uart). */
#ifdef DEBUG
	.console_log_levels = (PR_TRACE << 4) | PR_DEBUG,
#else
	.console_log_levels = (PR_DEBUG << 4) | PR_NOTICE,
#endif
};

static void checksum_romem(void);

static bool try_load_elf64_le(struct elf_hdr *header)
{
	struct elf64le_hdr *kh = (struct elf64le_hdr *)header;
	uint64_t load_base = (uint64_t)kh;
	struct elf64le_phdr *ph;
	unsigned int i;

	printf("INIT: 64-bit LE kernel discovered\n");

	/* Look for a loadable program header that has our entry in it
	 *
	 * Note that we execute the kernel in-place, we don't actually
	 * obey the load informations in the headers. This is expected
	 * to work for the Linux Kernel because it's a fairly dumb ELF
	 * but it will not work for any ELF binary.
	 */
	ph = (struct elf64le_phdr *)(load_base + le64_to_cpu(kh->e_phoff));
	for (i = 0; i < le16_to_cpu(kh->e_phnum); i++, ph++) {
		if (le32_to_cpu(ph->p_type) != ELF_PTYPE_LOAD)
			continue;
		if (le64_to_cpu(ph->p_vaddr) > le64_to_cpu(kh->e_entry) ||
		    (le64_to_cpu(ph->p_vaddr) + le64_to_cpu(ph->p_memsz)) <
		    le64_to_cpu(kh->e_entry))
			continue;

		/* Get our entry */
		kernel_entry = le64_to_cpu(kh->e_entry) -
			le64_to_cpu(ph->p_vaddr) + le64_to_cpu(ph->p_offset);
		break;
	}

	if (!kernel_entry) {
		prerror("INIT: Failed to find kernel entry !\n");
		return false;
	}
	kernel_entry += load_base;
	kernel_32bit = false;

	kernel_size = le64_to_cpu(kh->e_shoff) +
		((uint32_t)le16_to_cpu(kh->e_shentsize) *
		 (uint32_t)le16_to_cpu(kh->e_shnum));

	prlog(PR_DEBUG, "INIT: 64-bit kernel entry at 0x%llx, size 0x%lx\n",
	      kernel_entry, kernel_size);

	return true;
}

static bool try_load_elf64(struct elf_hdr *header)
{
	struct elf64be_hdr *kh = (struct elf64be_hdr *)header;
	struct elf64le_hdr *khle = (struct elf64le_hdr *)header;
	uint64_t load_base = (uint64_t)kh;
	struct elf64be_phdr *ph;
	struct elf64be_shdr *sh;
	unsigned int i;

	/* Check it's a ppc64 LE ELF */
	if (khle->ei_ident == ELF_IDENT		&&
	    khle->ei_data == ELF_DATA_LSB	&&
	    le16_to_cpu(khle->e_machine) == ELF_MACH_PPC64) {
		return try_load_elf64_le(header);
	}

	/* Check it's a ppc64 ELF */
	if (kh->ei_ident != ELF_IDENT		||
	    kh->ei_data != ELF_DATA_MSB		||
	    be16_to_cpu(kh->e_machine) != ELF_MACH_PPC64) {
		prerror("INIT: Kernel doesn't look like an ppc64 ELF\n");
		return false;
	}

	/* Look for a loadable program header that has our entry in it
	 *
	 * Note that we execute the kernel in-place, we don't actually
	 * obey the load informations in the headers. This is expected
	 * to work for the Linux Kernel because it's a fairly dumb ELF
	 * but it will not work for any ELF binary.
	 */
	ph = (struct elf64be_phdr *)(load_base + be64_to_cpu(kh->e_phoff));
	for (i = 0; i < be16_to_cpu(kh->e_phnum); i++, ph++) {
		if (be32_to_cpu(ph->p_type) != ELF_PTYPE_LOAD)
			continue;
		if (be64_to_cpu(ph->p_vaddr) > be64_to_cpu(kh->e_entry) ||
		    (be64_to_cpu(ph->p_vaddr) + be64_to_cpu(ph->p_memsz)) <
		    be64_to_cpu(kh->e_entry))
			continue;

		/* Get our entry */
		kernel_entry = be64_to_cpu(kh->e_entry) -
			be64_to_cpu(ph->p_vaddr) + be64_to_cpu(ph->p_offset);
		break;
	}

	if (!kernel_entry) {
		prerror("INIT: Failed to find kernel entry !\n");
		return false;
	}

	/* For the normal big-endian ELF ABI, the kernel entry points
	 * to a function descriptor in the data section. Linux instead
	 * has it point directly to code. Test whether it is pointing
	 * into an executable section or not to figure this out. Default
	 * to assuming it obeys the ABI.
	 */
	sh = (struct elf64be_shdr *)(load_base + be64_to_cpu(kh->e_shoff));
	for (i = 0; i < be16_to_cpu(kh->e_shnum); i++, sh++) {
		if (be64_to_cpu(sh->sh_addr) <= be64_to_cpu(kh->e_entry) &&
		    (be64_to_cpu(sh->sh_addr) + be64_to_cpu(sh->sh_size)) >
		    be64_to_cpu(kh->e_entry))
			break;
	}

	if (i == be16_to_cpu(kh->e_shnum) ||
			!(be64_to_cpu(sh->sh_flags) & ELF_SFLAGS_X)) {
		kernel_entry = *(uint64_t *)(kernel_entry + load_base);
		kernel_entry = kernel_entry -
			be64_to_cpu(ph->p_vaddr) + be64_to_cpu(ph->p_offset);
	}

	kernel_entry += load_base;
	kernel_32bit = false;

	kernel_size = be64_to_cpu(kh->e_shoff) +
		((uint32_t)be16_to_cpu(kh->e_shentsize) *
		 (uint32_t)be16_to_cpu(kh->e_shnum));

	printf("INIT: 64-bit kernel entry at 0x%llx, size 0x%lx\n",
	       kernel_entry, kernel_size);

	return true;
}

static bool try_load_elf32_le(struct elf_hdr *header)
{
	struct elf32le_hdr *kh = (struct elf32le_hdr *)header;
	uint64_t load_base = (uint64_t)kh;
	struct elf32le_phdr *ph;
	unsigned int i;

	printf("INIT: 32-bit LE kernel discovered\n");

	/* Look for a loadable program header that has our entry in it
	 *
	 * Note that we execute the kernel in-place, we don't actually
	 * obey the load informations in the headers. This is expected
	 * to work for the Linux Kernel because it's a fairly dumb ELF
	 * but it will not work for any ELF binary.
	 */
	ph = (struct elf32le_phdr *)(load_base + le32_to_cpu(kh->e_phoff));
	for (i = 0; i < le16_to_cpu(kh->e_phnum); i++, ph++) {
		if (le32_to_cpu(ph->p_type) != ELF_PTYPE_LOAD)
			continue;
		if (le32_to_cpu(ph->p_vaddr) > le32_to_cpu(kh->e_entry) ||
		    (le32_to_cpu(ph->p_vaddr) + le32_to_cpu(ph->p_memsz)) <
		    le32_to_cpu(kh->e_entry))
			continue;

		/* Get our entry */
		kernel_entry = le32_to_cpu(kh->e_entry) -
			le32_to_cpu(ph->p_vaddr) + le32_to_cpu(ph->p_offset);
		break;
	}

	if (!kernel_entry) {
		prerror("INIT: Failed to find kernel entry !\n");
		return false;
	}

	kernel_entry += load_base;
	kernel_32bit = true;

	printf("INIT: 32-bit kernel entry at 0x%llx\n", kernel_entry);

	return true;
}

static bool try_load_elf32(struct elf_hdr *header)
{
	struct elf32be_hdr *kh = (struct elf32be_hdr *)header;
	struct elf32le_hdr *khle = (struct elf32le_hdr *)header;
	uint64_t load_base = (uint64_t)kh;
	struct elf32be_phdr *ph;
	unsigned int i;

	/* Check it's a ppc32 LE ELF */
	if (khle->ei_ident == ELF_IDENT		&&
	    khle->ei_data == ELF_DATA_LSB	&&
	    le16_to_cpu(khle->e_machine) == ELF_MACH_PPC32) {
		return try_load_elf32_le(header);
	}

	/* Check it's a ppc32 ELF */
	if (kh->ei_ident != ELF_IDENT		||
	    kh->ei_data != ELF_DATA_MSB		||
	    be16_to_cpu(kh->e_machine) != ELF_MACH_PPC32) {
		prerror("INIT: Kernel doesn't look like an ppc32 ELF\n");
		return false;
	}

	/* Look for a loadable program header that has our entry in it
	 *
	 * Note that we execute the kernel in-place, we don't actually
	 * obey the load informations in the headers. This is expected
	 * to work for the Linux Kernel because it's a fairly dumb ELF
	 * but it will not work for any ELF binary.
	 */
	ph = (struct elf32be_phdr *)(load_base + be32_to_cpu(kh->e_phoff));
	for (i = 0; i < be16_to_cpu(kh->e_phnum); i++, ph++) {
		if (be32_to_cpu(ph->p_type) != ELF_PTYPE_LOAD)
			continue;
		if (be32_to_cpu(ph->p_vaddr) > be32_to_cpu(kh->e_entry) ||
		    (be32_to_cpu(ph->p_vaddr) + be32_to_cpu(ph->p_memsz)) <
		    be32_to_cpu(kh->e_entry))
			continue;

		/* Get our entry */
		kernel_entry = be32_to_cpu(kh->e_entry) -
			be32_to_cpu(ph->p_vaddr) + be32_to_cpu(ph->p_offset);
		break;
	}

	if (!kernel_entry) {
		prerror("INIT: Failed to find kernel entry !\n");
		return false;
	}

	kernel_entry += load_base;
	kernel_32bit = true;

	printf("INIT: 32-bit kernel entry at 0x%llx\n", kernel_entry);

	return true;
}

extern char __builtin_kernel_start[];
extern char __builtin_kernel_end[];
extern uint64_t boot_offset;

static size_t initramfs_size;

bool start_preload_kernel(void)
{
	int loaded;

	/* Try to load an external kernel payload through the platform hooks */
	kernel_size = KERNEL_LOAD_SIZE;
	loaded = start_preload_resource(RESOURCE_ID_KERNEL,
					RESOURCE_SUBID_NONE,
					KERNEL_LOAD_BASE,
					&kernel_size);
	if (loaded != OPAL_SUCCESS) {
		printf("INIT: platform start load kernel failed\n");
		kernel_size = 0;
		return false;
	}

	initramfs_size = INITRAMFS_LOAD_SIZE;
	loaded = start_preload_resource(RESOURCE_ID_INITRAMFS,
					RESOURCE_SUBID_NONE,
					INITRAMFS_LOAD_BASE, &initramfs_size);
	if (loaded != OPAL_SUCCESS) {
		printf("INIT: platform start load initramfs failed\n");
		initramfs_size = 0;
		return false;
	}

	return true;
}

static bool load_kernel(void)
{
	void *stb_container = NULL;
	struct elf_hdr *kh;
	int loaded;

	prlog(PR_NOTICE, "INIT: Waiting for kernel...\n");

	loaded = wait_for_resource_loaded(RESOURCE_ID_KERNEL,
					  RESOURCE_SUBID_NONE);

	if (loaded != OPAL_SUCCESS) {
		printf("INIT: platform wait for kernel load failed\n");
		kernel_size = 0;
	}

	/* Try embedded kernel payload */
	if (!kernel_size) {
		kernel_size = __builtin_kernel_end - __builtin_kernel_start;
		if (kernel_size) {
			/* Move the built-in kernel up */
			uint64_t builtin_base =
				((uint64_t)__builtin_kernel_start) -
				SKIBOOT_BASE + boot_offset;
			printf("Using built-in kernel\n");
			memmove(KERNEL_LOAD_BASE, (void*)builtin_base,
				kernel_size);
		}
	}

	if (dt_has_node_property(dt_chosen, "kernel-base-address", NULL)) {
		kernel_entry = dt_prop_get_u64(dt_chosen,
					       "kernel-base-address");
		prlog(PR_DEBUG, "INIT: Kernel image at 0x%llx\n", kernel_entry);
		kh = (struct elf_hdr *)kernel_entry;
		/*
		 * If the kernel is at 0, restore it as it was overwritten
		 * by our vectors.
		 */
		if (kernel_entry < EXCEPTION_VECTORS_END) {
			cpu_set_sreset_enable(false);
			memcpy_null(NULL, old_vectors, EXCEPTION_VECTORS_END);
			sync_icache();
		} else {
			/* Hack for STB in Mambo, assume at least 4kb in mem */
			if (!kernel_size)
				kernel_size = SECURE_BOOT_HEADERS_SIZE;
			if (stb_is_container((void*)kernel_entry, kernel_size)) {
				stb_container = (void*)kernel_entry;
				kh = (struct elf_hdr *) (kernel_entry + SECURE_BOOT_HEADERS_SIZE);
			} else
				kh = (struct elf_hdr *) (kernel_entry);
		}
	} else {
		if (!kernel_size) {
			printf("INIT: Assuming kernel at %p\n",
			       KERNEL_LOAD_BASE);
			/* Hack for STB in Mambo, assume at least 4kb in mem */
			kernel_size = SECURE_BOOT_HEADERS_SIZE;
			kernel_entry = (uint64_t)KERNEL_LOAD_BASE;
		}
		if (stb_is_container(KERNEL_LOAD_BASE, kernel_size)) {
			stb_container = KERNEL_LOAD_BASE;
			kh = (struct elf_hdr *) (KERNEL_LOAD_BASE + SECURE_BOOT_HEADERS_SIZE);
		} else
			kh = (struct elf_hdr *) (KERNEL_LOAD_BASE);

	}

	prlog(PR_DEBUG,
	      "INIT: Kernel loaded, size: %zu bytes (0 = unknown preload)\n",
	      kernel_size);

	if (kh->ei_ident != ELF_IDENT) {
		prerror("INIT: ELF header not found. Assuming raw binary.\n");
		return true;
	}

	if (kh->ei_class == ELF_CLASS_64) {
		if (!try_load_elf64(kh))
			return false;
	} else if (kh->ei_class == ELF_CLASS_32) {
		if (!try_load_elf32(kh))
			return false;
	} else {
		prerror("INIT: Neither ELF32 not ELF64 ?\n");
		return false;
	}

	if (chip_quirk(QUIRK_MAMBO_CALLOUTS)) {
		secureboot_verify(RESOURCE_ID_KERNEL,
				  stb_container,
				  SECURE_BOOT_HEADERS_SIZE + kernel_size);
		trustedboot_measure(RESOURCE_ID_KERNEL,
				    stb_container,
				    SECURE_BOOT_HEADERS_SIZE + kernel_size);
	}

	return true;
}

static void load_initramfs(void)
{
	uint64_t *initramfs_start;
	void *stb_container = NULL;
	int loaded;

	loaded = wait_for_resource_loaded(RESOURCE_ID_INITRAMFS,
					  RESOURCE_SUBID_NONE);

	if (loaded != OPAL_SUCCESS || !initramfs_size)
		return;

	if (stb_is_container(INITRAMFS_LOAD_BASE, initramfs_size)) {
		stb_container = INITRAMFS_LOAD_BASE;
		initramfs_start = INITRAMFS_LOAD_BASE + SECURE_BOOT_HEADERS_SIZE;
	} else {
		initramfs_start = INITRAMFS_LOAD_BASE;
	}

	dt_check_del_prop(dt_chosen, "linux,initrd-start");
	dt_check_del_prop(dt_chosen, "linux,initrd-end");

	printf("INIT: Initramfs loaded, size: %zu bytes\n", initramfs_size);

	dt_add_property_u64(dt_chosen, "linux,initrd-start",
			(uint64_t)initramfs_start);
	dt_add_property_u64(dt_chosen, "linux,initrd-end",
			(uint64_t)initramfs_start + initramfs_size);

	if (chip_quirk(QUIRK_MAMBO_CALLOUTS)) {
		secureboot_verify(RESOURCE_ID_INITRAMFS,
				  stb_container,
				  SECURE_BOOT_HEADERS_SIZE + initramfs_size);
		trustedboot_measure(RESOURCE_ID_INITRAMFS,
				    stb_container,
				    SECURE_BOOT_HEADERS_SIZE + initramfs_size);
	}
}

static void cpu_disable_ME_RI_one(void *param __unused)
{
	disable_machine_check();
	mtmsrd(0, 1);
}

static int64_t cpu_disable_ME_RI_all(void)
{
	struct cpu_thread *cpu;
	struct cpu_job **jobs;

	jobs = zalloc(sizeof(struct cpu_job *) * (cpu_max_pir + 1));
	assert(jobs);

	for_each_available_cpu(cpu) {
		if (cpu == this_cpu())
			continue;
		jobs[cpu->pir] = cpu_queue_job(cpu, "cpu_disable_ME_RI",
						cpu_disable_ME_RI_one, NULL);
	}

	/* this cpu */
	cpu_disable_ME_RI_one(NULL);

	for_each_available_cpu(cpu) {
		if (jobs[cpu->pir])
			cpu_wait_job(jobs[cpu->pir], true);
	}

	free(jobs);

	return OPAL_SUCCESS;
}

static void *fdt;

void __noreturn load_and_boot_kernel(bool is_reboot)
{
	const struct dt_property *memprop;
	const char *cmdline, *stdoutp;
	uint64_t mem_top;

	memprop = dt_find_property(dt_root, DT_PRIVATE "maxmem");
	if (memprop)
		mem_top = (u64)dt_property_get_cell(memprop, 0) << 32
			| dt_property_get_cell(memprop, 1);
	else /* XXX HB hack, might want to calc it */
		mem_top = 0x40000000;

	op_display(OP_LOG, OP_MOD_INIT, 0x000A);

	/* Load kernel LID */
	if (!load_kernel()) {
		op_display(OP_FATAL, OP_MOD_INIT, 1);
		abort();
	}

	load_initramfs();

	trustedboot_exit_boot_services();

	ipmi_set_fw_progress_sensor(IPMI_FW_OS_BOOT);


	if (!is_reboot) {
		/* We wait for the nvram read to complete here so we can
		 * grab stuff from there such as the kernel arguments
		 */
		nvram_wait_for_load();

		if (!occ_sensors_init())
			dts_sensor_create_nodes(sensor_node);

		opal_mpipl_init();

	} else {
		/* fdt will be rebuilt */
		free(fdt);
		fdt = NULL;

		nvram_reinit();
		occ_pstates_init();
	}

	/* Use nvram bootargs over device tree */
	cmdline = nvram_query_safe("bootargs");
	if (cmdline) {
		dt_check_del_prop(dt_chosen, "bootargs");
		dt_add_property_string(dt_chosen, "bootargs", cmdline);
		prlog(PR_DEBUG, "INIT: Command line from NVRAM: %s\n",
		      cmdline);
	}

	op_display(OP_LOG, OP_MOD_INIT, 0x000B);

	add_fast_reboot_dt_entries();

	if (platform.finalise_dt)
		platform.finalise_dt(is_reboot);

	/* Create the device tree blob to boot OS. */
	fdt = create_dtb(dt_root, false);
	if (!fdt) {
		op_display(OP_FATAL, OP_MOD_INIT, 2);
		abort();
	}

	op_display(OP_LOG, OP_MOD_INIT, 0x000C);

	mem_dump_free();

	/* Dump the selected console */
	stdoutp = dt_prop_get_def(dt_chosen, "linux,stdout-path", NULL);
	prlog(PR_DEBUG, "INIT: stdout-path: %s\n", stdoutp ? stdoutp : "");

	fdt_set_boot_cpuid_phys(fdt, this_cpu()->pir);

	/* Check there is something there before we branch to it */
	if (*(uint32_t *)kernel_entry == 0) {
		prlog(PR_EMERG, "FATAL: Kernel is zeros, can't execute!\n");
		assert(0);
	}

	if (platform.exit)
		platform.exit();

	/* Take processors out of nap */
	cpu_set_sreset_enable(false);
	cpu_set_ipi_enable(false);

	printf("INIT: Starting kernel at 0x%llx, fdt at %p %u bytes\n",
	       kernel_entry, fdt, fdt_totalsize(fdt));

	/* Disable machine checks on all */
	cpu_disable_ME_RI_all();

	patch_traps(false);
	cpu_set_hile_mode(false); /* Clear HILE on all CPUs */

	checksum_romem();

	debug_descriptor.state_flags |= OPAL_BOOT_COMPLETE;

	cpu_give_self_os();

	if (kernel_32bit)
		start_kernel32(kernel_entry, fdt, mem_top);
	start_kernel(kernel_entry, fdt, mem_top);
}

static void storage_keys_fixup(void)
{
	struct dt_node *cpus, *n;

	cpus = dt_find_by_path(dt_root, "/cpus");
	assert(cpus);

	if (proc_gen == proc_gen_unknown)
		return;

	dt_for_each_child(cpus, n) {
		/* There may be cache nodes in /cpus. */
		if (!dt_has_node_property(n, "device_type", "cpu") ||
		    dt_has_node_property(n, "ibm,processor-storage-keys", NULL))
			continue;

		/*
		 * skiboot supports p8 & p9, both of which support the IAMR, and
		 * both of which support 32 keys. So advertise 32 keys for data
		 * accesses and 32 for instruction accesses.
		 */
		dt_add_property_cells(n, "ibm,processor-storage-keys", 32, 32);
	}
}

static void dt_fixups(void)
{
	struct dt_node *n;
	struct dt_node *primary_lpc = NULL;

	/* lpc node missing #address/size cells. Also pick one as
	 * primary for now (TBD: How to convey that from HB)
	 */
	dt_for_each_compatible(dt_root, n, "ibm,power8-lpc") {
		if (!primary_lpc || dt_has_node_property(n, "primary", NULL))
			primary_lpc = n;
		if (dt_has_node_property(n, "#address-cells", NULL))
			break;
		dt_add_property_cells(n, "#address-cells", 2);
		dt_add_property_cells(n, "#size-cells", 1);
		dt_add_property_strings(n, "status", "ok");
	}

	/* Missing "primary" property in LPC bus */
	if (primary_lpc && !dt_has_node_property(primary_lpc, "primary", NULL))
		dt_add_property(primary_lpc, "primary", NULL, 0);

	/* Missing "scom-controller" */
	dt_for_each_compatible(dt_root, n, "ibm,xscom") {
		if (!dt_has_node_property(n, "scom-controller", NULL))
			dt_add_property(n, "scom-controller", NULL, 0);
	}

	storage_keys_fixup();
}

static void add_arch_vector(void)
{
	/**
	 * vec5 = a PVR-list : Number-of-option-vectors :
	 *	  option-vectors[Number-of-option-vectors + 1]
	 */
	uint8_t vec5[] = {0x05, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00};

	if (dt_has_node_property(dt_chosen, "ibm,architecture-vec-5", NULL))
		return;

	dt_add_property(dt_chosen, "ibm,architecture-vec-5",
			vec5, sizeof(vec5));
}

static void dt_init_misc(void)
{
	/* Check if there's a /chosen node, if not, add one */
	dt_chosen = dt_find_by_path(dt_root, "/chosen");
	if (!dt_chosen)
		dt_chosen = dt_new(dt_root, "chosen");
	assert(dt_chosen);

	/* Add IBM architecture vectors if needed */
	add_arch_vector();

	/* Add the "OPAL virtual ICS*/
	add_ics_node();

	/* Additional fixups. TODO: Move into platform */
	dt_fixups();
}

static u8 console_get_level(const char *s)
{
	if (strcmp(s, "emerg") == 0)
		return PR_EMERG;
	if (strcmp(s, "alert") == 0)
		return PR_ALERT;
	if (strcmp(s, "crit") == 0)
		return PR_CRIT;
	if (strcmp(s, "err") == 0)
		return PR_ERR;
	if (strcmp(s, "warning") == 0)
		return PR_WARNING;
	if (strcmp(s, "notice") == 0)
		return PR_NOTICE;
	if (strcmp(s, "printf") == 0)
		return PR_PRINTF;
	if (strcmp(s, "info") == 0)
		return PR_INFO;
	if (strcmp(s, "debug") == 0)
		return PR_DEBUG;
	if (strcmp(s, "trace") == 0)
		return PR_TRACE;
	if (strcmp(s, "insane") == 0)
		return PR_INSANE;
	/* Assume it's a number instead */
	return atoi(s);
}

static void console_log_level(void)
{
	const char *s;
	u8 level;

	/* console log level:
	 *   high 4 bits in memory, low 4 bits driver (e.g. uart). */
	s = nvram_query_safe("log-level-driver");
	if (s) {
		level = console_get_level(s);
		debug_descriptor.console_log_levels =
			(debug_descriptor.console_log_levels & 0xf0 ) |
			(level & 0x0f);
		prlog(PR_NOTICE, "console: Setting driver log level to %i\n",
		      level & 0x0f);
	}
	s = nvram_query_safe("log-level-memory");
	if (s) {
		level = console_get_level(s);
		debug_descriptor.console_log_levels =
			(debug_descriptor.console_log_levels & 0x0f ) |
			((level & 0x0f) << 4);
		prlog(PR_NOTICE, "console: Setting memory log level to %i\n",
		      level & 0x0f);
	}
}

typedef void (*ctorcall_t)(void);

static void __nomcount do_ctors(void)
{
	extern ctorcall_t __ctors_start[], __ctors_end[];
	ctorcall_t *call;

	for (call = __ctors_start; call < __ctors_end; call++)
		(*call)();
}

#ifdef ELF_ABI_v2
static void setup_branch_null_catcher(void)
{
	asm volatile(							\
		".section .rodata"				"\n\t"	\
		"3:	.string	\"branch to NULL\""		"\n\t"	\
		".previous"					"\n\t"	\
		".section .trap_table,\"aw\""			"\n\t"	\
		".llong	0"					"\n\t"	\
		".llong	3b"					"\n\t"	\
		".previous"					"\n\t"	\
		);
}
#else
static void branch_null(void)
{
	assert(0);
}

static void setup_branch_null_catcher(void)
{
       void (*bn)(void) = branch_null;

       /*
        * FIXME: This copies the function descriptor (16 bytes) for
        * ABI v1 (ie. big endian).  This will be broken if we ever
        * move to ABI v2 (ie little endian)
        */
       memcpy_null((void *)0, bn, 16);
}
#endif

void copy_sreset_vector(void)
{
	uint32_t *src, *dst;

	/* Copy the reset code over the entry point. */
	src = &reset_patch_start;
	dst = (uint32_t *)0x100;
	while(src < &reset_patch_end)
		*(dst++) = *(src++);
	sync_icache();
}

void copy_sreset_vector_fast_reboot(void)
{
	uint32_t *src, *dst;

	/* Copy the reset code over the entry point. */
	src = &reset_fast_reboot_patch_start;
	dst = (uint32_t *)0x100;
	while(src < &reset_fast_reboot_patch_end)
		*(dst++) = *(src++);
	sync_icache();
}

void copy_exception_vectors(void)
{
	/* Copy from 0x100 to EXCEPTION_VECTORS_END, avoid below 0x100 as
	 * this is the boot flag used by CPUs still potentially entering
	 * skiboot.
	 */
	void *skiboot_constant_addr exception_vectors_start_addr = (void *)(SKIBOOT_BASE + 0x100);
	void *skiboot_constant_addr dst = (void *)0x100;


	memcpy(dst, exception_vectors_start_addr,
			EXCEPTION_VECTORS_END - 0x100);
	sync_icache();
}

/*
 * When skiboot owns the exception vectors, patch in 'trap' for assert fails.
 * Otherwise use assert_fail()
 */
void patch_traps(bool enable)
{
	struct trap_table_entry *tte;

	for (tte = __trap_table_start; tte < __trap_table_end; tte++) {
		uint32_t *insn;

		insn = (uint32_t *)tte->address;
		if (enable) {
			*insn = PPC_INST_TRAP;
		} else {
			*insn = PPC_INST_NOP;
		}
	}

	sync_icache();
}

static void per_thread_sanity_checks(void)
{
	struct cpu_thread *cpu = this_cpu();

	/**
	 * @fwts-label NonZeroHRMOR
	 * @fwts-advice The contents of the hypervisor real mode offset register
	 * (HRMOR) is bitwise orded with the address of any hypervisor real mode
	 * (i.e Skiboot) memory accesses. Skiboot does not support operating
	 * with a non-zero HRMOR and setting it will break some things (e.g
	 * XSCOMs) in hard-to-debug ways.
	 */
	assert(mfspr(SPR_HRMOR) == 0);

	/**
	 * @fwts-label UnknownSecondary
	 * @fwts-advice The boot CPU attampted to call in a secondary thread
	 * without initialising the corresponding cpu_thread structure. This may
	 * happen if the HDAT or devicetree reports too few threads or cores for
	 * this processor.
	 */
	assert(cpu->state != cpu_state_no_cpu);
}

void pci_nvram_init(void)
{
	const char *nvram_speed;

	verbose_eeh = nvram_query_eq_safe("pci-eeh-verbose", "true");
	if (verbose_eeh)
		prlog(PR_INFO, "PHB: Verbose EEH enabled\n");

	pcie_max_link_speed = 0;

	nvram_speed = nvram_query_dangerous("pcie-max-link-speed");
	if (nvram_speed) {
		pcie_max_link_speed = atoi(nvram_speed);
		prlog(PR_NOTICE, "PHB: NVRAM set max link speed to GEN%i\n",
		      pcie_max_link_speed);
	}

	pci_tracing = nvram_query_eq_safe("pci-tracing", "true");
}

static uint32_t mem_csum(void *_p, void *_e)
{
	size_t len = _e - _p;
	uint32_t *p = _p;
	uint32_t v1 = 0, v2 = 0;
	uint32_t csum;
	unsigned int i;

	for (i = 0; i < len; i += 4) {
		uint32_t v = *p++;
		v1 += v;
		v2 += v1;
	}

	csum = v1 ^ v2;

	return csum;
}

static uint32_t romem_csum;

static void checksum_romem(void)
{
	uint32_t csum;

	romem_csum = 0;
	if (chip_quirk(QUIRK_SLOW_SIM))
		return;

	csum = mem_csum(_start, _head_end);
	romem_csum ^= csum;

	csum = mem_csum(_stext, _romem_end);
	romem_csum ^= csum;

	csum = mem_csum(__builtin_kernel_start, __builtin_kernel_end);
	romem_csum ^= csum;
}

bool verify_romem(void)
{
	uint32_t old = romem_csum;
	checksum_romem();
	if (old != romem_csum) {
		romem_csum = old;
		prlog(PR_NOTICE, "OPAL checksums did not match\n");
		return false;
	}
	return true;
}

static void mask_pc_system_xstop(void)
{
        struct cpu_thread *cpu;
        uint32_t chip_id, core_id;
        int rc;

	if (proc_gen != proc_gen_p10)
                return;

	if (chip_quirk(QUIRK_MAMBO_CALLOUTS) || chip_quirk(QUIRK_AWAN))
		return;

        /*
         * On P10 Mask PC system checkstop (bit 28). This is needed
         * for HW570622. We keep processor recovery disabled via
         * HID[5] and mask the checkstop that it can cause. CME does
         * the recovery handling for us.
         */
        for_each_cpu(cpu) {
                chip_id = cpu->chip_id;
                core_id = pir_to_core_id(cpu->pir);

                rc = xscom_write(chip_id,
                                 XSCOM_ADDR_P10_EC(core_id, P10_CORE_FIRMASK_OR),
                                 PPC_BIT(28));
                if (rc)
                        prerror("Error setting FIR MASK rc:%d on PIR:%x\n",
                                rc, cpu->pir);
        }
}

bool lpar_per_core = false;

static void probe_lpar_per_core(void)
{
	struct cpu_thread *cpu = this_cpu();
	uint32_t chip_id = pir_to_chip_id(cpu->pir);
	uint32_t core_id = pir_to_core_id(cpu->pir);
	uint64_t addr;
	uint64_t core_thread_state;
	int rc;

	if (chip_quirk(QUIRK_MAMBO_CALLOUTS) || chip_quirk(QUIRK_AWAN))
		return;

	if (proc_gen == proc_gen_p9)
		addr = XSCOM_ADDR_P9_EC(core_id, P9_CORE_THREAD_STATE);
	else if (proc_gen == proc_gen_p10)
		addr = XSCOM_ADDR_P10_EC(core_id, P10_EC_CORE_THREAD_STATE);
	else
		return;

	rc = xscom_read(chip_id, addr, &core_thread_state);
	if (rc) {
		prerror("Error reading CORE_THREAD_STATE rc:%d on PIR:%x\n",
			rc, cpu->pir);
		return;
	}

	if (core_thread_state & PPC_BIT(62)) {
		lpar_per_core = true;
		prlog(PR_WARNING, "LPAR-per-core mode detected. KVM may not be usable.\n");
	}
}


/* Called from head.S, thus no prototype. */
void __noreturn __nomcount  main_cpu_entry(const void *fdt);

void __noreturn __nomcount main_cpu_entry(const void *fdt)
{
	/*
	 * WARNING: At this point. the timebases have
	 * *not* been synchronized yet. Do not use any timebase
	 * related functions for timeouts etc... unless you can cope
	 * with the speed being some random core clock divider and
	 * the value jumping backward when the synchronization actually
	 * happens (in chiptod_init() below).
	 *
	 * Also the current cpu_thread() struct is not initialized
	 * either so we need to clear it out first thing first (without
	 * putting any other useful info in there jus yet) otherwise
	 * printf an locks are going to play funny games with "con_suspend"
	 */
	pre_init_boot_cpu();

	/*
	 * Point to our mem console
	 */
	debug_descriptor.memcons_phys = cpu_to_be64((uint64_t)&memcons);

	/*
	 * Before first printk, ensure console buffer is clear or
	 * reading tools might think it has wrapped
	 */
	clear_console();

	/* Backup previous vectors as this could contain a kernel
	 * image.
	 */
	memcpy_null(old_vectors, NULL, EXCEPTION_VECTORS_END);

	/*
	 * Some boot firmwares enter OPAL with MSR[ME]=1, as they presumably
	 * handle machine checks until we take over. As we overwrite the
	 * previous exception vectors with our own handlers, disable MSR[ME].
	 * This could be done atomically by patching in a branch then patching
	 * it out last, but that's a lot of effort.
	 */
	disable_machine_check();

	/* Copy all vectors down to 0 */
	copy_exception_vectors();

	/* Enable trap based asserts */
	patch_traps(true);

	/*
	 * Enable MSR[ME] bit so we can take MCEs. We don't currently
	 * recover, but we print some useful information.
	 */
	enable_machine_check();
	mtmsrd(MSR_RI, 1);

	/* Setup a NULL catcher to catch accidental NULL ptr calls */
	setup_branch_null_catcher();

	/* Call library constructors */
	do_ctors();

	prlog(PR_NOTICE, "OPAL %s%s starting...\n", version, DEBUG_STR);

	prlog(PR_DEBUG, "initial console log level: memory %d, driver %d\n",
	       (debug_descriptor.console_log_levels >> 4),
	       (debug_descriptor.console_log_levels & 0x0f));
	prlog(PR_TRACE, "OPAL is Powered By Linked-List Technology.\n");

#ifdef SKIBOOT_GCOV
	skiboot_gcov_done();
#endif

	/* Initialize boot cpu's cpu_thread struct */
	init_boot_cpu();

	/* Now locks can be used */
	init_locks();

	/* Create the OPAL call table early on, entries can be overridden
	 * later on (FSP console code for example)
	 */
	opal_table_init();

	/* Init the physical map table so we can start mapping things */
	phys_map_init(mfspr(SPR_PVR));

	/*
	 * If we are coming in with a flat device-tree, we expand it
	 * now. Else look for HDAT and create a device-tree from them
	 *
	 * Hack alert: When entering via the OPAL entry point, fdt
	 * is set to -1, we record that and pass it to parse_hdat
	 */

	dt_root = dt_new_root("");

	if (fdt == (void *)-1ul) {
		if (parse_hdat(true) < 0)
			abort();
	} else if (fdt == NULL) {
		if (parse_hdat(false) < 0)
			abort();
	} else {
		dt_expand(fdt);
	}
	dt_add_cpufeatures(dt_root);

	/* Now that we have a full devicetree, verify that we aren't on fire. */
	per_thread_sanity_checks();

	/*
	 * From there, we follow a fairly strict initialization order.
	 *
	 * First we need to build up our chip data structures and initialize
	 * XSCOM which will be needed for a number of susbequent things.
	 *
	 * We want XSCOM available as early as the platform probe in case the
	 * probe requires some HW accesses.
	 *
	 * We also initialize the FSI master at that point in case we need
	 * to access chips via that path early on.
	 */
	init_chips();

	xscom_init();
	mfsi_init();

	/*
	 * Direct controls facilities provides some controls over CPUs
	 * using scoms.
	 */
	direct_controls_init();

	/*
	 * Put various bits & pieces in device-tree that might not
	 * already be there such as the /chosen node if not there yet,
	 * the ICS node, etc... This can potentially use XSCOM
	 */
	dt_init_misc();

	/*
	 * Initialize LPC (P8 and beyond) so we can get to UART, BMC and
	 * other system controller. This is done before probe_platform
	 * so that the platform probing code can access an external
	 * BMC if needed.
	 */
	lpc_init();

	/*
	 * This should be done before mem_region_init, so the stack
	 * region length can be set according to the maximum PIR.
	 */
	init_cpu_max_pir();

	/*
	 * Now, we init our memory map from the device-tree, and immediately
	 * reserve areas which we know might contain data coming from
	 * HostBoot. We need to do these things before we start doing
	 * allocations outside of our heap, such as chip local allocs,
	 * otherwise we might clobber those data.
	 */
	mem_region_init();

	/*
	 * Reserve memory required to capture OPAL dump. This should be done
	 * immediately after mem_region_init to avoid any clash with local
	 * memory allocation.
	 */
	opal_mpipl_reserve_mem();

	/* Reserve HOMER and OCC area */
	homer_init();

	/* Initialize the rest of the cpu thread structs */
	init_all_cpus();
	if (proc_gen == proc_gen_p9 || proc_gen == proc_gen_p10)
		cpu_set_ipi_enable(true);

        /* Once all CPU are up apply this workaround */
        mask_pc_system_xstop();

	/* P9/10 may be in LPAR-per-core mode, which is incompatible with KVM */
	probe_lpar_per_core();

	/* Add the /opal node to the device-tree */
	add_opal_node();

	/*
	 * We probe the platform now. This means the platform probe gets
	 * the opportunity to reserve additional areas of memory if needed.
	 *
	 * Note: Timebases still not synchronized.
	 */
	probe_platform();

	/* Allocate our split trace buffers now. Depends add_opal_node() */
	init_trace_buffers();

	/* On P8, get the ICPs and make sure they are in a sane state */
	init_interrupts();
	if (proc_gen == proc_gen_p8)
		cpu_set_ipi_enable(true);

	/* On P9 and P10, initialize XIVE */
	if (proc_gen == proc_gen_p9)
		init_xive();
	else if (proc_gen == proc_gen_p10)
		xive2_init();

	/* Grab centaurs from device-tree if present (only on FSP-less) */
	centaur_init();

	/* initialize ocmb scom-controller */
	ocmb_init();

	/* Initialize PSI (depends on probe_platform being called) */
	psi_init();

	/* Initialize/enable LPC interrupts. This must be done after the
	 * PSI interface has been initialized since it serves as an interrupt
	 * source for LPC interrupts.
	 */
	lpc_init_interrupts();

	/* Call in secondary CPUs */
	cpu_bringup();

	/* We can now overwrite the 0x100 vector as we are no longer being
	 * entered there.
	 */
	copy_sreset_vector();

	/* We can now do NAP mode */
	cpu_set_sreset_enable(true);

	/*
	 * Synchronize time bases. Prior to chiptod_init() the timebase
	 * is free-running at a frequency based on the core clock rather
	 * than being synchronised to the ChipTOD network. This means
	 * that the timestamps in early boot might be a little off compared
	 * to wall clock time.
	 */
	chiptod_init();

	/* Initialize P9 DIO */
	p9_dio_init();

	/*
	 * SBE uses TB value for scheduling timer. Hence init after
	 * chiptod init
	 */
	p9_sbe_init();

	/* Initialize i2c */
	p8_i2c_init();

	/* Register routine to dispatch and read sensors */
	sensor_init();

        /*
	 * Initialize the opal messaging before platform.init as we are
	 * getting request to queue occ load opal message when host services
	 * got load occ request from FSP
	 */
        opal_init_msg();

	/*
	 * We have initialized the basic HW, we can now call into the
	 * platform to perform subsequent inits, such as establishing
	 * communication with the FSP or starting IPMI.
	 */
	if (platform.init)
		platform.init();

	/* Read in NVRAM and set it up */
	nvram_init();

	/* Set the console level */
	console_log_level();

	/* Secure/Trusted Boot init. We look for /ibm,secureboot in DT */
	secureboot_init();
	trustedboot_init();

	/* Secure variables init, handled by platform */
	if (platform.secvar_init && is_fw_secureboot())
		platform.secvar_init();

	/*
	 * BMC platforms load version information from flash after
	 * secure/trustedboot init.
	 */
	if (platform.bmc)
		flash_fw_version_preload();

        /* preload the IMC catalog dtb */
        imc_catalog_preload();

	/* Install the OPAL Console handlers */
	init_opal_console();

	/*
	 * Some platforms set a flag to wait for SBE validation to be
	 * performed by the BMC. If this occurs it leaves the SBE in a
	 * bad state and the system will reboot at this point.
	 */
	if (platform.seeprom_update)
		platform.seeprom_update();

	/* Init SLW related stuff, including fastsleep */
	slw_init();

	op_display(OP_LOG, OP_MOD_INIT, 0x0002);

	/*
	 * On some POWER9 BMC systems, we need to initialise the OCC
	 * before the NPU to facilitate NVLink/OpenCAPI presence
	 * detection, so we set it up as early as possible. On FSP
	 * systems, Hostboot starts booting the OCC later, so we delay
	 * OCC initialisation as late as possible to give it the
	 * maximum time to boot up.
	 */
	if (platform.bmc)
		occ_pstates_init();

	pci_nvram_init();

	preload_capp_ucode();
	start_preload_kernel();

	/* Catalog decompression routine */
	imc_decompress_catalog();

	/* Probe all HWPROBE hardware we have code linked for */
	probe_hardware();

	/* Initialize PCI */
	pci_init_slots();

	/* Add OPAL timer related properties */
	late_init_timers();

	/* Setup ibm,firmware-versions if able */
	if (platform.bmc) {
		flash_dt_add_fw_version();
		ipmi_dt_add_bmc_info();
	}

	ipmi_set_fw_progress_sensor(IPMI_FW_PCI_INIT);

	/*
	 * These last few things must be done as late as possible
	 * because they rely on various other things having been setup,
	 * for example, add_opal_interrupts() will add all the interrupt
	 * sources that are going to the firmware. We can't add a new one
	 * after that call. Similarly, the mem_region calls will construct
	 * the reserve maps in the DT so we shouldn't affect the memory
	 * regions after that
	 */

	/* Create the LPC bus interrupt-map on P9 */
	lpc_finalize_interrupts();

	/* Add the list of interrupts going to OPAL */
	add_opal_interrupts();

	/* Init In-Memory Collection related stuff (load the IMC dtb into memory) */
	imc_init();

	/* Disable protected execution facility in BML */
	cpu_disable_pef();

	/* export the trace buffers */
	trace_add_dt_props();

	/* Now release parts of memory nodes we haven't used ourselves... */
	mem_region_release_unused();

	/* ... and add remaining reservations to the DT */
	mem_region_add_dt_reserved();

	/*
	 * Update /ibm,secureboot/ibm,cvc/memory-region to point to
	 * /reserved-memory/secure-crypt-algo-code instead of
	 * /ibm,hostboot/reserved-memory/secure-crypt-algo-code.
	 */
	cvc_update_reserved_memory_phandle();

	prd_register_reserved_memory();

	load_and_boot_kernel(false);
}

void __noreturn __secondary_cpu_entry(void)
{
	struct cpu_thread *cpu = this_cpu();

	/* Secondary CPU called in */
	cpu_callin(cpu);

	enable_machine_check();
	mtmsrd(MSR_RI, 1);

	/* Some XIVE setup */
	if (proc_gen == proc_gen_p9)
		xive_cpu_callin(cpu);
	else if (proc_gen == proc_gen_p10)
		xive2_cpu_callin(cpu);

	/* Wait for work to do */
	while(true) {
		if (cpu_check_jobs(cpu))
			cpu_process_jobs();
		else
			cpu_idle_job();
	}
}

/* Called from head.S, thus no prototype. */
void __noreturn __nomcount secondary_cpu_entry(void);

void __noreturn __nomcount secondary_cpu_entry(void)
{
	struct cpu_thread *cpu = this_cpu();

	per_thread_sanity_checks();

	prlog(PR_DEBUG, "INIT: CPU PIR 0x%04x called in\n", cpu->pir);

	__secondary_cpu_entry();
}
