// SPDX-License-Identifier: GPL-2.0-only
/*
 * efi.c - EFI subsystem
 *
 * Copyright (C) 2001,2003,2004 Dell <Matt_Domsch@dell.com>
 * Copyright (C) 2004 Intel Corporation <matthew.e.tolentino@intel.com>
 * Copyright (C) 2013 Tom Gundersen <teg@jklm.no>
 *
 * This code registers /sys/firmware/efi{,/efivars} when EFI is supported,
 * allowing the efivarfs to be mounted or the efivars module to be loaded.
 * The existance of /sys/firmware/efi may also be used by userspace to
 * determine that the system supports EFI.
 */

#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

#include <linux/kobject.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/debugfs.h>
#include <linux/device.h>
#include <linux/efi.h>
#include <linux/of.h>
#include <linux/initrd.h>
#include <linux/io.h>
#include <linux/kexec.h>
#include <linux/platform_device.h>
#include <linux/random.h>
#include <linux/reboot.h>
#include <linux/slab.h>
#include <linux/acpi.h>
#include <linux/ucs2_string.h>
#include <linux/memblock.h>
#include <linux/security.h>
#include <linux/notifier.h>

#include <asm/early_ioremap.h>

struct efi __read_mostly efi = {
	.runtime_supported_mask = EFI_RT_SUPPORTED_ALL,
	.acpi			= EFI_INVALID_TABLE_ADDR,
	.acpi20			= EFI_INVALID_TABLE_ADDR,
	.smbios			= EFI_INVALID_TABLE_ADDR,
	.smbios3		= EFI_INVALID_TABLE_ADDR,
	.esrt			= EFI_INVALID_TABLE_ADDR,
	.tpm_log		= EFI_INVALID_TABLE_ADDR,
	.tpm_final_log		= EFI_INVALID_TABLE_ADDR,
	.ovmf_debug_log         = EFI_INVALID_TABLE_ADDR,
#ifdef CONFIG_LOAD_UEFI_KEYS
	.mokvar_table		= EFI_INVALID_TABLE_ADDR,
#endif
#ifdef CONFIG_EFI_COCO_SECRET
	.coco_secret		= EFI_INVALID_TABLE_ADDR,
#endif
#ifdef CONFIG_UNACCEPTED_MEMORY
	.unaccepted		= EFI_INVALID_TABLE_ADDR,
#endif
};
EXPORT_SYMBOL(efi);

unsigned long __ro_after_init efi_rng_seed = EFI_INVALID_TABLE_ADDR;
static unsigned long __initdata mem_reserve = EFI_INVALID_TABLE_ADDR;
static unsigned long __initdata rt_prop = EFI_INVALID_TABLE_ADDR;
static unsigned long __initdata initrd = EFI_INVALID_TABLE_ADDR;

extern unsigned long primary_display_table;

struct mm_struct efi_mm = {
	.mm_mt			= MTREE_INIT_EXT(mm_mt, MM_MT_FLAGS, efi_mm.mmap_lock),
	.mm_users		= ATOMIC_INIT(2),
	.mm_count		= ATOMIC_INIT(1),
	.write_protect_seq      = SEQCNT_ZERO(efi_mm.write_protect_seq),
	MMAP_LOCK_INITIALIZER(efi_mm)
	.page_table_lock	= __SPIN_LOCK_UNLOCKED(efi_mm.page_table_lock),
	.mmlist			= LIST_HEAD_INIT(efi_mm.mmlist),
	.user_ns		= &init_user_ns,
#ifdef CONFIG_SCHED_MM_CID
	.mm_cid.lock		= __RAW_SPIN_LOCK_UNLOCKED(efi_mm.mm_cid.lock),
#endif
	.flexible_array		= MM_STRUCT_FLEXIBLE_ARRAY_INIT,
};

struct workqueue_struct *efi_rts_wq;

static bool disable_runtime = IS_ENABLED(CONFIG_EFI_DISABLE_RUNTIME);
static int __init setup_noefi(char *arg)
{
	disable_runtime = true;
	return 0;
}
early_param("noefi", setup_noefi);

bool efi_runtime_disabled(void)
{
	return disable_runtime;
}

bool __pure __efi_soft_reserve_enabled(void)
{
	return !efi_enabled(EFI_MEM_NO_SOFT_RESERVE);
}

static int __init parse_efi_cmdline(char *str)
{
	if (!str) {
		pr_warn("need at least one option\n");
		return -EINVAL;
	}

	if (parse_option_str(str, "debug"))
		set_bit(EFI_DBG, &efi.flags);

	if (parse_option_str(str, "noruntime"))
		disable_runtime = true;

	if (parse_option_str(str, "runtime"))
		disable_runtime = false;

	if (parse_option_str(str, "nosoftreserve"))
		set_bit(EFI_MEM_NO_SOFT_RESERVE, &efi.flags);

	return 0;
}
early_param("efi", parse_efi_cmdline);

struct kobject *efi_kobj;

/*
 * Let's not leave out systab information that snuck into
 * the efivars driver
 * Note, do not add more fields in systab sysfs file as it breaks sysfs
 * one value per file rule!
 */
static ssize_t systab_show(struct kobject *kobj,
			   struct kobj_attribute *attr, char *buf)
{
	char *str = buf;

	if (!kobj || !buf)
		return -EINVAL;

