1d2912cb1SThomas Gleixner // SPDX-License-Identifier: GPL-2.0-only 2f84d0275SMark Salter /* 3f84d0275SMark Salter * Extensible Firmware Interface 4f84d0275SMark Salter * 5f84d0275SMark Salter * Based on Extensible Firmware Interface Specification version 2.4 6f84d0275SMark Salter * 7f84d0275SMark Salter * Copyright (C) 2013, 2014 Linaro Ltd. 8f84d0275SMark Salter */ 9f84d0275SMark Salter 10f84d0275SMark Salter #include <linux/efi.h> 11e5bc22a4SArd Biesheuvel #include <linux/init.h> 1246e27b99SWaiman Long #include <linux/kmemleak.h> 138b0d1354SThomas Zimmermann #include <linux/screen_info.h> 140069455bSKent Overstreet #include <linux/vmalloc.h> 15f84d0275SMark Salter 16f84d0275SMark Salter #include <asm/efi.h> 178a9a1a18SArd Biesheuvel #include <asm/stacktrace.h> 18d1ae8c00SYi Li 199b9eaee9SArd Biesheuvel static bool region_is_misaligned(const efi_memory_desc_t *md) 209b9eaee9SArd Biesheuvel { 219b9eaee9SArd Biesheuvel if (PAGE_SIZE == EFI_PAGE_SIZE) 229b9eaee9SArd Biesheuvel return false; 239b9eaee9SArd Biesheuvel return !PAGE_ALIGNED(md->phys_addr) || 249b9eaee9SArd Biesheuvel !PAGE_ALIGNED(md->num_pages << EFI_PAGE_SHIFT); 259b9eaee9SArd Biesheuvel } 269b9eaee9SArd Biesheuvel 27f7d92489SArd Biesheuvel /* 28f7d92489SArd Biesheuvel * Only regions of type EFI_RUNTIME_SERVICES_CODE need to be 29f7d92489SArd Biesheuvel * executable, everything else can be mapped with the XN bits 301fd55a9aSArd Biesheuvel * set. Also take the new (optional) RO/XP bits into account. 31f7d92489SArd Biesheuvel */ 321fd55a9aSArd Biesheuvel static __init pteval_t create_mapping_protection(efi_memory_desc_t *md) 331fd55a9aSArd Biesheuvel { 341fd55a9aSArd Biesheuvel u64 attr = md->attribute; 351fd55a9aSArd Biesheuvel u32 type = md->type; 361fd55a9aSArd Biesheuvel 37*491db21dSSuzuki K Poulose if (type == EFI_MEMORY_MAPPED_IO) { 38*491db21dSSuzuki K Poulose pgprot_t prot = __pgprot(PROT_DEVICE_nGnRE); 39*491db21dSSuzuki K Poulose 40*491db21dSSuzuki K Poulose if (arm64_is_protected_mmio(md->phys_addr, 41*491db21dSSuzuki K Poulose md->num_pages << EFI_PAGE_SHIFT)) 42*491db21dSSuzuki K Poulose prot = pgprot_encrypted(prot); 43*491db21dSSuzuki K Poulose else 44*491db21dSSuzuki K Poulose prot = pgprot_decrypted(prot); 45*491db21dSSuzuki K Poulose return pgprot_val(prot); 46*491db21dSSuzuki K Poulose } 471fd55a9aSArd Biesheuvel 489b9eaee9SArd Biesheuvel if (region_is_misaligned(md)) { 499b9eaee9SArd Biesheuvel static bool __initdata code_is_misaligned; 509b9eaee9SArd Biesheuvel 511fd55a9aSArd Biesheuvel /* 529b9eaee9SArd Biesheuvel * Regions that are not aligned to the OS page size cannot be 539b9eaee9SArd Biesheuvel * mapped with strict permissions, as those might interfere 549b9eaee9SArd Biesheuvel * with the permissions that are needed by the adjacent 559b9eaee9SArd Biesheuvel * region's mapping. However, if we haven't encountered any 569b9eaee9SArd Biesheuvel * misaligned runtime code regions so far, we can safely use 579b9eaee9SArd Biesheuvel * non-executable permissions for non-code regions. 581fd55a9aSArd Biesheuvel */ 599b9eaee9SArd Biesheuvel code_is_misaligned |= (type == EFI_RUNTIME_SERVICES_CODE); 609b9eaee9SArd Biesheuvel 619b9eaee9SArd Biesheuvel return code_is_misaligned ? pgprot_val(PAGE_KERNEL_EXEC) 629b9eaee9SArd Biesheuvel : pgprot_val(PAGE_KERNEL); 639b9eaee9SArd Biesheuvel } 641fd55a9aSArd Biesheuvel 651fd55a9aSArd Biesheuvel /* R-- */ 661fd55a9aSArd Biesheuvel if ((attr & (EFI_MEMORY_XP | EFI_MEMORY_RO)) == 671fd55a9aSArd Biesheuvel (EFI_MEMORY_XP | EFI_MEMORY_RO)) 681fd55a9aSArd Biesheuvel return pgprot_val(PAGE_KERNEL_RO); 691fd55a9aSArd Biesheuvel 701fd55a9aSArd Biesheuvel /* R-X */ 711fd55a9aSArd Biesheuvel if (attr & EFI_MEMORY_RO) 721fd55a9aSArd Biesheuvel return pgprot_val(PAGE_KERNEL_ROX); 731fd55a9aSArd Biesheuvel 741fd55a9aSArd Biesheuvel /* RW- */ 751e9de1d2SArd Biesheuvel if (((attr & (EFI_MEMORY_RP | EFI_MEMORY_WP | EFI_MEMORY_XP)) == 761e9de1d2SArd Biesheuvel EFI_MEMORY_XP) || 771e9de1d2SArd Biesheuvel type != EFI_RUNTIME_SERVICES_CODE) 781fd55a9aSArd Biesheuvel return pgprot_val(PAGE_KERNEL); 791fd55a9aSArd Biesheuvel 801fd55a9aSArd Biesheuvel /* RWX */ 811fd55a9aSArd Biesheuvel return pgprot_val(PAGE_KERNEL_EXEC); 821fd55a9aSArd Biesheuvel } 831fd55a9aSArd Biesheuvel 841fd55a9aSArd Biesheuvel int __init efi_create_mapping(struct mm_struct *mm, efi_memory_desc_t *md) 851fd55a9aSArd Biesheuvel { 861fd55a9aSArd Biesheuvel pteval_t prot_val = create_mapping_protection(md); 87f14c66ceSArd Biesheuvel bool page_mappings_only = (md->type == EFI_RUNTIME_SERVICES_CODE || 88f14c66ceSArd Biesheuvel md->type == EFI_RUNTIME_SERVICES_DATA); 89f7d92489SArd Biesheuvel 9074c102c9SArd Biesheuvel /* 919b9eaee9SArd Biesheuvel * If this region is not aligned to the page size used by the OS, the 929b9eaee9SArd Biesheuvel * mapping will be rounded outwards, and may end up sharing a page 939b9eaee9SArd Biesheuvel * frame with an adjacent runtime memory region. Given that the page 949b9eaee9SArd Biesheuvel * table descriptor covering the shared page will be rewritten when the 959b9eaee9SArd Biesheuvel * adjacent region gets mapped, we must avoid block mappings here so we 969b9eaee9SArd Biesheuvel * don't have to worry about splitting them when that happens. 9774c102c9SArd Biesheuvel */ 989b9eaee9SArd Biesheuvel if (region_is_misaligned(md)) 99f14c66ceSArd Biesheuvel page_mappings_only = true; 10074c102c9SArd Biesheuvel 101f7d92489SArd Biesheuvel create_pgd_mapping(mm, md->phys_addr, md->virt_addr, 102f7d92489SArd Biesheuvel md->num_pages << EFI_PAGE_SHIFT, 103f14c66ceSArd Biesheuvel __pgprot(prot_val | PTE_NG), page_mappings_only); 104f7d92489SArd Biesheuvel return 0; 105f7d92489SArd Biesheuvel } 106f7d92489SArd Biesheuvel 1071d959312SArd Biesheuvel struct set_perm_data { 1081d959312SArd Biesheuvel const efi_memory_desc_t *md; 1091d959312SArd Biesheuvel bool has_bti; 1101d959312SArd Biesheuvel }; 1111d959312SArd Biesheuvel 1128b1e0f81SAnshuman Khandual static int __init set_permissions(pte_t *ptep, unsigned long addr, void *data) 113bd264d04SArd Biesheuvel { 1141d959312SArd Biesheuvel struct set_perm_data *spd = data; 1151d959312SArd Biesheuvel const efi_memory_desc_t *md = spd->md; 1165a00bfd6SRyan Roberts pte_t pte = __ptep_get(ptep); 117bd264d04SArd Biesheuvel 118bd264d04SArd Biesheuvel if (md->attribute & EFI_MEMORY_RO) 119bd264d04SArd Biesheuvel pte = set_pte_bit(pte, __pgprot(PTE_RDONLY)); 120bd264d04SArd Biesheuvel if (md->attribute & EFI_MEMORY_XP) 121bd264d04SArd Biesheuvel pte = set_pte_bit(pte, __pgprot(PTE_PXN)); 122bbbb6577SMark Rutland else if (system_supports_bti_kernel() && spd->has_bti) 1231d959312SArd Biesheuvel pte = set_pte_bit(pte, __pgprot(PTE_GP)); 1245a00bfd6SRyan Roberts __set_pte(ptep, pte); 125bd264d04SArd Biesheuvel return 0; 126bd264d04SArd Biesheuvel } 127bd264d04SArd Biesheuvel 128bd264d04SArd Biesheuvel int __init efi_set_mapping_permissions(struct mm_struct *mm, 129cf1d2ffcSArd Biesheuvel efi_memory_desc_t *md, 130cf1d2ffcSArd Biesheuvel bool has_bti) 131bd264d04SArd Biesheuvel { 1321d959312SArd Biesheuvel struct set_perm_data data = { md, has_bti }; 1331d959312SArd Biesheuvel 134bd264d04SArd Biesheuvel BUG_ON(md->type != EFI_RUNTIME_SERVICES_CODE && 135bd264d04SArd Biesheuvel md->type != EFI_RUNTIME_SERVICES_DATA); 136bd264d04SArd Biesheuvel 1379b9eaee9SArd Biesheuvel if (region_is_misaligned(md)) 1389b9eaee9SArd Biesheuvel return 0; 1399b9eaee9SArd Biesheuvel 140bd264d04SArd Biesheuvel /* 141bd264d04SArd Biesheuvel * Calling apply_to_page_range() is only safe on regions that are 142bd264d04SArd Biesheuvel * guaranteed to be mapped down to pages. Since we are only called 143bd264d04SArd Biesheuvel * for regions that have been mapped using efi_create_mapping() above 144bd264d04SArd Biesheuvel * (and this is checked by the generic Memory Attributes table parsing 145bd264d04SArd Biesheuvel * routines), there is no need to check that again here. 146bd264d04SArd Biesheuvel */ 147bd264d04SArd Biesheuvel return apply_to_page_range(mm, md->virt_addr, 148bd264d04SArd Biesheuvel md->num_pages << EFI_PAGE_SHIFT, 1491d959312SArd Biesheuvel set_permissions, &data); 150bd264d04SArd Biesheuvel } 151bd264d04SArd Biesheuvel 15260c0d45aSArd Biesheuvel /* 15360c0d45aSArd Biesheuvel * UpdateCapsule() depends on the system being shutdown via 15460c0d45aSArd Biesheuvel * ResetSystem(). 15560c0d45aSArd Biesheuvel */ 15660c0d45aSArd Biesheuvel bool efi_poweroff_required(void) 15760c0d45aSArd Biesheuvel { 15860c0d45aSArd Biesheuvel return efi_enabled(EFI_RUNTIME_SERVICES); 15960c0d45aSArd Biesheuvel } 1607e611e7dSArd Biesheuvel 1617e611e7dSArd Biesheuvel asmlinkage efi_status_t efi_handle_corrupted_x18(efi_status_t s, const char *f) 1627e611e7dSArd Biesheuvel { 1637e611e7dSArd Biesheuvel pr_err_ratelimited(FW_BUG "register x18 corrupted by EFI %s\n", f); 1647e611e7dSArd Biesheuvel return s; 1657e611e7dSArd Biesheuvel } 166ff7a1679SArd Biesheuvel 167c37ce235SArd Biesheuvel static DEFINE_RAW_SPINLOCK(efi_rt_lock); 168c37ce235SArd Biesheuvel 169c37ce235SArd Biesheuvel void arch_efi_call_virt_setup(void) 170c37ce235SArd Biesheuvel { 171c37ce235SArd Biesheuvel efi_virtmap_load(); 172c37ce235SArd Biesheuvel __efi_fpsimd_begin(); 173c37ce235SArd Biesheuvel raw_spin_lock(&efi_rt_lock); 174c37ce235SArd Biesheuvel } 175c37ce235SArd Biesheuvel 176c37ce235SArd Biesheuvel void arch_efi_call_virt_teardown(void) 177c37ce235SArd Biesheuvel { 178c37ce235SArd Biesheuvel raw_spin_unlock(&efi_rt_lock); 179c37ce235SArd Biesheuvel __efi_fpsimd_end(); 180c37ce235SArd Biesheuvel efi_virtmap_unload(); 181c37ce235SArd Biesheuvel } 182ff7a1679SArd Biesheuvel 183ff7a1679SArd Biesheuvel asmlinkage u64 *efi_rt_stack_top __ro_after_init; 184ff7a1679SArd Biesheuvel 185e8dfdf31SArd Biesheuvel asmlinkage efi_status_t __efi_rt_asm_recover(void); 186e8dfdf31SArd Biesheuvel 187e8dfdf31SArd Biesheuvel bool efi_runtime_fixup_exception(struct pt_regs *regs, const char *msg) 188e8dfdf31SArd Biesheuvel { 189e8dfdf31SArd Biesheuvel /* Check whether the exception occurred while running the firmware */ 1908a9a1a18SArd Biesheuvel if (!current_in_efi() || regs->pc >= TASK_SIZE_64) 191e8dfdf31SArd Biesheuvel return false; 192e8dfdf31SArd Biesheuvel 193e8dfdf31SArd Biesheuvel pr_err(FW_BUG "Unable to handle %s in EFI runtime service\n", msg); 194e8dfdf31SArd Biesheuvel add_taint(TAINT_FIRMWARE_WORKAROUND, LOCKDEP_STILL_OK); 195e8dfdf31SArd Biesheuvel clear_bit(EFI_RUNTIME_SERVICES, &efi.flags); 196e8dfdf31SArd Biesheuvel 197e8dfdf31SArd Biesheuvel regs->regs[0] = EFI_ABORTED; 198e8dfdf31SArd Biesheuvel regs->regs[30] = efi_rt_stack_top[-1]; 199e8dfdf31SArd Biesheuvel regs->pc = (u64)__efi_rt_asm_recover; 200e8dfdf31SArd Biesheuvel 201e8dfdf31SArd Biesheuvel if (IS_ENABLED(CONFIG_SHADOW_CALL_STACK)) 202e8dfdf31SArd Biesheuvel regs->regs[18] = efi_rt_stack_top[-2]; 203e8dfdf31SArd Biesheuvel 204e8dfdf31SArd Biesheuvel return true; 205e8dfdf31SArd Biesheuvel } 206e8dfdf31SArd Biesheuvel 207ff7a1679SArd Biesheuvel /* EFI requires 8 KiB of stack space for runtime services */ 208ff7a1679SArd Biesheuvel static_assert(THREAD_SIZE >= SZ_8K); 209ff7a1679SArd Biesheuvel 210ff7a1679SArd Biesheuvel static int __init arm64_efi_rt_init(void) 211ff7a1679SArd Biesheuvel { 212ff7a1679SArd Biesheuvel void *p; 213ff7a1679SArd Biesheuvel 214ff7a1679SArd Biesheuvel if (!efi_enabled(EFI_RUNTIME_SERVICES)) 215ff7a1679SArd Biesheuvel return 0; 216ff7a1679SArd Biesheuvel 217ff7a1679SArd Biesheuvel p = __vmalloc_node(THREAD_SIZE, THREAD_ALIGN, GFP_KERNEL, 218ff7a1679SArd Biesheuvel NUMA_NO_NODE, &&l); 219ff7a1679SArd Biesheuvel l: if (!p) { 220ff7a1679SArd Biesheuvel pr_warn("Failed to allocate EFI runtime stack\n"); 221ff7a1679SArd Biesheuvel clear_bit(EFI_RUNTIME_SERVICES, &efi.flags); 222ff7a1679SArd Biesheuvel return -ENOMEM; 223ff7a1679SArd Biesheuvel } 224ff7a1679SArd Biesheuvel 22546e27b99SWaiman Long kmemleak_not_leak(p); 226ff7a1679SArd Biesheuvel efi_rt_stack_top = p + THREAD_SIZE; 227ff7a1679SArd Biesheuvel return 0; 228ff7a1679SArd Biesheuvel } 229ff7a1679SArd Biesheuvel core_initcall(arm64_efi_rt_init); 230