	if (efi.acpi20 != EFI_INVALID_TABLE_ADDR)
		str += sprintf(str, "ACPI20=0x%lx\n", efi.acpi20);
	if (efi.acpi != EFI_INVALID_TABLE_ADDR)
		str += sprintf(str, "ACPI=0x%lx\n", efi.acpi);
	/*
	 * If both SMBIOS and SMBIOS3 entry points are implemented, the
	 * SMBIOS3 entry point shall be preferred, so we list it first to
	 * let applications stop parsing after the first match.
	 */
	if (efi.smbios3 != EFI_INVALID_TABLE_ADDR)
		str += sprintf(str, "SMBIOS3=0x%lx\n", efi.smbios3);
	if (efi.smbios != EFI_INVALID_TABLE_ADDR)
		str += sprintf(str, "SMBIOS=0x%lx\n", efi.smbios);

	return str - buf;
}

static struct kobj_attribute efi_attr_systab = __ATTR_RO_MODE(systab, 0400);

static ssize_t fw_platform_size_show(struct kobject *kobj,
				     struct kobj_attribute *attr, char *buf)
{
	return sprintf(buf, "%d\n", efi_enabled(EFI_64BIT) ? 64 : 32);
}

extern __weak struct kobj_attribute efi_attr_fw_vendor;
extern __weak struct kobj_attribute efi_attr_runtime;
extern __weak struct kobj_attribute efi_attr_config_table;
static struct kobj_attribute efi_attr_fw_platform_size =
	__ATTR_RO(fw_platform_size);

static struct attribute *efi_subsys_attrs[] = {
	&efi_attr_systab.attr,
	&efi_attr_fw_platform_size.attr,
	&efi_attr_fw_vendor.attr,
	&efi_attr_runtime.attr,
	&efi_attr_config_table.attr,
	NULL,
};

umode_t __weak efi_attr_is_visible(struct kobject *kobj, struct attribute *attr,
				   int n)
{
	return attr->mode;
}

static const struct attribute_group efi_subsys_attr_group = {
	.attrs = efi_subsys_attrs,
	.is_visible = efi_attr_is_visible,
};

struct blocking_notifier_head efivar_ops_nh;
EXPORT_SYMBOL_GPL(efivar_ops_nh);

static struct efivars generic_efivars;
static struct efivar_operations generic_ops;

static bool generic_ops_supported(void)
{
	unsigned long name_size;
	efi_status_t status;
	efi_char16_t name;
	efi_guid_t guid;

	name_size = sizeof(name);

	if (!efi.get_next_variable)
		return false;
	status = efi.get_next_variable(&name_size, &name, &guid);
	if (status == EFI_UNSUPPORTED)
		return false;

	return true;
}

static int generic_ops_register(void)
{
	if (!generic_ops_supported())
		return 0;

	generic_ops.get_variable = efi.get_variable;
	generic_ops.get_next_variable = efi.get_next_variable;
	generic_ops.query_variable_store = efi_query_variable_store;
	generic_ops.query_variable_info = efi.query_variable_info;

	if (efi_rt_services_supported(EFI_RT_SUPPORTED_SET_VARIABLE)) {
		generic_ops.set_variable = efi.set_variable;
		generic_ops.set_variable_nonblocking = efi.set_variable_nonblocking;
	}
	return efivars_register(&generic_efivars, &generic_ops);
}

static void generic_ops_unregister(void)
{
	if (!generic_ops.get_variable)
		return;

	efivars_unregister(&generic_efivars);
}

void efivars_generic_ops_register(void)
{
	generic_ops_register();
}
EXPORT_SYMBOL_GPL(efivars_generic_ops_register);

void efivars_generic_ops_unregister(void)
{
	generic_ops_unregister();
}
EXPORT_SYMBOL_GPL(efivars_generic_ops_unregister);

#ifdef CONFIG_EFI_CUSTOM_SSDT_OVERLAYS
#define EFIVAR_SSDT_NAME_MAX	16UL
static char efivar_ssdt[EFIVAR_SSDT_NAME_MAX] __initdata;
static int __init efivar_ssdt_setup(char *str)
{
	int ret = security_locked_down(LOCKDOWN_ACPI_TABLES);

	if (ret)
		return ret;

	if (strlen(str) < sizeof(efivar_ssdt))
		memcpy(efivar_ssdt, str, strlen(str));
	else
		pr_warn("efivar_ssdt: name too long: %s\n", str);
	return 1;
}
__setup("efivar_ssdt=", efivar_ssdt_setup);

static __init int efivar_ssdt_load(void)
{
	unsigned long name_size = 256;
	efi_char16_t *name = NULL;
	efi_status_t status;
	efi_guid_t guid;
	int ret = 0;

	if (!efivar_ssdt[0])
		return 0;

	name = kzalloc(name_size, GFP_KERNEL);
	if (!name)
		return -ENOMEM;

	for (;;) {
		char utf8_name[EFIVAR_SSDT_NAME_MAX];
		unsigned long data_size = 0;
		void *data;
		int limit;

		status = efi.get_next_variable(&name_size, name, &guid);
		if (status == EFI_NOT_FOUND) {
			break;
		} else if (status == EFI_BUFFER_TOO_SMALL) {
			efi_char16_t *name_tmp =
				krealloc(name, name_size, GFP_KERNEL);
			if (!name_tmp) {
				ret = -ENOMEM;
				goto out;
			}
			name = name_tmp;
			continue;
		}

		limit = min(EFIVAR_SSDT_NAME_MAX, name_size);
		ucs2_as_utf8(utf8_name, name, limit - 1);
		if (strncmp(utf8_name, efivar_ssdt, limit) != 0)
			continue;

		pr_info("loading SSDT from variable %s-%pUl\n", efivar_ssdt, &guid);

		status = efi.get_variable(name, &guid, NULL, &data_size, NULL);
		if (status != EFI_BUFFER_TOO_SMALL || !data_size) {
			ret = -EIO;
			goto out;
		}

		data = kmalloc(data_size, GFP_KERNEL);
		if (!data) {
			ret = -ENOMEM;
			goto out;
		}

		status = efi.get_variable(name, &guid, NULL, &data_size, data);
		if (status == EFI_SUCCESS) {
			acpi_status acpi_ret = acpi_load_table(data, NULL);
			if (ACPI_FAILURE(acpi_ret)) {
				pr_err("efivar_ssdt: failed to load table: %u\n",
				       acpi_ret);
			} else {
				/*
				 * The @data will be in use by ACPI engine,
				 * do not free it!
				 */
				continue;
			}
		} else {
			pr_err("efivar_ssdt: failed to get var data: 0x%lx\n", status);
		}
		kfree(data);
	}
out:
	kfree(name);
	return ret;
}
#else
static inline int efivar_ssdt_load(void) { return 0; }
#endif

#ifdef CONFIG_DEBUG_FS

#define EFI_DEBUGFS_MAX_BLOBS 32

static struct debugfs_blob_wrapper debugfs_blob[EFI_DEBUGFS_MAX_BLOBS];

static void __init efi_debugfs_init(void)
{
	struct dentry *efi_debugfs;
	efi_memory_desc_t *md;
	char name[32];
	int type_count[EFI_BOOT_SERVICES_DATA + 1] = {};
	int i = 0;

	efi_debugfs = debugfs_create_dir("efi", NULL);
	if (IS_ERR(efi_debugfs))
		return;

	for_each_efi_memory_desc(md) {
		switch (md->type) {
		case EFI_BOOT_SERVICES_CODE:
			snprintf(name, sizeof(name), "boot_services_code%d",
				 type_count[md->type]++);
			break;
		case EFI_BOOT_SERVICES_DATA:
			snprintf(name, sizeof(name), "boot_services_data%d",
				 type_count[md->type]++);
			break;
		default:
			continue;
		}

		if (i >= EFI_DEBUGFS_MAX_BLOBS) {
			pr_warn("More then %d EFI boot service segments, only showing first %d in debugfs\n",
				EFI_DEBUGFS_MAX_BLOBS, EFI_DEBUGFS_MAX_BLOBS);
			break;
		}

		debugfs_blob[i].size = md->num_pages << EFI_PAGE_SHIFT;
		debugfs_blob[i].data = memremap(md->phys_addr,
						debugfs_blob[i].size,
						MEMREMAP_WB);
		if (!debugfs_blob[i].data)
			continue;

		debugfs_create_blob(name, 0400, efi_debugfs, &debugfs_blob[i]);
		i++;
	}
}
#else
static inline void efi_debugfs_init(void) {}
#endif

static int __init efipostcore_init(void)
{
	if (!efi_enabled(EFI_RUNTIME_SERVICES))
		efi.runtime_supported_mask = 0;

	if (efi.runtime_supported_mask) {
		/*
		 * Since we process only one efi_runtime_service() at a time, an
		 * ordered workqueue (which creates only one execution context)
		 * should suffice for all our needs.
		 */
		efi_rts_wq = alloc_ordered_workqueue("efi_runtime", WQ_SYSFS);
		if (!efi_rts_wq) {
			pr_err("Creating efi_rts_wq failed, EFI runtime services disabled.\n");
			clear_bit(EFI_RUNTIME_SERVICES, &efi.flags);
			efi.runtime_supported_mask = 0;
		}
	}
	return 0;
}
postcore_initcall(efipostcore_init);

/*
 * We register the efi subsystem with the firmware subsystem and the
 * efivars subsystem with the efi subsystem, if the system was booted with
 * EFI.
 */
static int __init efisubsys_init(void)
{
	int error;

	if (!efi_enabled(EFI_BOOT))
		return 0;

	if (efi_rt_services_supported(EFI_RT_SUPPORTED_TIME_SERVICES))
		platform_device_register_simple("rtc-efi", 0, NULL, 0);

	/* We register the efi directory at /sys/firmware/efi */
	efi_kobj = kobject_create_and_add("efi", firmware_kobj);
	if (!efi_kobj) {
		pr_err("efi: Firmware registration failed.\n");
		error = -ENOMEM;
		goto err_destroy_wq;
	}

	if (efi_rt_services_supported(EFI_RT_SUPPORTED_GET_VARIABLE |
				      EFI_RT_SUPPORTED_GET_NEXT_VARIABLE_NAME)) {
		error = generic_ops_register();
		if (error)
			goto err_put;
		error = efivar_ssdt_load();
		if (error)
			pr_err("efi: failed to load SSDT, error %d.\n", error);
		platform_device_register_simple("efivars", 0, NULL, 0);
	}

	BLOCKING_INIT_NOTIFIER_HEAD(&efivar_ops_nh);

	error = sysfs_create_group(efi_kobj, &efi_subsys_attr_group);
	if (error) {
		pr_err("efi: Sysfs attribute export failed with error %d.\n",
		       error);
		goto err_unregister;
	}

	/* and the standard mountpoint for efivarfs */
	error = sysfs_create_mount_point(efi_kobj, "efivars");
	if (error) {
		pr_err("efivars: Subsystem registration failed.\n");
		goto err_remove_group;
	}

	if (efi_enabled(EFI_DBG) && efi_enabled(EFI_PRESERVE_BS_REGIONS))
		efi_debugfs_init();

#ifdef CONFIG_EFI_COCO_SECRET
	if (efi.coco_secret != EFI_INVALID_TABLE_ADDR)
		platform_device_register_simple("efi_secret", 0, NULL, 0);
#endif

	if (IS_ENABLED(CONFIG_OVMF_DEBUG_LOG) &&
	    efi.ovmf_debug_log != EFI_INVALID_TABLE_ADDR)
		ovmf_log_probe(efi.ovmf_debug_log);

	return 0;

err_remove_group:
	sysfs_remove_group(efi_kobj, &efi_subsys_attr_group);
err_unregister:
	if (efi_rt_services_supported(EFI_RT_SUPPORTED_GET_VARIABLE |
				      EFI_RT_SUPPORTED_GET_NEXT_VARIABLE_NAME))
		generic_ops_unregister();
err_put:
	kobject_put(efi_kobj);
	efi_kobj = NULL;
err_destroy_wq:
	if (efi_rts_wq)
		destroy_workqueue(efi_rts_wq);

	return error;
}

subsys_initcall(efisubsys_init);

void __init efi_find_mirror(void)
{
	efi_memory_desc_t *md;
	u64 mirror_size = 0, total_size = 0;

	if (!efi_enabled(EFI_MEMMAP))
		return;

	for_each_efi_memory_desc(md) {
		unsigned long long start = md->phys_addr;
		unsigned long long size = md->num_pages << EFI_PAGE_SHIFT;

		total_size += size;
		if (md->attribute & EFI_MEMORY_MORE_RELIABLE) {
			memblock_mark_mirror(start, size);
			mirror_size += size;
		}
	}
	if (mirror_size)
		pr_info("Memory: %lldM/%lldM mirrored memory\n",
			mirror_size>>20, total_size>>20);
}

/*
 * Find the efi memory descriptor for a given physical address.  Given a
 * physical address, determine if it exists within an EFI Memory Map entry,
 * and if so, populate the supplied memory descriptor with the appropriate
 * data.
 */
int __efi_mem_desc_lookup(u64 phys_addr, efi_memory_desc_t *out_md)
{
	efi_memory_desc_t *md;

	if (!efi_enabled(EFI_MEMMAP)) {
		pr_err_once("EFI_MEMMAP is not enabled.\n");
		return -EINVAL;
	}

	if (!out_md) {
		pr_err_once("out_md is null.\n");
		return -EINVAL;
        }

	for_each_efi_memory_desc(md) {
		u64 size;
		u64 end;

		/* skip bogus entries (including empty ones) */
		if ((md->phys_addr & (EFI_PAGE_SIZE - 1)) ||
		    (md->num_pages <= 0) ||
		    (md->num_pages > (U64_MAX - md->phys_addr) >> EFI_PAGE_SHIFT))
			continue;

		size = md->num_pages << EFI_PAGE_SHIFT;
		end = md->phys_addr + size;
		if (phys_addr >= md->phys_addr && phys_addr < end) {
			memcpy(out_md, md, sizeof(*out_md));
			return 0;
		}
	}
	return -ENOENT;
}

extern int efi_mem_desc_lookup(u64 phys_addr, efi_memory_desc_t *out_md)
	__weak __alias(__efi_mem_desc_lookup);
EXPORT_SYMBOL_GPL(efi_mem_desc_lookup);

/*
 * Calculate the highest address of an efi memory descriptor.
 */
u64 __init efi_mem_desc_end(efi_memory_desc_t *md)
{
	u64 size = md->num_pages << EFI_PAGE_SHIFT;
	u64 end = md->phys_addr + size;
	return end;
}

void __init __weak efi_arch_mem_reserve(phys_addr_t addr, u64 size) {}

/**
 * efi_mem_reserve - Reserve an EFI memory region
 * @addr: Physical address to reserve
 * @size: Size of reservation
 *
 * Mark a region as reserved from general kernel allocation and
 * prevent it being released by efi_free_boot_services().
 *
 * This function should be called drivers once they've parsed EFI
 * configuration tables to figure out where their data lives, e.g.
 * efi_esrt_init().
 */
void __init efi_mem_reserve(phys_addr_t addr, u64 size)
{
	/* efi_mem_reserve() does not work under Xen */
	if (WARN_ON_ONCE(efi_enabled(EFI_PARAVIRT)))
		return;

	if (!memblock_is_region_reserved(addr, size))
		memblock_reserve_kern(addr, size);
	else
		memblock_reserved_mark_kern(addr, size);

	/*
	 * Some architectures (x86) reserve all boot services ranges
	 * until efi_free_boot_services() because of buggy firmware
	 * implementations. This means the above memblock_reserve() is
	 * superfluous on x86 and instead what it needs to do is
	 * ensure the @start, @size is not freed.
	 */
	efi_arch_mem_reserve(addr, size);
}

static const efi_config_table_type_t common_tables[] __initconst = {
	{ACPI_20_TABLE_GUID,			&efi.acpi20,		"ACPI 2.0"	},
	{ACPI_TABLE_GUID,			&efi.acpi,		"ACPI"		},
	{SMBIOS_TABLE_GUID,			&efi.smbios,		"SMBIOS"	},
	{SMBIOS3_TABLE_GUID,			&efi.smbios3,		"SMBIOS 3.0"	},
	{EFI_SYSTEM_RESOURCE_TABLE_GUID,	&efi.esrt,		"ESRT"		},
	{EFI_MEMORY_ATTRIBUTES_TABLE_GUID,	&efi_mem_attr_table,	"MEMATTR"	},
	{LINUX_EFI_RANDOM_SEED_TABLE_GUID,	&efi_rng_seed,		"RNG"		},
	{LINUX_EFI_TPM_EVENT_LOG_GUID,		&efi.tpm_log,		"TPMEventLog"	},
	{EFI_TCG2_FINAL_EVENTS_TABLE_GUID,	&efi.tpm_final_log,	"TPMFinalLog"	},
	{EFI_CC_FINAL_EVENTS_TABLE_GUID,	&efi.tpm_final_log,	"CCFinalLog"	},
	{LINUX_EFI_MEMRESERVE_TABLE_GUID,	&mem_reserve,		"MEMRESERVE"	},
	{LINUX_EFI_INITRD_MEDIA_GUID,		&initrd,		"INITRD"	},
	{EFI_RT_PROPERTIES_TABLE_GUID,		&rt_prop,		"RTPROP"	},
#ifdef CONFIG_OVMF_DEBUG_LOG
	{OVMF_MEMORY_LOG_TABLE_GUID,		&efi.ovmf_debug_log,	"OvmfDebugLog"	},
#endif
#ifdef CONFIG_EFI_RCI2_TABLE
	{DELLEMC_EFI_RCI2_TABLE_GUID,		&rci2_table_phys			},
#endif
#ifdef CONFIG_LOAD_UEFI_KEYS
	{LINUX_EFI_MOK_VARIABLE_TABLE_GUID,	&efi.mokvar_table,	"MOKvar"	},
#endif
#ifdef CONFIG_EFI_COCO_SECRET
	{LINUX_EFI_COCO_SECRET_AREA_GUID,	&efi.coco_secret,	"CocoSecret"	},
#endif
#ifdef CONFIG_UNACCEPTED_MEMORY
	{LINUX_EFI_UNACCEPTED_MEM_TABLE_GUID,	&efi.unaccepted,	"Unaccepted"	},
#endif
#ifdef CONFIG_EFI_GENERIC_STUB
	{LINUX_EFI_PRIMARY_DISPLAY_TABLE_GUID,	&primary_display_table			},
#endif
	{},
};

static __init int match_config_table(const efi_guid_t *guid,
				     unsigned long table,
				     const efi_config_table_type_t *table_types)
{
	int i;

	for (i = 0; efi_guidcmp(table_types[i].guid, NULL_GUID); i++) {
		if (efi_guidcmp(*guid, table_types[i].guid))
			continue;

		if (!efi_config_table_is_usable(guid, table)) {
			if (table_types[i].name[0])
				pr_cont("(%s=0x%lx unusable) ",
					table_types[i].name, table);
			return 1;
		}

		*(table_types[i].ptr) = table;
		if (table_types[i].name[0])
			pr_cont("%s=0x%lx ", table_types[i].name, table);
		return 1;
	}

	return 0;
}

/**
 * reserve_unaccepted - Map and reserve unaccepted configuration table
 * @unaccepted: Pointer to unaccepted memory table
 *
 * memblock_add() makes sure that the table is mapped in direct mapping. During
 * normal boot it happens automatically because the table is allocated from
 * usable memory. But during crashkernel boot only memory specifically reserved
 * for crash scenario is mapped. memblock_add() forces the table to be mapped
 * in crashkernel case.
 *
 * Align the range to the nearest page borders. Ranges smaller than page size
 * are not going to be mapped.
 *
 * memblock_reserve() makes sure that future allocations will not touch the
 * table.
 */

static __init void reserve_unaccepted(struct efi_unaccepted_memory *unaccepted)
{
	phys_addr_t start, end;

	start = PAGE_ALIGN_DOWN(efi.unaccepted);
	end = PAGE_ALIGN(efi.unaccepted + sizeof(*unaccepted) + unaccepted->size);

	memblock_add(start, end - start);
	memblock_reserve(start, end - start);
}

int __init efi_config_parse_tables(const efi_config_table_t *config_tables,
				   int count,
				   const efi_config_table_type_t *arch_tables)
{
	const efi_config_table_64_t *tbl64 = (void *)config_tables;
	const efi_config_table_32_t *tbl32 = (void *)config_tables;
	const efi_guid_t *guid;
	unsigned long table;
	int i;

	pr_info("");
	for (i = 0; i < count; i++) {
		if (!IS_ENABLED(CONFIG_X86)) {
			guid = &config_tables[i].guid;
			table = (unsigned long)config_tables[i].table;
		} else if (efi_enabled(EFI_64BIT)) {
			guid = &tbl64[i].guid;
			table = tbl64[i].table;

			if (IS_ENABLED(CONFIG_X86_32) &&
			    tbl64[i].table > U32_MAX) {
				pr_cont("\n");
				pr_err("Table located above 4GB, disabling EFI.\n");
				return -EINVAL;
			}
		} else {
			guid = &tbl32[i].guid;
			table = tbl32[i].table;
		}

		if (!match_config_table(guid, table, common_tables) && arch_tables)
			match_config_table(guid, table, arch_tables);
	}
	pr_cont("\n");
	set_bit(EFI_CONFIG_TABLES, &efi.flags);

	if (efi_rng_seed != EFI_INVALID_TABLE_ADDR) {
		struct linux_efi_random_seed *seed;
		u32 size = 0;

		seed = early_memremap(efi_rng_seed, sizeof(*seed));
		if (seed != NULL) {
			size = min_t(u32, seed->size, SZ_1K); // sanity check
			early_memunmap(seed, sizeof(*seed));
		} else {
			pr_err("Could not map UEFI random seed!\n");
		}
		if (size > 0) {
			seed = early_memremap(efi_rng_seed,
					      sizeof(*seed) + size);
			if (seed != NULL) {
				add_bootloader_randomness(seed->bits, size);
				memzero_explicit(seed->bits, size);
				early_memunmap(seed, sizeof(*seed) + size);
			} else {
				pr_err("Could not map UEFI random seed!\n");
			}
		}
	}

	if (!IS_ENABLED(CONFIG_X86_32) && efi_enabled(EFI_MEMMAP))
		efi_memattr_init();

	efi_tpm_eventlog_init();

	if (mem_reserve != EFI_INVALID_TABLE_ADDR) {
		unsigned long prsv = mem_reserve;

		while (prsv) {
			struct linux_efi_memreserve *rsv;
			u8 *p;

			/*
			 * Just map a full page: that is what we will get
			 * anyway, and it permits us to map the entire entry
			 * before knowing its size.
			 */
			p = early_memremap(ALIGN_DOWN(prsv, PAGE_SIZE),
					   PAGE_SIZE);
			if (p == NULL) {
				pr_err("Could not map UEFI memreserve entry!\n");
				return -ENOMEM;
			}

			rsv = (void *)(p + prsv % PAGE_SIZE);

			/* reserve the entry itself */
			memblock_reserve(prsv,
					 struct_size(rsv, entry, rsv->size));

			for (i = 0; i < atomic_read(&rsv->count); i++) {
				memblock_reserve(rsv->entry[i].base,
						 rsv->entry[i].size);
			}

			prsv = rsv->next;
			early_memunmap(p, PAGE_SIZE);
		}
	}

	if (rt_prop != EFI_INVALID_TABLE_ADDR) {
		efi_rt_properties_table_t *tbl;

		tbl = early_memremap(rt_prop, sizeof(*tbl));
		if (tbl) {
			efi.runtime_supported_mask &= tbl->runtime_services_supported;
			early_memunmap(tbl, sizeof(*tbl));
		}
	}

	if (IS_ENABLED(CONFIG_BLK_DEV_INITRD) &&
	    initrd != EFI_INVALID_TABLE_ADDR && phys_initrd_size == 0) {
		struct linux_efi_initrd *tbl;

		tbl = early_memremap(initrd, sizeof(*tbl));
		if (tbl) {
			phys_initrd_start = tbl->base;
			phys_initrd_size = tbl->size;
			tbl->base = tbl->size = 0;
			early_memunmap(tbl, sizeof(*tbl));
		}
	}

	if (IS_ENABLED(CONFIG_UNACCEPTED_MEMORY) &&
	    efi.unaccepted != EFI_INVALID_TABLE_ADDR) {
		struct efi_unaccepted_memory *unaccepted;

		unaccepted = early_memremap(efi.unaccepted, sizeof(*unaccepted));
		if (unaccepted) {

			if (unaccepted->version == 1) {
				reserve_unaccepted(unaccepted);
			} else {
				efi.unaccepted = EFI_INVALID_TABLE_ADDR;
			}

			early_memunmap(unaccepted, sizeof(*unaccepted));
		}
	}

	return 0;
}

int __init efi_systab_check_header(const efi_table_hdr_t *systab_hdr)
{
	if (systab_hdr->signature != EFI_SYSTEM_TABLE_SIGNATURE) {
		pr_err("System table signature incorrect!\n");
		return -EINVAL;
	}

	return 0;
}

static const efi_char16_t *__init map_fw_vendor(unsigned long fw_vendor,
						size_t size)
{
	const efi_char16_t *ret;

	ret = early_memremap_ro(fw_vendor, size);
	if (!ret)
		pr_err("Could not map the firmware vendor!\n");
	return ret;
}

static void __init unmap_fw_vendor(const void *fw_vendor, size_t size)
{
	early_memunmap((void *)fw_vendor, size);
}

void __init efi_systab_report_header(const efi_table_hdr_t *systab_hdr,
				     unsigned long fw_vendor)
{
	char vendor[100] = "unknown";
	const efi_char16_t *c16;
	size_t i;
	u16 rev;

	c16 = map_fw_vendor(fw_vendor, sizeof(vendor) * sizeof(efi_char16_t));
	if (c16) {
		for (i = 0; i < sizeof(vendor) - 1 && c16[i]; ++i)
			vendor[i] = c16[i];
		vendor[i] = '\0';

		unmap_fw_vendor(c16, sizeof(vendor) * sizeof(efi_char16_t));
	}

	rev = (u16)systab_hdr->revision;
	pr_info("EFI v%u.%u", systab_hdr->revision >> 16, rev / 10);

	rev %= 10;
	if (rev)
		pr_cont(".%u", rev);

	pr_cont(" by %s\n", vendor);

	if (IS_ENABLED(CONFIG_X86_64) &&
	    systab_hdr->revision > EFI_1_10_SYSTEM_TABLE_REVISION &&
	    !strcmp(vendor, "Apple")) {
		pr_info("Apple Mac detected, using EFI v1.10 runtime services only\n");
		efi.runtime_version = EFI_1_10_SYSTEM_TABLE_REVISION;
	}
}

static __initdata char memory_type_name[][13] = {
	"Reserved",
	"Loader Code",
	"Loader Data",
	"Boot Code",
	"Boot Data",
	"Runtime Code",
	"Runtime Data",
	"Conventional",
	"Unusable",
	"ACPI Reclaim",
	"ACPI Mem NVS",
	"MMIO",
	"MMIO Port",
	"PAL Code",
	"Persistent",
	"Unaccepted",
};

char * __init efi_md_typeattr_format(char *buf, size_t size,
				     const efi_memory_desc_t *md)
{
	char *pos;
	int type_len;
	u64 attr;

	pos = buf;
	if (md->type >= ARRAY_SIZE(memory_type_name))
		type_len = snprintf(pos, size, "[type=%u", md->type);
	else
		type_len = snprintf(pos, size, "[%-*s",
				    (int)(sizeof(memory_type_name[0]) - 1),
				    memory_type_name[md->type]);
	if (type_len >= size)
		return buf;

	pos += type_len;
	size -= type_len;

	attr = md->attribute;
	if (attr & ~(EFI_MEMORY_UC | EFI_MEMORY_WC | EFI_MEMORY_WT |
		     EFI_MEMORY_WB | EFI_MEMORY_UCE | EFI_MEMORY_RO |
		     EFI_MEMORY_WP | EFI_MEMORY_RP | EFI_MEMORY_XP |
		     EFI_MEMORY_NV | EFI_MEMORY_SP | EFI_MEMORY_CPU_CRYPTO |
		     EFI_MEMORY_MORE_RELIABLE | EFI_MEMORY_HOT_PLUGGABLE |
		     EFI_MEMORY_RUNTIME))
		snprintf(pos, size, "|attr=0x%016llx]",
			 (unsigned long long)attr);
	else
		snprintf(pos, size,
			 "|%3s|%2s|%2s|%2s|%2s|%2s|%2s|%2s|%2s|%2s|%3s|%2s|%2s|%2s|%2s]",
			 attr & EFI_MEMORY_RUNTIME		? "RUN" : "",
			 attr & EFI_MEMORY_HOT_PLUGGABLE	? "HP"  : "",
			 attr & EFI_MEMORY_MORE_RELIABLE	? "MR"  : "",
			 attr & EFI_MEMORY_CPU_CRYPTO   	? "CC"  : "",
			 attr & EFI_MEMORY_SP			? "SP"  : "",
			 attr & EFI_MEMORY_NV			? "NV"  : "",
			 attr & EFI_MEMORY_XP			? "XP"  : "",
			 attr & EFI_MEMORY_RP			? "RP"  : "",
			 attr & EFI_MEMORY_WP			? "WP"  : "",
			 attr & EFI_MEMORY_RO			? "RO"  : "",
			 attr & EFI_MEMORY_UCE			? "UCE" : "",
			 attr & EFI_MEMORY_WB			? "WB"  : "",
			 attr & EFI_MEMORY_WT			? "WT"  : "",
			 attr & EFI_MEMORY_WC			? "WC"  : "",
			 attr & EFI_MEMORY_UC			? "UC"  : "");
	return buf;
}

/*
 * efi_mem_attributes - lookup memmap attributes for physical address
 * @phys_addr: the physical address to lookup
 *
 * Search in the EFI memory map for the region covering
 * @phys_addr. Returns the EFI memory attributes if the region
 * was found in the memory map, 0 otherwise.
 */
u64 efi_mem_attributes(unsigned long phys_addr)
{
	efi_memory_desc_t md;

	if (efi_mem_desc_lookup(phys_addr, &md))
		return 0;

	return md.attribute;
}

/*
 * efi_mem_type - lookup memmap type for physical address
 * @phys_addr: the physical address to lookup
 *
 * Search in the EFI memory map for the region covering @phys_addr.
 * Returns the EFI memory type if the region was found in the memory
 * map, -EINVAL otherwise.
 */
int efi_mem_type(unsigned long phys_addr)
{
	efi_memory_desc_t md;

	if (!efi_enabled(EFI_MEMMAP) && !efi_enabled(EFI_PARAVIRT))
		return -ENOTSUPP;

	if (efi_mem_desc_lookup(phys_addr, &md))
		return -EINVAL;

	return md.type;
}

int efi_status_to_err(efi_status_t status)
{
	int err;

	switch (status) {
	case EFI_SUCCESS:
		err = 0;
		break;
	case EFI_INVALID_PARAMETER:
		err = -EINVAL;
		break;
	case EFI_OUT_OF_RESOURCES:
		err = -ENOSPC;
		break;
	case EFI_DEVICE_ERROR:
		err = -EIO;
		break;
	case EFI_WRITE_PROTECTED:
		err = -EROFS;
		break;
	case EFI_SECURITY_VIOLATION:
		err = -EACCES;
		break;
	case EFI_NOT_FOUND:
		err = -ENOENT;
		break;
	case EFI_ABORTED:
		err = -EINTR;
		break;
	default:
		err = -EINVAL;
	}

	return err;
}
EXPORT_SYMBOL_GPL(efi_status_to_err);

static DEFINE_SPINLOCK(efi_mem_reserve_persistent_lock);
static struct linux_efi_memreserve *efi_memreserve_root __ro_after_init;

static int __init efi_memreserve_map_root(void)
{
	if (mem_reserve == EFI_INVALID_TABLE_ADDR)
		return -ENODEV;

	efi_memreserve_root = memremap(mem_reserve,
				       sizeof(*efi_memreserve_root),
				       MEMREMAP_WB);
	if (WARN_ON_ONCE(!efi_memreserve_root))
		return -ENOMEM;
	return 0;
}

static int efi_mem_reserve_iomem(phys_addr_t addr, u64 size)
{
	struct resource *res, *parent;
	int ret;

	res = kzalloc_obj(struct resource, GFP_ATOMIC);
	if (!res)
		return -ENOMEM;

	res->name	= "reserved";
	res->flags	= IORESOURCE_MEM;
	res->start	= addr;
	res->end	= addr + size - 1;

	/* we expect a conflict with a 'System RAM' region */
	parent = request_resource_conflict(&iomem_resource, res);
	ret = parent ? request_resource(parent, res) : 0;

	/*
	 * Given that efi_mem_reserve_iomem() can be called at any
	 * time, only call memblock_reserve() if the architecture
	 * keeps the infrastructure around.
	 */
	if (IS_ENABLED(CONFIG_ARCH_KEEP_MEMBLOCK) && !ret)
		memblock_reserve(addr, size);

	return ret;
}

int __ref efi_mem_reserve_persistent(phys_addr_t addr, u64 size)
{
	struct linux_efi_memreserve *rsv;
	unsigned long prsv;
	int rc, index;

	if (efi_memreserve_root == (void *)ULONG_MAX)
		return -ENODEV;

	if (!efi_memreserve_root) {
		rc = efi_memreserve_map_root();
		if (rc)
			return rc;
	}

	/* first try to find a slot in an existing linked list entry */
	for (prsv = efi_memreserve_root->next; prsv; ) {
		rsv = memremap(prsv, sizeof(*rsv), MEMREMAP_WB);
		if (!rsv)
			return -ENOMEM;
		index = atomic_fetch_add_unless(&rsv->count, 1, rsv->size);
		if (index < rsv->size) {
			rsv->entry[index].base = addr;
			rsv->entry[index].size = size;

			memunmap(rsv);
			return efi_mem_reserve_iomem(addr, size);
		}
		prsv = rsv->next;
		memunmap(rsv);
	}

	/* no slot found - allocate a new linked list entry */
	rsv = (struct linux_efi_memreserve *)__get_free_page(GFP_ATOMIC);
	if (!rsv)
		return -ENOMEM;

	rc = efi_mem_reserve_iomem(__pa(rsv), SZ_4K);
	if (rc) {
		free_page((unsigned long)rsv);
		return rc;
	}

	/*
	 * The memremap() call above assumes that a linux_efi_memreserve entry
	 * never crosses a page boundary, so let's ensure that this remains true
	 * even when kexec'ing a 4k pages kernel from a >4k pages kernel, by
	 * using SZ_4K explicitly in the size calculation below.
	 */
	rsv->size = EFI_MEMRESERVE_COUNT(SZ_4K);
	atomic_set(&rsv->count, 1);
	rsv->entry[0].base = addr;
	rsv->entry[0].size = size;

	spin_lock(&efi_mem_reserve_persistent_lock);
	rsv->next = efi_memreserve_root->next;
	efi_memreserve_root->next = __pa(rsv);
	spin_unlock(&efi_mem_reserve_persistent_lock);

	return efi_mem_reserve_iomem(addr, size);
}

static int __init efi_memreserve_root_init(void)
{
	if (efi_memreserve_root)
		return 0;
	if (efi_memreserve_map_root())
		efi_memreserve_root = (void *)ULONG_MAX;
	return 0;
}
early_initcall(efi_memreserve_root_init);

#ifdef CONFIG_KEXEC
static int update_efi_random_seed(struct notifier_block *nb,
				  unsigned long code, void *unused)
{
	struct linux_efi_random_seed *seed;
	u32 size = 0;

	if (!kexec_in_progress)
		return NOTIFY_DONE;

	seed = memremap(efi_rng_seed, sizeof(*seed), MEMREMAP_WB);
	if (seed != NULL) {
		size = min(seed->size, EFI_RANDOM_SEED_SIZE);
		memunmap(seed);
	} else {
		pr_err("Could not map UEFI random seed!\n");
	}
	if (size > 0) {
		seed = memremap(efi_rng_seed, sizeof(*seed) + size,
				MEMREMAP_WB);
		if (seed != NULL) {
			seed->size = size;
			get_random_bytes(seed->bits, seed->size);
			memunmap(seed);
		} else {
			pr_err("Could not map UEFI random seed!\n");
		}
	}
	return NOTIFY_DONE;
}

static struct notifier_block efi_random_seed_nb = {
	.notifier_call = update_efi_random_seed,
};

static int __init register_update_efi_random_seed(void)
{
	if (efi_rng_seed == EFI_INVALID_TABLE_ADDR)
		return 0;
	return register_reboot_notifier(&efi_random_seed_nb);
}
late_initcall(register_update_efi_random_seed);
#endif
