linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [GIT PULL 00/28] More EFI fixes for v5.7
@ 2020-03-08  8:08 Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 01/28] efi/x86: Add TPM related EFI tables to unencrypted mapping checks Ard Biesheuvel
                   ` (28 more replies)
  0 siblings, 29 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

The following changes since commit b9d8b63e340392d7f3ad79881f36a550566cbbbe:

  Merge tag 'stable-shared-branch-for-driver-tree' into HEAD (2020-03-05 09:58:20 +0100)

are available in the Git repository at:

  git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi.git tags/efi-next

for you to fetch changes up to dfb2a1c61fcdc8be5dd74608c411c78008a0f078:

  partitions/efi: Fix partition name parsing in GUID partition entry (2020-03-06 11:17:42 +0100)

----------------------------------------------------------------
More EFI updates for v5.7

- a fix for a boot regression in the IMA code on x86 booting without UEFI
- memory encryption fixes for x86, so that the TPM tables and the RNG
  config table created by the stub are correctly identified as living in
  unencrypted memory
- style tweak and doc update from Heinrich
- followup to the ARM EFI entry code simplifications to ensure that we
  don't rely on EFI_LOADER_DATA memory being RWX
- fixes from Arvind to ensure that the new mixed mode approach works as
  expected regardless of where the image is loaded in memory by the UEFI
  PE/COFF loader
- more fixes from Arvind to make it more likely that the image can be
  decompressed in place, regardless of where it was loaded in memory
- efivars bugfix and some cleanup from Vladis
- incorporate a stable branch with the EFI pieces of Hans's work on
  loading device firmware from EFI boot service memory regions
- some followup fixes for the EFI stub changes that are queued for
  v5.7 already
- an endianness fix for the EFI GPT partition table driver

----------------------------------------------------------------
Ard Biesheuvel (7):
      efi/arm: clean EFI stub exit code from cache instead of avoiding it
      efi/arm64: clean EFI stub exit code from cache instead of avoiding it
      efi: mark all EFI runtime services as unsupported on non-EFI boot
      efi/libstub/x86: deal with exit() boot service returning
      efi/x86: ignore memory attributes table on i386
      efi/x86: preserve %ebx correctly in efi_set_virtual_address_map()
      efi/libstub/x86: use ULONG_MAX as upper bound for all allocations

Arvind Sankar (11):
      efi/x86: Annotate the LOADED_IMAGE_PROTOCOL_GUID with SYM_DATA
      efi/x86: Respect 32-bit ABI in efi32_pe_entry
      efi/x86: Make efi32_pe_entry more readable
      efi/x86: Avoid using code32_start
      x86/boot: Use unsigned comparison for addresses
      x86/boot/compressed/32: Save the output address instead of recalculating it
      efi/x86: Decompress at start of PE image load address
      efi/x86: Add kernel preferred address to PE header
      efi/x86: Remove extra headroom for setup block
      efi/x86: Don't relocate the kernel unless necessary
      efi/x86: Fix cast of image argument

Heinrich Schuchardt (2):
      efi: don't shadow i in efi_config_parse_tables()
      efi/libstub: add libstub/mem.c to documentation tree

Lukas Bulwahn (1):
      MAINTAINERS: adjust EFI entry to removing eboot.c

Masahiro Yamada (1):
      efi/libstub: avoid linking libstub/lib-ksyms.o into vmlinux

Nikolai Merinov (1):
      partitions/efi: Fix partition name parsing in GUID partition entry

Tom Lendacky (2):
      efi/x86: Add TPM related EFI tables to unencrypted mapping checks
      efi/x86: Add RNG seed EFI table to unencrypted mapping check

Vladis Dronov (3):
      efi: fix a race and a buffer overflow while reading efivars via sysfs
      efi: add a sanity check to efivar_store_raw()
      efi: fix a mistype in comments mentioning efivar_entry_iter_begin()

 Documentation/driver-api/firmware/efi/index.rst |  11 +++
 Documentation/driver-api/firmware/index.rst     |   1 +
 MAINTAINERS                                     |   1 -
 arch/arm/boot/compressed/head.S                 |  18 ++--
 arch/arm64/kernel/efi-entry.S                   |  26 +++---
 arch/arm64/kernel/image-vars.h                  |   4 +-
 arch/x86/boot/compressed/head_32.S              |  47 ++++++----
 arch/x86/boot/compressed/head_64.S              | 112 +++++++++++++++++++-----
 arch/x86/boot/header.S                          |   6 +-
 arch/x86/boot/tools/build.c                     |  44 +++++++---
 arch/x86/kernel/asm-offsets.c                   |   1 -
 arch/x86/platform/efi/efi.c                     |   3 +
 arch/x86/platform/efi/efi_stub_32.S             |   2 +-
 block/partitions/efi.c                          |  35 ++++++--
 block/partitions/efi.h                          |   2 +-
 drivers/firmware/efi/Makefile                   |   2 +-
 drivers/firmware/efi/efi-pstore.c               |   2 +-
 drivers/firmware/efi/efi.c                      |  27 +++---
 drivers/firmware/efi/efivars.c                  |  32 +++++--
 drivers/firmware/efi/libstub/x86-stub.c         |  80 +++++++++++------
 drivers/firmware/efi/vars.c                     |   2 +-
 include/linux/efi.h                             |   2 +
 22 files changed, 319 insertions(+), 141 deletions(-)
 create mode 100644 Documentation/driver-api/firmware/efi/index.rst

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

* [PATCH 01/28] efi/x86: Add TPM related EFI tables to unencrypted mapping checks
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 02/28] efi/x86: Add RNG seed EFI table to unencrypted mapping check Ard Biesheuvel
                   ` (27 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Tom Lendacky <thomas.lendacky@amd.com>

When booting with SME active, EFI tables must be mapped unencrypted since
they were built by UEFI in unencrypted memory. Update the list of tables
to be checked during early_memremap() processing to account for the EFI
TPM tables.

This fixes a bug where an EFI TPM log table has been created by UEFI, but
it lives in memory that has been marked as usable rather than reserved.

Cc: <stable@vger.kernel.org> # v5.4+
Signed-off-by: Tom Lendacky <thomas.lendacky@amd.com>
Link: https://lore.kernel.org/r/4144cd813f113c20cdfa511cf59500a64e6015be.1582662842.git.thomas.lendacky@amd.com
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/platform/efi/efi.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/arch/x86/platform/efi/efi.c b/arch/x86/platform/efi/efi.c
index ebcec4bd273f..3ce695501681 100644
--- a/arch/x86/platform/efi/efi.c
+++ b/arch/x86/platform/efi/efi.c
@@ -88,6 +88,8 @@ static const unsigned long * const efi_tables[] = {
 #ifdef CONFIG_EFI_RCI2_TABLE
 	&rci2_table_phys,
 #endif
+	&efi.tpm_log,
+	&efi.tpm_final_log,
 };
 
 u64 efi_setup;		/* efi setup_data physical address */
-- 
2.17.1


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

* [PATCH 02/28] efi/x86: Add RNG seed EFI table to unencrypted mapping check
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 01/28] efi/x86: Add TPM related EFI tables to unencrypted mapping checks Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 03/28] efi: don't shadow i in efi_config_parse_tables() Ard Biesheuvel
                   ` (26 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Tom Lendacky <thomas.lendacky@amd.com>

When booting with SME active, EFI tables must be mapped unencrypted since
they were built by UEFI in unencrypted memory. Update the list of tables
to be checked during early_memremap() processing to account for the EFI
RNG seed table.

Signed-off-by: Tom Lendacky <thomas.lendacky@amd.com>
Link: https://lore.kernel.org/r/b64385fc13e5d7ad4b459216524f138e7879234f.1582662842.git.thomas.lendacky@amd.com
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/platform/efi/efi.c |  1 +
 drivers/firmware/efi/efi.c  | 18 ++++++++++--------
 include/linux/efi.h         |  2 ++
 3 files changed, 13 insertions(+), 8 deletions(-)

diff --git a/arch/x86/platform/efi/efi.c b/arch/x86/platform/efi/efi.c
index 3ce695501681..1aae5302501d 100644
--- a/arch/x86/platform/efi/efi.c
+++ b/arch/x86/platform/efi/efi.c
@@ -90,6 +90,7 @@ static const unsigned long * const efi_tables[] = {
 #endif
 	&efi.tpm_log,
 	&efi.tpm_final_log,
+	&efi_rng_seed,
 };
 
 u64 efi_setup;		/* efi setup_data physical address */
diff --git a/drivers/firmware/efi/efi.c b/drivers/firmware/efi/efi.c
index f3dda0c82187..5f77cb8756ef 100644
--- a/drivers/firmware/efi/efi.c
+++ b/drivers/firmware/efi/efi.c
@@ -46,7 +46,7 @@ struct efi __read_mostly efi = {
 };
 EXPORT_SYMBOL(efi);
 
-static unsigned long __ro_after_init rng_seed = EFI_INVALID_TABLE_ADDR;
+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;
 
@@ -508,7 +508,7 @@ static const efi_config_table_type_t common_tables[] __initconst = {
 	{SMBIOS3_TABLE_GUID, "SMBIOS 3.0", &efi.smbios3},
 	{EFI_SYSTEM_RESOURCE_TABLE_GUID, "ESRT", &efi.esrt},
 	{EFI_MEMORY_ATTRIBUTES_TABLE_GUID, "MEMATTR", &efi_mem_attr_table},
-	{LINUX_EFI_RANDOM_SEED_TABLE_GUID, "RNG", &rng_seed},
+	{LINUX_EFI_RANDOM_SEED_TABLE_GUID, "RNG", &efi_rng_seed},
 	{LINUX_EFI_TPM_EVENT_LOG_GUID, "TPMEventLog", &efi.tpm_log},
 	{LINUX_EFI_TPM_FINAL_LOG_GUID, "TPMFinalLog", &efi.tpm_final_log},
 	{LINUX_EFI_MEMRESERVE_TABLE_GUID, "MEMRESERVE", &mem_reserve},
@@ -576,11 +576,11 @@ int __init efi_config_parse_tables(const efi_config_table_t *config_tables,
 	pr_cont("\n");
 	set_bit(EFI_CONFIG_TABLES, &efi.flags);
 
-	if (rng_seed != EFI_INVALID_TABLE_ADDR) {
+	if (efi_rng_seed != EFI_INVALID_TABLE_ADDR) {
 		struct linux_efi_random_seed *seed;
 		u32 size = 0;
 
-		seed = early_memremap(rng_seed, sizeof(*seed));
+		seed = early_memremap(efi_rng_seed, sizeof(*seed));
 		if (seed != NULL) {
 			size = seed->size;
 			early_memunmap(seed, sizeof(*seed));
@@ -588,7 +588,8 @@ int __init efi_config_parse_tables(const efi_config_table_t *config_tables,
 			pr_err("Could not map UEFI random seed!\n");
 		}
 		if (size > 0) {
-			seed = early_memremap(rng_seed, sizeof(*seed) + size);
+			seed = early_memremap(efi_rng_seed,
+					      sizeof(*seed) + size);
 			if (seed != NULL) {
 				pr_notice("seeding entropy pool\n");
 				add_bootloader_randomness(seed->bits, seed->size);
@@ -980,7 +981,7 @@ static int update_efi_random_seed(struct notifier_block *nb,
 	if (!kexec_in_progress)
 		return NOTIFY_DONE;
 
-	seed = memremap(rng_seed, sizeof(*seed), MEMREMAP_WB);
+	seed = memremap(efi_rng_seed, sizeof(*seed), MEMREMAP_WB);
 	if (seed != NULL) {
 		size = min(seed->size, EFI_RANDOM_SEED_SIZE);
 		memunmap(seed);
@@ -988,7 +989,8 @@ static int update_efi_random_seed(struct notifier_block *nb,
 		pr_err("Could not map UEFI random seed!\n");
 	}
 	if (size > 0) {
-		seed = memremap(rng_seed, sizeof(*seed) + size, MEMREMAP_WB);
+		seed = memremap(efi_rng_seed, sizeof(*seed) + size,
+				MEMREMAP_WB);
 		if (seed != NULL) {
 			seed->size = size;
 			get_random_bytes(seed->bits, seed->size);
@@ -1006,7 +1008,7 @@ static struct notifier_block efi_random_seed_nb = {
 
 static int __init register_update_efi_random_seed(void)
 {
-	if (rng_seed == EFI_INVALID_TABLE_ADDR)
+	if (efi_rng_seed == EFI_INVALID_TABLE_ADDR)
 		return 0;
 	return register_reboot_notifier(&efi_random_seed_nb);
 }
diff --git a/include/linux/efi.h b/include/linux/efi.h
index 08186e0f98f1..abfc98e4dfe1 100644
--- a/include/linux/efi.h
+++ b/include/linux/efi.h
@@ -526,6 +526,8 @@ typedef struct {
 	efi_time_t time_of_revocation;
 } efi_cert_x509_sha256_t;
 
+extern unsigned long __ro_after_init efi_rng_seed;		/* RNG Seed table */
+
 /*
  * All runtime access to EFI goes through this structure:
  */
-- 
2.17.1


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

* [PATCH 03/28] efi: don't shadow i in efi_config_parse_tables()
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 01/28] efi/x86: Add TPM related EFI tables to unencrypted mapping checks Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 02/28] efi/x86: Add RNG seed EFI table to unencrypted mapping check Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 04/28] efi/arm: clean EFI stub exit code from cache instead of avoiding it Ard Biesheuvel
                   ` (25 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Heinrich Schuchardt <xypron.glpk@gmx.de>

Shadowing variables is generally frowned upon.

Let's simply reuse the existing loop counter i instead of shadowing it.

Signed-off-by: Heinrich Schuchardt <xypron.glpk@gmx.de>
Link: https://lore.kernel.org/r/20200223221324.156086-1-xypron.glpk@gmx.de
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/efi.c | 1 -
 1 file changed, 1 deletion(-)

diff --git a/drivers/firmware/efi/efi.c b/drivers/firmware/efi/efi.c
index 5f77cb8756ef..91f546dc13d4 100644
--- a/drivers/firmware/efi/efi.c
+++ b/drivers/firmware/efi/efi.c
@@ -611,7 +611,6 @@ int __init efi_config_parse_tables(const efi_config_table_t *config_tables,
 		while (prsv) {
 			struct linux_efi_memreserve *rsv;
 			u8 *p;
-			int i;
 
 			/*
 			 * Just map a full page: that is what we will get
-- 
2.17.1


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

* [PATCH 04/28] efi/arm: clean EFI stub exit code from cache instead of avoiding it
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (2 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 03/28] efi: don't shadow i in efi_config_parse_tables() Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 05/28] efi/arm64: " Ard Biesheuvel
                   ` (24 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

Commit c7225494b ("efi/arm: Work around missing cache maintenance in
decompressor handover") modified the handover code written in assembler
to work around the missing cache maintenance of the piece of code that
is executed after the MMU and caches are turned off. Due to the fact
that this sequence incorporates a subroutine call, cleaning that code
from the cache is not a matter of simply passing the start and end of
the currently running subroutine into cache_clean_flush(), which is why
instead, the code jumps across into the cleaned copy of the image.

However, this assumes that this copy is executable, and this means we
expect EFI_LOADER_DATA regions to be executable as well, which is not
a reasonable assumption to make, even if this is true for most UEFI
implementations today.

So change this back, and add a cache_clean_flush() call to cover the
remaining code in the subroutine, and any code it may execute in the
context of cache_off().

Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/arm/boot/compressed/head.S | 18 ++++++++----------
 1 file changed, 8 insertions(+), 10 deletions(-)

diff --git a/arch/arm/boot/compressed/head.S b/arch/arm/boot/compressed/head.S
index 36ffbeecd30b..04f77214f050 100644
--- a/arch/arm/boot/compressed/head.S
+++ b/arch/arm/boot/compressed/head.S
@@ -1452,13 +1452,11 @@ ENTRY(efi_enter_kernel)
 
 		@ The PE/COFF loader might not have cleaned the code we are
 		@ running beyond the PoU, and so calling cache_off below from
-		@ inside the PE/COFF loader allocated region is unsafe. Let's
-		@ assume our own zImage relocation code did a better job, and
-		@ jump into its version of this routine before proceeding.
-		ldr	r1, .Ljmp
-		sub	r1, r7, r1
-		mov	pc, r1				@ no mode switch
-0:
+		@ inside the PE/COFF loader allocated region is unsafe unless
+		@ we explicitly clean it to the PoC.
+		adr	r0, call_cache_fn		@ region of code we will
+		adr	r1, 0f				@ run with MMU off
+		bl	cache_clean_flush
 		bl	cache_off
 
 		@ Set parameters for booting zImage according to boot protocol
@@ -1467,10 +1465,10 @@ ENTRY(efi_enter_kernel)
 		mov	r0, #0
 		mov	r1, #0xFFFFFFFF
 		mov	r2, r4
-		b	__efi_start
+		add	r7, r7, #(__efi_start - start)
+		mov	pc, r7				@ no mode switch
 ENDPROC(efi_enter_kernel)
-		.align	2
-.Ljmp:		.long	start - 0b
+0:
 #endif
 
 		.align
-- 
2.17.1


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

* [PATCH 05/28] efi/arm64: clean EFI stub exit code from cache instead of avoiding it
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (3 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 04/28] efi/arm: clean EFI stub exit code from cache instead of avoiding it Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 06/28] efi: mark all EFI runtime services as unsupported on non-EFI boot Ard Biesheuvel
                   ` (23 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

Commit 9f9223778 ("efi/libstub/arm: Make efi_entry() an ordinary PE/COFF
entrypoint") modified the handover code written in assembler, and for
maintainability, aligned the logic with the logic used in the 32-bit ARM
version, which is to avoid cache maintenance on the remaining instructions
in the subroutine that will be executed with the MMU and caches off, and
instead, branch into the relocated copy of the kernel image.

However, this assumes that this copy is executable, and this means we
expect EFI_LOADER_DATA regions to be executable as well, which is not
a reasonable assumption to make, even if this is true for most UEFI
implementations today.

So change this back, and add a __clean_dcache_area_poc() call to cover
the remaining code in the subroutine. While at it, switch the other
call site over to __clean_dcache_area_poc() as well, and clean up the
terminology in comments to avoid using 'flush' in the context of cache
maintenance. Also, let's switch to the new style asm annotations.

Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/arm64/kernel/efi-entry.S  | 26 +++++++++++++-------------
 arch/arm64/kernel/image-vars.h |  4 ++--
 2 files changed, 15 insertions(+), 15 deletions(-)

diff --git a/arch/arm64/kernel/efi-entry.S b/arch/arm64/kernel/efi-entry.S
index 4cfd03c35c49..1a03618df0df 100644
--- a/arch/arm64/kernel/efi-entry.S
+++ b/arch/arm64/kernel/efi-entry.S
@@ -12,32 +12,32 @@
 
 	__INIT
 
-ENTRY(efi_enter_kernel)
+SYM_CODE_START(efi_enter_kernel)
 	/*
 	 * efi_entry() will have copied the kernel image if necessary and we
 	 * end up here with device tree address in x1 and the kernel entry
 	 * point stored in x0. Save those values in registers which are
 	 * callee preserved.
 	 */
-	mov	x19, x0			// relocated Image address
+	ldr	w2, =stext_offset
+	add	x19, x0, x2		// relocated Image entrypoint
 	mov	x20, x1			// DTB address
 
 	/*
-	 * Flush the copied Image to the PoC, and ensure it is not shadowed by
+	 * Clean the copied Image to the PoC, and ensure it is not shadowed by
 	 * stale icache entries from before relocation.
 	 */
 	ldr	w1, =kernel_size
-	bl	__flush_dcache_area
+	bl	__clean_dcache_area_poc
 	ic	ialluis
-	dsb	sy
 
 	/*
-	 * Jump across, into the copy of the image that we just cleaned
-	 * to the PoC, so that we can safely disable the MMU and caches.
+	 * Clean the remainder of this routine to the PoC
+	 * so that we can safely disable the MMU and caches.
 	 */
-	ldr	w0, .Ljmp
-	sub	x0, x19, w0, sxtw
-	br	x0
+	adr	x0, 0f
+	ldr	w1, 3f
+	bl	__clean_dcache_area_poc
 0:
 	/* Turn off Dcache and MMU */
 	mrs	x0, CurrentEL
@@ -63,6 +63,6 @@ ENTRY(efi_enter_kernel)
 	mov	x1, xzr
 	mov	x2, xzr
 	mov	x3, xzr
-	b	stext
-ENDPROC(efi_enter_kernel)
-.Ljmp:	.long	_text - 0b
+	br	x19
+SYM_CODE_END(efi_enter_kernel)
+3:	.long	. - 0b
diff --git a/arch/arm64/kernel/image-vars.h b/arch/arm64/kernel/image-vars.h
index 9a7aef0d6f70..7f06ad93fc95 100644
--- a/arch/arm64/kernel/image-vars.h
+++ b/arch/arm64/kernel/image-vars.h
@@ -13,6 +13,7 @@
 #ifdef CONFIG_EFI
 
 __efistub_kernel_size		= _edata - _text;
+__efistub_stext_offset		= stext - _text;
 
 
 /*
@@ -34,7 +35,7 @@ __efistub_strnlen		= __pi_strnlen;
 __efistub_strcmp		= __pi_strcmp;
 __efistub_strncmp		= __pi_strncmp;
 __efistub_strrchr		= __pi_strrchr;
-__efistub___flush_dcache_area	= __pi___flush_dcache_area;
+__efistub___clean_dcache_area_poc = __pi___clean_dcache_area_poc;
 
 #ifdef CONFIG_KASAN
 __efistub___memcpy		= __pi_memcpy;
@@ -43,7 +44,6 @@ __efistub___memset		= __pi_memset;
 #endif
 
 __efistub__text			= _text;
-__efistub_stext			= stext;
 __efistub__end			= _end;
 __efistub__edata		= _edata;
 __efistub_screen_info		= screen_info;
-- 
2.17.1


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

* [PATCH 06/28] efi: mark all EFI runtime services as unsupported on non-EFI boot
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (4 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 05/28] efi/arm64: " Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 07/28] MAINTAINERS: adjust EFI entry to removing eboot.c Ard Biesheuvel
                   ` (22 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

Recent changes to the way we deal with EFI runtime services that
are marked as unsupported by the firmware resulted in a regression
for non-EFI boot. The problem is that all EFI runtime services are
marked as available by default, and any non-NULL checks on the EFI
service function pointers (which will be non-NULL even for runtime
services that are unsupported on an EFI boot) were replaced with
checks against the mask stored in efi.runtime_supported_mask.

When doing a non-EFI boot, this check against the mask will return
a false positive, given the fact that all runtime services are
marked as enabled by default. Since we dropped the non-NULL check
of the runtime service function pointer in favor of the mask check,
we will now unconditionally dereference the function pointer, even
if it is NULL, and go boom.

So let's ensure that the mask reflects reality on a non-EFI boot,
which is that all EFI runtime services are unsupported.

Reported-by: David Hildenbrand <david@redhat.com>
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/efi.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/firmware/efi/efi.c b/drivers/firmware/efi/efi.c
index 91f546dc13d4..1d5e9a030cb1 100644
--- a/drivers/firmware/efi/efi.c
+++ b/drivers/firmware/efi/efi.c
@@ -354,12 +354,12 @@ static int __init efisubsys_init(void)
 {
 	int error;
 
-	if (!efi_enabled(EFI_BOOT))
-		return 0;
-
 	if (!efi_enabled(EFI_RUNTIME_SERVICES))
 		efi.runtime_supported_mask = 0;
 
+	if (!efi_enabled(EFI_BOOT))
+		return 0;
+
 	if (efi.runtime_supported_mask) {
 		/*
 		 * Since we process only one efi_runtime_service() at a time, an
-- 
2.17.1


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

* [PATCH 07/28] MAINTAINERS: adjust EFI entry to removing eboot.c
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (5 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 06/28] efi: mark all EFI runtime services as unsupported on non-EFI boot Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 08/28] efi/libstub: add libstub/mem.c to documentation tree Ard Biesheuvel
                   ` (21 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Lukas Bulwahn <lukas.bulwahn@gmail.com>

Commit c2d0b470154c ("efi/libstub/x86: Incorporate eboot.c into libstub")
removed arch/x86/boot/compressed/eboot.[ch], but missed to adjust the
MAINTAINERS entry.

Since then, ./scripts/get_maintainer.pl --self-test complains:

  warning: no file matches F: arch/x86/boot/compressed/eboot.[ch]

Rectify EXTENSIBLE FIRMWARE INTERFACE (EFI) entry in MAINTAINERS.

Signed-off-by: Lukas Bulwahn <lukas.bulwahn@gmail.com>
Link: https://lore.kernel.org/r/20200301155748.4788-1-lukas.bulwahn@gmail.com
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 MAINTAINERS | 1 -
 1 file changed, 1 deletion(-)

diff --git a/MAINTAINERS b/MAINTAINERS
index 8f27f40d22bb..5df99dab099f 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -6344,7 +6344,6 @@ T:	git git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi.git
 S:	Maintained
 F:	Documentation/admin-guide/efi-stub.rst
 F:	arch/*/kernel/efi.c
-F:	arch/x86/boot/compressed/eboot.[ch]
 F:	arch/*/include/asm/efi.h
 F:	arch/x86/platform/efi/
 F:	drivers/firmware/efi/
-- 
2.17.1


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

* [PATCH 08/28] efi/libstub: add libstub/mem.c to documentation tree
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (6 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 07/28] MAINTAINERS: adjust EFI entry to removing eboot.c Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 09/28] efi/x86: Annotate the LOADED_IMAGE_PROTOCOL_GUID with SYM_DATA Ard Biesheuvel
                   ` (20 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Heinrich Schuchardt <xypron.glpk@gmx.de>

Let the description of the efi/libstub/mem.c functions appear in the Kernel
API documentation in chapter

    The Linux driver implementer’s API guide
        Linux Firmware API
            UEFI Support
                UEFI stub library functions

Signed-off-by: Heinrich Schuchardt <xypron.glpk@gmx.de>
Acked-by: Jonathan Corbet <corbet@lwn.net>
Link: https://lore.kernel.org/r/20200221035832.144960-1-xypron.glpk@gmx.de
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 Documentation/driver-api/firmware/efi/index.rst | 11 +++++++++++
 Documentation/driver-api/firmware/index.rst     |  1 +
 2 files changed, 12 insertions(+)
 create mode 100644 Documentation/driver-api/firmware/efi/index.rst

diff --git a/Documentation/driver-api/firmware/efi/index.rst b/Documentation/driver-api/firmware/efi/index.rst
new file mode 100644
index 000000000000..4fe8abba9fc6
--- /dev/null
+++ b/Documentation/driver-api/firmware/efi/index.rst
@@ -0,0 +1,11 @@
+.. SPDX-License-Identifier: GPL-2.0
+
+============
+UEFI Support
+============
+
+UEFI stub library functions
+===========================
+
+.. kernel-doc:: drivers/firmware/efi/libstub/mem.c
+   :internal:
diff --git a/Documentation/driver-api/firmware/index.rst b/Documentation/driver-api/firmware/index.rst
index 29da39ec4b8a..57415d657173 100644
--- a/Documentation/driver-api/firmware/index.rst
+++ b/Documentation/driver-api/firmware/index.rst
@@ -6,6 +6,7 @@ Linux Firmware API
 
    introduction
    core
+   efi/index
    request_firmware
    other_interfaces
 
-- 
2.17.1


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

* [PATCH 09/28] efi/x86: Annotate the LOADED_IMAGE_PROTOCOL_GUID with SYM_DATA
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (7 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 08/28] efi/libstub: add libstub/mem.c to documentation tree Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 10/28] efi/x86: Respect 32-bit ABI in efi32_pe_entry Ard Biesheuvel
                   ` (19 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

Use SYM_DATA* macro to annotate this constant, and explicitly align it
to 4-byte boundary. Use lower-case for hexadecimal data.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200301230436.2246909-2-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/head_64.S | 9 ++++++---
 1 file changed, 6 insertions(+), 3 deletions(-)

diff --git a/arch/x86/boot/compressed/head_64.S b/arch/x86/boot/compressed/head_64.S
index f7bacc4c1494..86c97797bf78 100644
--- a/arch/x86/boot/compressed/head_64.S
+++ b/arch/x86/boot/compressed/head_64.S
@@ -672,7 +672,7 @@ SYM_FUNC_START(efi32_pe_entry)
 	/* Get the loaded image protocol pointer from the image handle */
 	subl	$12, %esp			// space for the loaded image pointer
 	pushl	%esp				// pass its address
-	leal	4f(%ebp), %eax
+	leal	loaded_image_proto(%ebp), %eax
 	pushl	%eax				// pass the GUID address
 	pushl	28(%esp)			// pass the image handle
 
@@ -695,9 +695,12 @@ SYM_FUNC_END(efi32_pe_entry)
 
 	.section ".rodata"
 	/* EFI loaded image protocol GUID */
-4:	.long	0x5B1B31A1
+	.balign 4
+SYM_DATA_START_LOCAL(loaded_image_proto)
+	.long	0x5b1b31a1
 	.word	0x9562, 0x11d2
-	.byte	0x8E, 0x3F, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B
+	.byte	0x8e, 0x3f, 0x00, 0xa0, 0xc9, 0x69, 0x72, 0x3b
+SYM_DATA_END(loaded_image_proto)
 #endif
 
 /*
-- 
2.17.1


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

* [PATCH 10/28] efi/x86: Respect 32-bit ABI in efi32_pe_entry
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (8 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 09/28] efi/x86: Annotate the LOADED_IMAGE_PROTOCOL_GUID with SYM_DATA Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 11/28] efi/x86: Make efi32_pe_entry more readable Ard Biesheuvel
                   ` (18 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

verify_cpu clobbers BX and DI. In case we have to return error, we need
to preserve them to respect 32-bit calling convention.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200301230436.2246909-3-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/head_64.S | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/arch/x86/boot/compressed/head_64.S b/arch/x86/boot/compressed/head_64.S
index 86c97797bf78..25fa763f4e83 100644
--- a/arch/x86/boot/compressed/head_64.S
+++ b/arch/x86/boot/compressed/head_64.S
@@ -660,7 +660,11 @@ SYM_DATA(efi_is64, .byte 1)
 SYM_FUNC_START(efi32_pe_entry)
 	pushl	%ebp
 
+	pushl	%ebx
+	pushl	%edi
 	call	verify_cpu			// check for long mode support
+	popl	%edi
+	popl	%ebx
 	testl	%eax, %eax
 	movl	$0x80000003, %eax		// EFI_UNSUPPORTED
 	jnz	3f
-- 
2.17.1


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

* [PATCH 11/28] efi/x86: Make efi32_pe_entry more readable
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (9 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 10/28] efi/x86: Respect 32-bit ABI in efi32_pe_entry Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 12/28] efi/x86: Avoid using code32_start Ard Biesheuvel
                   ` (17 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

Setup a proper frame pointer in efi32_pe_entry so that it's easier to
calculate offsets for arguments.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200301230436.2246909-4-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/head_64.S | 57 +++++++++++++++++++++---------
 1 file changed, 40 insertions(+), 17 deletions(-)

diff --git a/arch/x86/boot/compressed/head_64.S b/arch/x86/boot/compressed/head_64.S
index 25fa763f4e83..b74a012a6fea 100644
--- a/arch/x86/boot/compressed/head_64.S
+++ b/arch/x86/boot/compressed/head_64.S
@@ -658,42 +658,65 @@ SYM_DATA(efi_is64, .byte 1)
 	.text
 	.code32
 SYM_FUNC_START(efi32_pe_entry)
+/*
+ * efi_status_t efi32_pe_entry(efi_handle_t image_handle,
+ *			       efi_system_table_32_t *sys_table)
+ */
+
 	pushl	%ebp
+	movl	%esp, %ebp
+	pushl	%eax				// dummy push to allocate loaded_image
 
-	pushl	%ebx
+	pushl	%ebx				// save callee-save registers
 	pushl	%edi
+
 	call	verify_cpu			// check for long mode support
-	popl	%edi
-	popl	%ebx
 	testl	%eax, %eax
 	movl	$0x80000003, %eax		// EFI_UNSUPPORTED
-	jnz	3f
+	jnz	2f
 
 	call	1f
-1:	pop	%ebp
-	subl	$1b, %ebp
+1:	pop	%ebx
+	subl	$1b, %ebx
 
 	/* Get the loaded image protocol pointer from the image handle */
-	subl	$12, %esp			// space for the loaded image pointer
-	pushl	%esp				// pass its address
-	leal	loaded_image_proto(%ebp), %eax
+	leal	-4(%ebp), %eax
+	pushl	%eax				// &loaded_image
+	leal	loaded_image_proto(%ebx), %eax
 	pushl	%eax				// pass the GUID address
-	pushl	28(%esp)			// pass the image handle
+	pushl	8(%ebp)				// pass the image handle
 
-	movl	36(%esp), %eax			// sys_table
+	/*
+	 * Note the alignment of the stack frame.
+	 *   sys_table
+	 *   handle             <-- 16-byte aligned on entry by ABI
+	 *   return address
+	 *   frame pointer
+	 *   loaded_image       <-- local variable
+	 *   saved %ebx		<-- 16-byte aligned here
+	 *   saved %edi
+	 *   &loaded_image
+	 *   &loaded_image_proto
+	 *   handle             <-- 16-byte aligned for call to handle_protocol
+	 */
+
+	movl	12(%ebp), %eax			// sys_table
 	movl	ST32_boottime(%eax), %eax	// sys_table->boottime
 	call	*BS32_handle_protocol(%eax)	// sys_table->boottime->handle_protocol
-	cmp	$0, %eax
+	addl	$12, %esp			// restore argument space
+	testl	%eax, %eax
 	jnz	2f
 
-	movl	32(%esp), %ecx			// image_handle
-	movl	36(%esp), %edx			// sys_table
-	movl	12(%esp), %esi			// loaded_image
+	movl	8(%ebp), %ecx			// image_handle
+	movl	12(%ebp), %edx			// sys_table
+	movl	-4(%ebp), %esi			// loaded_image
 	movl	LI32_image_base(%esi), %esi	// loaded_image->image_base
+	movl	%ebx, %ebp			// startup_32 for efi32_pe_stub_entry
 	jmp	efi32_pe_stub_entry
 
-2:	addl	$24, %esp
-3:	popl	%ebp
+2:	popl	%edi				// restore callee-save registers
+	popl	%ebx
+	leave
 	ret
 SYM_FUNC_END(efi32_pe_entry)
 
-- 
2.17.1


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

* [PATCH 12/28] efi/x86: Avoid using code32_start
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (10 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 11/28] efi/x86: Make efi32_pe_entry more readable Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 13/28] x86/boot: Use unsigned comparison for addresses Ard Biesheuvel
                   ` (16 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

code32_start is meant for 16-bit real-mode bootloaders to inform the
kernel where the 32-bit protected mode code starts. Nothing in the
protected mode kernel except the EFI stub uses it.

efi_main currently returns boot_params, with code32_start set inside it
to tell efi_stub_entry where startup_32 is located. Since it was invoked
by efi_stub_entry in the first place, boot_params is already known.
Return the address of startup_32 instead.

This will allow a 64-bit kernel to live above 4Gb, for example, and it's
cleaner.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200301230436.2246909-5-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/head_32.S      |  3 +--
 arch/x86/boot/compressed/head_64.S      |  4 ++--
 arch/x86/kernel/asm-offsets.c           |  1 -
 drivers/firmware/efi/libstub/x86-stub.c | 10 +++++-----
 4 files changed, 8 insertions(+), 10 deletions(-)

diff --git a/arch/x86/boot/compressed/head_32.S b/arch/x86/boot/compressed/head_32.S
index 356060c5332c..9ffc9454fd22 100644
--- a/arch/x86/boot/compressed/head_32.S
+++ b/arch/x86/boot/compressed/head_32.S
@@ -157,9 +157,8 @@ SYM_FUNC_END(startup_32)
 SYM_FUNC_START(efi32_stub_entry)
 SYM_FUNC_START_ALIAS(efi_stub_entry)
 	add	$0x4, %esp
+	movl	8(%esp), %esi	/* save boot_params pointer */
 	call	efi_main
-	movl	%eax, %esi
-	movl	BP_code32_start(%esi), %eax
 	leal	startup_32(%eax), %eax
 	jmp	*%eax
 SYM_FUNC_END(efi32_stub_entry)
diff --git a/arch/x86/boot/compressed/head_64.S b/arch/x86/boot/compressed/head_64.S
index b74a012a6fea..08351d16ccc0 100644
--- a/arch/x86/boot/compressed/head_64.S
+++ b/arch/x86/boot/compressed/head_64.S
@@ -472,9 +472,9 @@ SYM_CODE_END(startup_64)
 SYM_FUNC_START(efi64_stub_entry)
 SYM_FUNC_START_ALIAS(efi_stub_entry)
 	and	$~0xf, %rsp			/* realign the stack */
+	movq	%rdx, %rbx			/* save boot_params pointer */
 	call	efi_main
-	movq	%rax,%rsi
-	movl	BP_code32_start(%esi), %eax
+	movq	%rbx,%rsi
 	leaq	startup_64(%rax), %rax
 	jmp	*%rax
 SYM_FUNC_END(efi64_stub_entry)
diff --git a/arch/x86/kernel/asm-offsets.c b/arch/x86/kernel/asm-offsets.c
index 5c7ee3df4d0b..3ca07ad552ae 100644
--- a/arch/x86/kernel/asm-offsets.c
+++ b/arch/x86/kernel/asm-offsets.c
@@ -88,7 +88,6 @@ static void __used common(void)
 	OFFSET(BP_kernel_alignment, boot_params, hdr.kernel_alignment);
 	OFFSET(BP_init_size, boot_params, hdr.init_size);
 	OFFSET(BP_pref_address, boot_params, hdr.pref_address);
-	OFFSET(BP_code32_start, boot_params, hdr.code32_start);
 
 	BLANK();
 	DEFINE(PTREGS_SIZE, sizeof(struct pt_regs));
diff --git a/drivers/firmware/efi/libstub/x86-stub.c b/drivers/firmware/efi/libstub/x86-stub.c
index 9db98839d7b4..7f3e97c2aad3 100644
--- a/drivers/firmware/efi/libstub/x86-stub.c
+++ b/drivers/firmware/efi/libstub/x86-stub.c
@@ -703,10 +703,11 @@ static efi_status_t exit_boot(struct boot_params *boot_params, void *handle)
 }
 
 /*
- * On success we return a pointer to a boot_params structure, and NULL
- * on failure.
+ * On success, we return the address of startup_32, which has potentially been
+ * relocated by efi_relocate_kernel.
+ * On failure, we exit to the firmware via efi_exit instead of returning.
  */
-struct boot_params *efi_main(efi_handle_t handle,
+unsigned long efi_main(efi_handle_t handle,
 			     efi_system_table_t *sys_table_arg,
 			     struct boot_params *boot_params)
 {
@@ -736,7 +737,6 @@ struct boot_params *efi_main(efi_handle_t handle,
 			goto fail;
 		}
 	}
-	hdr->code32_start = (u32)bzimage_addr;
 
 	/*
 	 * efi_pe_entry() may have been called before efi_main(), in which
@@ -799,7 +799,7 @@ struct boot_params *efi_main(efi_handle_t handle,
 		goto fail;
 	}
 
-	return boot_params;
+	return bzimage_addr;
 fail:
 	efi_printk("efi_main() failed!\n");
 
-- 
2.17.1


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

* [PATCH 13/28] x86/boot: Use unsigned comparison for addresses
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (11 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 12/28] efi/x86: Avoid using code32_start Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 14/28] efi/libstub/x86: deal with exit() boot service returning Ard Biesheuvel
                   ` (15 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

The load address is compared with LOAD_PHYSICAL_ADDR using a signed
comparison currently (using jge instruction).

When loading a 64-bit kernel using the new efi32_pe_entry point added by
commit 97aa276579b2 ("efi/x86: Add true mixed mode entry point into
.compat section") using qemu with -m 3072, the firmware actually loads
us above 2Gb, resulting in a very early crash.

Use jae instruction to perform unsigned comparison instead, as physical
addresses should be considered as unsigned.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200301230436.2246909-6-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/head_32.S | 2 +-
 arch/x86/boot/compressed/head_64.S | 4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/arch/x86/boot/compressed/head_32.S b/arch/x86/boot/compressed/head_32.S
index 9ffc9454fd22..f250fc49cd61 100644
--- a/arch/x86/boot/compressed/head_32.S
+++ b/arch/x86/boot/compressed/head_32.S
@@ -105,7 +105,7 @@ SYM_FUNC_START(startup_32)
 	notl	%eax
 	andl    %eax, %ebx
 	cmpl	$LOAD_PHYSICAL_ADDR, %ebx
-	jge	1f
+	jae	1f
 #endif
 	movl	$LOAD_PHYSICAL_ADDR, %ebx
 1:
diff --git a/arch/x86/boot/compressed/head_64.S b/arch/x86/boot/compressed/head_64.S
index 08351d16ccc0..1199c4ef0c83 100644
--- a/arch/x86/boot/compressed/head_64.S
+++ b/arch/x86/boot/compressed/head_64.S
@@ -105,7 +105,7 @@ SYM_FUNC_START(startup_32)
 	notl	%eax
 	andl	%eax, %ebx
 	cmpl	$LOAD_PHYSICAL_ADDR, %ebx
-	jge	1f
+	jae	1f
 #endif
 	movl	$LOAD_PHYSICAL_ADDR, %ebx
 1:
@@ -305,7 +305,7 @@ SYM_CODE_START(startup_64)
 	notq	%rax
 	andq	%rax, %rbp
 	cmpq	$LOAD_PHYSICAL_ADDR, %rbp
-	jge	1f
+	jae	1f
 #endif
 	movq	$LOAD_PHYSICAL_ADDR, %rbp
 1:
-- 
2.17.1


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

* [PATCH 14/28] efi/libstub/x86: deal with exit() boot service returning
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (12 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 13/28] x86/boot: Use unsigned comparison for addresses Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 15/28] x86/boot/compressed/32: Save the output address instead of recalculating it Ard Biesheuvel
                   ` (14 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

Even though it is uncommon, there are cases where the Exit() EFI boot
service might return, e.g., when we were booted via the EFI handover
protocol from OVMF and the kernel image was specified on the command
line, in which case Exit() attempts to terminate the boot manager,
which is not an EFI application itself. So let's drop into a deadloop
instead.

Tested-by: Nathan Chancellor <natechancellor@gmail.com> # build
Link: https://lore.kernel.org/r/20200303080648.21427-1-ardb@kernel.org
[ardb: put 'hlt' in deadloop]
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/libstub/x86-stub.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/firmware/efi/libstub/x86-stub.c b/drivers/firmware/efi/libstub/x86-stub.c
index 7f3e97c2aad3..69a942f0640b 100644
--- a/drivers/firmware/efi/libstub/x86-stub.c
+++ b/drivers/firmware/efi/libstub/x86-stub.c
@@ -344,7 +344,8 @@ static void setup_graphics(struct boot_params *boot_params)
 static void __noreturn efi_exit(efi_handle_t handle, efi_status_t status)
 {
 	efi_bs_call(exit, handle, status, 0, NULL);
-	unreachable();
+	for(;;)
+		asm("hlt");
 }
 
 void startup_32(struct boot_params *boot_params);
-- 
2.17.1


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

* [PATCH 15/28] x86/boot/compressed/32: Save the output address instead of recalculating it
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (13 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 14/28] efi/libstub/x86: deal with exit() boot service returning Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 16/28] efi/x86: Decompress at start of PE image load address Ard Biesheuvel
                   ` (13 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

In preparation for being able to decompress into a buffer starting at a
different address than startup_32, save the calculated output address
instead of recalculating it later.

We now keep track of three addresses:
	%edx: startup_32 as we were loaded by bootloader
	%ebx: new location of compressed kernel
	%ebp: start of decompression buffer

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200303221205.4048668-2-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/head_32.S | 25 ++++++++++++-------------
 1 file changed, 12 insertions(+), 13 deletions(-)

diff --git a/arch/x86/boot/compressed/head_32.S b/arch/x86/boot/compressed/head_32.S
index f250fc49cd61..2a8965aec234 100644
--- a/arch/x86/boot/compressed/head_32.S
+++ b/arch/x86/boot/compressed/head_32.S
@@ -75,11 +75,11 @@ SYM_FUNC_START(startup_32)
  */
 	leal	(BP_scratch+4)(%esi), %esp
 	call	1f
-1:	popl	%ebp
-	subl	$1b, %ebp
+1:	popl	%edx
+	subl	$1b, %edx
 
 	/* Load new GDT */
-	leal	gdt(%ebp), %eax
+	leal	gdt(%edx), %eax
 	movl	%eax, 2(%eax)
 	lgdt	(%eax)
 
@@ -92,13 +92,14 @@ SYM_FUNC_START(startup_32)
 	movl	%eax, %ss
 
 /*
- * %ebp contains the address we are loaded at by the boot loader and %ebx
+ * %edx contains the address we are loaded at by the boot loader and %ebx
  * contains the address where we should move the kernel image temporarily
- * for safe in-place decompression.
+ * for safe in-place decompression. %ebp contains the address that the kernel
+ * will be decompressed to.
  */
 
 #ifdef CONFIG_RELOCATABLE
-	movl	%ebp, %ebx
+	movl	%edx, %ebx
 	movl	BP_kernel_alignment(%esi), %eax
 	decl	%eax
 	addl    %eax, %ebx
@@ -110,10 +111,10 @@ SYM_FUNC_START(startup_32)
 	movl	$LOAD_PHYSICAL_ADDR, %ebx
 1:
 
+	movl	%ebx, %ebp	// Save the output address for later
 	/* Target address to relocate to for decompression */
-	movl    BP_init_size(%esi), %eax
-	subl    $_end, %eax
-	addl    %eax, %ebx
+	addl    BP_init_size(%esi), %ebx
+	subl    $_end, %ebx
 
 	/* Set up the stack */
 	leal	boot_stack_end(%ebx), %esp
@@ -127,7 +128,7 @@ SYM_FUNC_START(startup_32)
  * where decompression in place becomes safe.
  */
 	pushl	%esi
-	leal	(_bss-4)(%ebp), %esi
+	leal	(_bss-4)(%edx), %esi
 	leal	(_bss-4)(%ebx), %edi
 	movl	$(_bss - startup_32), %ecx
 	shrl	$2, %ecx
@@ -197,9 +198,7 @@ SYM_FUNC_START_LOCAL_NOALIGN(.Lrelocated)
 				/* push arguments for extract_kernel: */
 	pushl	$z_output_len	/* decompressed length, end of relocs */
 
-	leal	_end(%ebx), %eax
-	subl    BP_init_size(%esi), %eax
-	pushl	%eax		/* output address */
+	pushl	%ebp		/* output address */
 
 	pushl	$z_input_len	/* input_len */
 	leal	input_data(%ebx), %eax
-- 
2.17.1


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

* [PATCH 16/28] efi/x86: Decompress at start of PE image load address
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (14 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 15/28] x86/boot/compressed/32: Save the output address instead of recalculating it Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 17/28] efi/x86: Add kernel preferred address to PE header Ard Biesheuvel
                   ` (12 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

When booted via PE loader, define image_offset to hold the offset of
startup_32 from the start of the PE image, and use it as the start of
the decompression buffer.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200303221205.4048668-3-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/head_32.S      | 17 ++++++++++
 arch/x86/boot/compressed/head_64.S      | 42 +++++++++++++++++++++++--
 drivers/firmware/efi/libstub/x86-stub.c | 17 ++++++++--
 3 files changed, 70 insertions(+), 6 deletions(-)

diff --git a/arch/x86/boot/compressed/head_32.S b/arch/x86/boot/compressed/head_32.S
index 2a8965aec234..f7b52ccaa4ee 100644
--- a/arch/x86/boot/compressed/head_32.S
+++ b/arch/x86/boot/compressed/head_32.S
@@ -100,6 +100,19 @@ SYM_FUNC_START(startup_32)
 
 #ifdef CONFIG_RELOCATABLE
 	movl	%edx, %ebx
+
+#ifdef CONFIG_EFI_STUB
+/*
+ * If we were loaded via the EFI LoadImage service, startup_32 will be at an
+ * offset to the start of the space allocated for the image. efi_pe_entry will
+ * setup image_offset to tell us where the image actually starts, so that we
+ * can use the full available buffer.
+ *	image_offset = startup_32 - image_base
+ * Otherwise image_offset will be zero and have no effect on the calculations.
+ */
+	subl    image_offset(%edx), %ebx
+#endif
+
 	movl	BP_kernel_alignment(%esi), %eax
 	decl	%eax
 	addl    %eax, %ebx
@@ -227,6 +240,10 @@ SYM_DATA_START_LOCAL(gdt)
 	.quad	0x00cf92000000ffff	/* __KERNEL_DS */
 SYM_DATA_END_LABEL(gdt, SYM_L_LOCAL, gdt_end)
 
+#ifdef CONFIG_EFI_STUB
+SYM_DATA(image_offset, .long 0)
+#endif
+
 /*
  * Stack and heap for uncompression
  */
diff --git a/arch/x86/boot/compressed/head_64.S b/arch/x86/boot/compressed/head_64.S
index 1199c4ef0c83..4d4b4763a770 100644
--- a/arch/x86/boot/compressed/head_64.S
+++ b/arch/x86/boot/compressed/head_64.S
@@ -99,6 +99,19 @@ SYM_FUNC_START(startup_32)
 
 #ifdef CONFIG_RELOCATABLE
 	movl	%ebp, %ebx
+
+#ifdef CONFIG_EFI_STUB
+/*
+ * If we were loaded via the EFI LoadImage service, startup_32 will be at an
+ * offset to the start of the space allocated for the image. efi_pe_entry will
+ * setup image_offset to tell us where the image actually starts, so that we
+ * can use the full available buffer.
+ *	image_offset = startup_32 - image_base
+ * Otherwise image_offset will be zero and have no effect on the calculations.
+ */
+	subl    image_offset(%ebp), %ebx
+#endif
+
 	movl	BP_kernel_alignment(%esi), %eax
 	decl	%eax
 	addl	%eax, %ebx
@@ -111,9 +124,8 @@ SYM_FUNC_START(startup_32)
 1:
 
 	/* Target address to relocate to for decompression */
-	movl	BP_init_size(%esi), %eax
-	subl	$_end, %eax
-	addl	%eax, %ebx
+	addl	BP_init_size(%esi), %ebx
+	subl	$_end, %ebx
 
 /*
  * Prepare for entering 64 bit mode
@@ -299,6 +311,20 @@ SYM_CODE_START(startup_64)
 	/* Start with the delta to where the kernel will run at. */
 #ifdef CONFIG_RELOCATABLE
 	leaq	startup_32(%rip) /* - $startup_32 */, %rbp
+
+#ifdef CONFIG_EFI_STUB
+/*
+ * If we were loaded via the EFI LoadImage service, startup_32 will be at an
+ * offset to the start of the space allocated for the image. efi_pe_entry will
+ * setup image_offset to tell us where the image actually starts, so that we
+ * can use the full available buffer.
+ *	image_offset = startup_32 - image_base
+ * Otherwise image_offset will be zero and have no effect on the calculations.
+ */
+	movl    image_offset(%rip), %eax
+	subq	%rax, %rbp
+#endif
+
 	movl	BP_kernel_alignment(%rsi), %eax
 	decl	%eax
 	addq	%rax, %rbp
@@ -647,6 +673,10 @@ SYM_DATA_START_LOCAL(gdt)
 	.quad   0x0000000000000000	/* TS continued */
 SYM_DATA_END_LABEL(gdt, SYM_L_LOCAL, gdt_end)
 
+#ifdef CONFIG_EFI_STUB
+SYM_DATA(image_offset, .long 0)
+#endif
+
 #ifdef CONFIG_EFI_MIXED
 SYM_DATA_LOCAL(efi32_boot_args, .long 0, 0, 0)
 SYM_DATA(efi_is64, .byte 1)
@@ -712,6 +742,12 @@ SYM_FUNC_START(efi32_pe_entry)
 	movl	-4(%ebp), %esi			// loaded_image
 	movl	LI32_image_base(%esi), %esi	// loaded_image->image_base
 	movl	%ebx, %ebp			// startup_32 for efi32_pe_stub_entry
+	/*
+	 * We need to set the image_offset variable here since startup_32 will
+	 * use it before we get to the 64-bit efi_pe_entry in C code.
+	 */
+	subl	%esi, %ebx
+	movl	%ebx, image_offset(%ebp)	// save image_offset
 	jmp	efi32_pe_stub_entry
 
 2:	popl	%edi				// restore callee-save registers
diff --git a/drivers/firmware/efi/libstub/x86-stub.c b/drivers/firmware/efi/libstub/x86-stub.c
index 69a942f0640b..96bc4a8733c8 100644
--- a/drivers/firmware/efi/libstub/x86-stub.c
+++ b/drivers/firmware/efi/libstub/x86-stub.c
@@ -19,6 +19,7 @@
 
 static efi_system_table_t *sys_table;
 extern const bool efi_is64;
+extern u32 image_offset;
 
 __pure efi_system_table_t *efi_system_table(void)
 {
@@ -365,6 +366,7 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 	struct boot_params *boot_params;
 	struct setup_header *hdr;
 	efi_loaded_image_t *image;
+	void *image_base;
 	efi_guid_t proto = LOADED_IMAGE_PROTOCOL_GUID;
 	int options_size = 0;
 	efi_status_t status;
@@ -385,7 +387,10 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 		efi_exit(handle, status);
 	}
 
-	hdr = &((struct boot_params *)efi_table_attr(image, image_base))->hdr;
+	image_base = efi_table_attr(image, image_base);
+	image_offset = (void *)startup_32 - image_base;
+
+	hdr = &((struct boot_params *)image_base)->hdr;
 	above4g = hdr->xloadflags & XLF_CAN_BE_LOADED_ABOVE_4G;
 
 	status = efi_allocate_pages(0x4000, (unsigned long *)&boot_params,
@@ -400,7 +405,7 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 	hdr = &boot_params->hdr;
 
 	/* Copy the second sector to boot_params */
-	memcpy(&hdr->jump, efi_table_attr(image, image_base) + 512, 512);
+	memcpy(&hdr->jump, image_base + 512, 512);
 
 	/*
 	 * Fill out some of the header fields ourselves because the
@@ -727,7 +732,7 @@ unsigned long efi_main(efi_handle_t handle,
 	 * If the kernel isn't already loaded at the preferred load
 	 * address, relocate it.
 	 */
-	if (bzimage_addr != hdr->pref_address) {
+	if (bzimage_addr - image_offset != hdr->pref_address) {
 		status = efi_relocate_kernel(&bzimage_addr,
 					     hdr->init_size, hdr->init_size,
 					     hdr->pref_address,
@@ -737,6 +742,12 @@ unsigned long efi_main(efi_handle_t handle,
 			efi_printk("efi_relocate_kernel() failed!\n");
 			goto fail;
 		}
+		/*
+		 * Now that we've copied the kernel elsewhere, we no longer
+		 * have a setup block before startup_32, so reset image_offset
+		 * to zero in case it was set earlier.
+		 */
+		image_offset = 0;
 	}
 
 	/*
-- 
2.17.1


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

* [PATCH 17/28] efi/x86: Add kernel preferred address to PE header
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (15 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 16/28] efi/x86: Decompress at start of PE image load address Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 18/28] efi/x86: Remove extra headroom for setup block Ard Biesheuvel
                   ` (11 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

Store the kernel's link address as ImageBase in the PE header. Note that
the PE specification requires the ImageBase to be 64k aligned. The
preferred address should almost always satisfy that, except for 32-bit
kernel if the configuration has been customized.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200303221205.4048668-4-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/header.S | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/arch/x86/boot/header.S b/arch/x86/boot/header.S
index 4ee25e28996f..736b3a0c9454 100644
--- a/arch/x86/boot/header.S
+++ b/arch/x86/boot/header.S
@@ -138,10 +138,12 @@ optional_header:
 #endif
 
 extra_header_fields:
+	# PE specification requires ImageBase to be 64k-aligned
+	.set	image_base, (LOAD_PHYSICAL_ADDR + 0xffff) & ~0xffff
 #ifdef CONFIG_X86_32
-	.long	0				# ImageBase
+	.long	image_base			# ImageBase
 #else
-	.quad	0				# ImageBase
+	.quad	image_base			# ImageBase
 #endif
 	.long	0x20				# SectionAlignment
 	.long	0x20				# FileAlignment
-- 
2.17.1


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

* [PATCH 18/28] efi/x86: Remove extra headroom for setup block
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (16 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 17/28] efi/x86: Add kernel preferred address to PE header Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 19/28] efi/x86: Don't relocate the kernel unless necessary Ard Biesheuvel
                   ` (10 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

commit 223e3ee56f77 ("efi/x86: add headroom to decompressor BSS to
account for setup block") added headroom to the PE image to account for
the setup block, which wasn't used for the decompression buffer.

Now that the decompression buffer is located at the start of the image,
and includes the setup block, this is no longer required.

Add a check to make sure that the head section of the compressed kernel
won't overwrite itself while relocating. This is only for
future-proofing as with current limits on the setup and the actual size
of the head section, this can never happen.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200303221205.4048668-5-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/tools/build.c | 28 ++++++++++++++++++++++++++--
 1 file changed, 26 insertions(+), 2 deletions(-)

diff --git a/arch/x86/boot/tools/build.c b/arch/x86/boot/tools/build.c
index 90d403dfec80..3d03ad753ed5 100644
--- a/arch/x86/boot/tools/build.c
+++ b/arch/x86/boot/tools/build.c
@@ -65,6 +65,8 @@ unsigned long efi_pe_entry;
 unsigned long efi32_pe_entry;
 unsigned long kernel_info;
 unsigned long startup_64;
+unsigned long _ehead;
+unsigned long _end;
 
 /*----------------------------------------------------------------------*/
 
@@ -232,7 +234,7 @@ static void update_pecoff_text(unsigned int text_start, unsigned int file_sz,
 {
 	unsigned int pe_header;
 	unsigned int text_sz = file_sz - text_start;
-	unsigned int bss_sz = init_sz + text_start - file_sz;
+	unsigned int bss_sz = init_sz - file_sz;
 
 	pe_header = get_unaligned_le32(&buf[0x3c]);
 
@@ -259,7 +261,7 @@ static void update_pecoff_text(unsigned int text_start, unsigned int file_sz,
 	put_unaligned_le32(file_sz - 512 + bss_sz, &buf[pe_header + 0x1c]);
 
 	/* Size of image */
-	put_unaligned_le32(init_sz + text_start, &buf[pe_header + 0x50]);
+	put_unaligned_le32(init_sz, &buf[pe_header + 0x50]);
 
 	/*
 	 * Address of entry point for PE/COFF executable
@@ -360,6 +362,8 @@ static void parse_zoffset(char *fname)
 		PARSE_ZOFS(p, efi32_pe_entry);
 		PARSE_ZOFS(p, kernel_info);
 		PARSE_ZOFS(p, startup_64);
+		PARSE_ZOFS(p, _ehead);
+		PARSE_ZOFS(p, _end);
 
 		p = strchr(p, '\n');
 		while (p && (*p == '\r' || *p == '\n'))
@@ -444,6 +448,26 @@ int main(int argc, char ** argv)
 	put_unaligned_le32(sys_size, &buf[0x1f4]);
 
 	init_sz = get_unaligned_le32(&buf[0x260]);
+#ifdef CONFIG_EFI_STUB
+	/*
+	 * The decompression buffer will start at ImageBase. When relocating
+	 * the compressed kernel to its end, we must ensure that the head
+	 * section does not get overwritten.  The head section occupies
+	 * [i, i + _ehead), and the destination is [init_sz - _end, init_sz).
+	 *
+	 * At present these should never overlap, because i is at most 32k
+	 * because of SETUP_SECT_MAX, _ehead is less than 1k, and the
+	 * calculation of INIT_SIZE in boot/header.S ensures that
+	 * init_sz - _end is at least 64k.
+	 *
+	 * For future-proofing, increase init_sz if necessary.
+	 */
+
+	if (init_sz - _end < i + _ehead) {
+		init_sz = (i + _ehead + _end + 4095) & ~4095;
+		put_unaligned_le32(init_sz, &buf[0x260]);
+	}
+#endif
 	update_pecoff_text(setup_sectors * 512, i + (sys_size * 16), init_sz);
 
 	efi_stub_entry_update();
-- 
2.17.1


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

* [PATCH 19/28] efi/x86: Don't relocate the kernel unless necessary
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (17 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 18/28] efi/x86: Remove extra headroom for setup block Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 20/28] efi/x86: ignore memory attributes table on i386 Ard Biesheuvel
                   ` (9 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

Add alignment slack to the PE image size, so that we can realign the
decompression buffer within the space allocated for the image.

Only relocate the kernel if it has been loaded at an unsuitable address:
* Below LOAD_PHYSICAL_ADDR, or
* Above 64T for 64-bit and 512MiB for 32-bit

For 32-bit, the upper limit is conservative, but the exact limit can be
difficult to calculate.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200303221205.4048668-6-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/tools/build.c             | 16 +++++-------
 drivers/firmware/efi/libstub/x86-stub.c | 33 ++++++++++++++++++++++---
 2 files changed, 36 insertions(+), 13 deletions(-)

diff --git a/arch/x86/boot/tools/build.c b/arch/x86/boot/tools/build.c
index 3d03ad753ed5..db528961c283 100644
--- a/arch/x86/boot/tools/build.c
+++ b/arch/x86/boot/tools/build.c
@@ -238,21 +238,17 @@ static void update_pecoff_text(unsigned int text_start, unsigned int file_sz,
 
 	pe_header = get_unaligned_le32(&buf[0x3c]);
 
-#ifdef CONFIG_EFI_MIXED
 	/*
-	 * In mixed mode, we will execute startup_32() at whichever offset in
-	 * memory it happened to land when the PE/COFF loader loaded the image,
-	 * which may be misaligned with respect to the kernel_alignment field
-	 * in the setup header.
+	 * The PE/COFF loader may load the image at an address which is
+	 * misaligned with respect to the kernel_alignment field in the setup
+	 * header.
 	 *
-	 * In order for startup_32 to safely execute in place at this offset,
-	 * we need to ensure that the CONFIG_PHYSICAL_ALIGN aligned allocation
-	 * it creates for the page tables does not extend beyond the declared
-	 * size of the image in the PE/COFF header. So add the required slack.
+	 * In order to avoid relocating the kernel to correct the misalignment,
+	 * add slack to allow the buffer to be aligned within the declared size
+	 * of the image.
 	 */
 	bss_sz	+= CONFIG_PHYSICAL_ALIGN;
 	init_sz	+= CONFIG_PHYSICAL_ALIGN;
-#endif
 
 	/*
 	 * Size of code: Subtract the size of the first sector (512 bytes)
diff --git a/drivers/firmware/efi/libstub/x86-stub.c b/drivers/firmware/efi/libstub/x86-stub.c
index 96bc4a8733c8..064941ecc36f 100644
--- a/drivers/firmware/efi/libstub/x86-stub.c
+++ b/drivers/firmware/efi/libstub/x86-stub.c
@@ -17,6 +17,9 @@
 
 #include "efistub.h"
 
+/* Maximum physical address for 64-bit kernel with 4-level paging */
+#define MAXMEM_X86_64_4LEVEL (1ull << 46)
+
 static efi_system_table_t *sys_table;
 extern const bool efi_is64;
 extern u32 image_offset;
@@ -718,6 +721,7 @@ unsigned long efi_main(efi_handle_t handle,
 			     struct boot_params *boot_params)
 {
 	unsigned long bzimage_addr = (unsigned long)startup_32;
+	unsigned long buffer_start, buffer_end;
 	struct setup_header *hdr = &boot_params->hdr;
 	efi_status_t status;
 	unsigned long cmdline_paddr;
@@ -729,10 +733,33 @@ unsigned long efi_main(efi_handle_t handle,
 		efi_exit(handle, EFI_INVALID_PARAMETER);
 
 	/*
-	 * If the kernel isn't already loaded at the preferred load
-	 * address, relocate it.
+	 * If the kernel isn't already loaded at a suitable address,
+	 * relocate it.
+	 *
+	 * It must be loaded above LOAD_PHYSICAL_ADDR.
+	 *
+	 * The maximum address for 64-bit is 1 << 46 for 4-level paging. This
+	 * is defined as the macro MAXMEM, but unfortunately that is not a
+	 * compile-time constant if 5-level paging is configured, so we instead
+	 * define our own macro for use here.
+	 *
+	 * For 32-bit, the maximum address is complicated to figure out, for
+	 * now use KERNEL_IMAGE_SIZE, which will be 512MiB, the same as what
+	 * KASLR uses.
+	 *
+	 * Also relocate it if image_offset is zero, i.e. we weren't loaded by
+	 * LoadImage, but we are not aligned correctly.
 	 */
-	if (bzimage_addr - image_offset != hdr->pref_address) {
+
+	buffer_start = ALIGN(bzimage_addr - image_offset,
+			     hdr->kernel_alignment);
+	buffer_end = buffer_start + hdr->init_size;
+
+	if ((buffer_start < LOAD_PHYSICAL_ADDR)				     ||
+	    (IS_ENABLED(CONFIG_X86_32) && buffer_end > KERNEL_IMAGE_SIZE)    ||
+	    (IS_ENABLED(CONFIG_X86_64) && buffer_end > MAXMEM_X86_64_4LEVEL) ||
+	    (image_offset == 0 && !IS_ALIGNED(bzimage_addr,
+					      hdr->kernel_alignment))) {
 		status = efi_relocate_kernel(&bzimage_addr,
 					     hdr->init_size, hdr->init_size,
 					     hdr->pref_address,
-- 
2.17.1


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

* [PATCH 20/28] efi/x86: ignore memory attributes table on i386
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (18 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 19/28] efi/x86: Don't relocate the kernel unless necessary Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 21/28] efi/x86: preserve %ebx correctly in efi_set_virtual_address_map() Ard Biesheuvel
                   ` (8 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

Commit 3a6b6c6fb23667fa ("efi: Make EFI_MEMORY_ATTRIBUTES_TABLE
initialization common across all architectures") moved the call to
efi_memattr_init() from ARM specific to generic EFI init code, in
order to be able to apply the restricted permissions described in
that table on x86 as well.

We never enabled this feature fully on i386, and so mapping and
reserving this table is pointless. However, due to the early call to
memblock_reserve(), the memory bookkeeping gets confused to the point
where it produces the splat below when we try to map the memory later
on:

  ------------[ cut here ]------------
  ioremap on RAM at 0x3f251000 - 0x3fa1afff
  WARNING: CPU: 0 PID: 0 at arch/x86/mm/ioremap.c:166 __ioremap_caller ...
  Modules linked in:
  CPU: 0 PID: 0 Comm: swapper/0 Not tainted 4.20.0 #48
  Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 0.0.0 02/06/2015
  EIP: __ioremap_caller.constprop.0+0x249/0x260
  Code: 90 0f b7 05 4e 38 40 de 09 45 e0 e9 09 ff ff ff 90 8d 45 ec c6 05 ...
  EAX: 00000029 EBX: 00000000 ECX: de59c228 EDX: 00000001
  ESI: 3f250fff EDI: 00000000 EBP: de3edf20 ESP: de3edee0
  DS: 007b ES: 007b FS: 00d8 GS: 00e0 SS: 0068 EFLAGS: 00200296
  CR0: 80050033 CR2: ffd17000 CR3: 1e58c000 CR4: 00040690
  Call Trace:
   ioremap_cache+0xd/0x10
   ? old_map_region+0x72/0x9d
   old_map_region+0x72/0x9d
   efi_map_region+0x8/0xa
   efi_enter_virtual_mode+0x260/0x43b
   start_kernel+0x329/0x3aa
   i386_start_kernel+0xa7/0xab
   startup_32_smp+0x164/0x168
  ---[ end trace e15ccf6b9f356833 ]---

Let's work around this by disregarding the memory attributes table
altogether on i386, which does not result in a loss of functionality
or protection, given that we never consumed the contents.

Fixes: 3a6b6c6fb23667fa ("efi: Make EFI_MEMORY_ATTRIBUTES_TABLE ... ")
Tested-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200304165917.5893-1-ardb@kernel.org
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/efi.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/firmware/efi/efi.c b/drivers/firmware/efi/efi.c
index 1d5e9a030cb1..348fe572816b 100644
--- a/drivers/firmware/efi/efi.c
+++ b/drivers/firmware/efi/efi.c
@@ -600,7 +600,7 @@ int __init efi_config_parse_tables(const efi_config_table_t *config_tables,
 		}
 	}
 
-	if (efi_enabled(EFI_MEMMAP))
+	if (!IS_ENABLED(CONFIG_X86_32) && efi_enabled(EFI_MEMMAP))
 		efi_memattr_init();
 
 	efi_tpm_eventlog_init();
-- 
2.17.1


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

* [PATCH 21/28] efi/x86: preserve %ebx correctly in efi_set_virtual_address_map()
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (19 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 20/28] efi/x86: ignore memory attributes table on i386 Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 22/28] efi/libstub: avoid linking libstub/lib-ksyms.o into vmlinux Ard Biesheuvel
                   ` (7 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

Commit 59f2a619a2db8611 ("efi: Add 'runtime' pointer to struct efi")
modified the assembler routine called by efi_set_virtual_address_map(),
to grab the 'runtime' EFI service pointer while running with paging
disabled (which is tricky to do in C code)

After the change, register %ebx is not restored correctly, resulting
in all kinds of weird behavior, so fix that.

Reported-by: Guenter Roeck <linux@roeck-us.net>
Tested-by: Guenter Roeck <linux@roeck-us.net>
Link: https://lore.kernel.org/r/20200304133515.15035-1-ardb@kernel.org
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/platform/efi/efi_stub_32.S | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/arch/x86/platform/efi/efi_stub_32.S b/arch/x86/platform/efi/efi_stub_32.S
index 09237236fb25..09ec84f6ef51 100644
--- a/arch/x86/platform/efi/efi_stub_32.S
+++ b/arch/x86/platform/efi/efi_stub_32.S
@@ -54,7 +54,7 @@ SYM_FUNC_START(efi_call_svam)
 	orl	$0x80000000, %edx
 	movl	%edx, %cr0
 
-	pop	%ebx
+	movl	16(%esp), %ebx
 	leave
 	ret
 SYM_FUNC_END(efi_call_svam)
-- 
2.17.1


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

* [PATCH 22/28] efi/libstub: avoid linking libstub/lib-ksyms.o into vmlinux
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (20 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 21/28] efi/x86: preserve %ebx correctly in efi_set_virtual_address_map() Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 23/28] efi: fix a race and a buffer overflow while reading efivars via sysfs Ard Biesheuvel
                   ` (6 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Masahiro Yamada <masahiroy@kernel.org>

drivers/firmware/efi/libstub/Makefile builds a static library, which
is not linked into the main vmlinux target in the ordinary way [arm64],
or at all [ARM, x86].

Since commit 7f2084fa55e6 ("[kbuild] handle exports in lib-y objects
reliably"), any Makefile using lib-y generates lib-ksyms.o which is
linked into vmlinux.

In this case, the following garbage object is linked into vmlinux.

  drivers/firmware/efi/libstub/lib-ksyms.o

We do not want to follow the default linking rules for static libraries
built under libstub/ so using subdir-y instead of obj-y is the correct
way to descend into this directory.

Signed-off-by: Masahiro Yamada <masahiroy@kernel.org>
Link: https://lore.kernel.org/r/20200305055047.6097-1-masahiroy@kernel.org
[ardb: update commit log to clarify that arm64 deviates in this respect]
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/Makefile | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/firmware/efi/Makefile b/drivers/firmware/efi/Makefile
index 317a05cd388b..7a216984552b 100644
--- a/drivers/firmware/efi/Makefile
+++ b/drivers/firmware/efi/Makefile
@@ -20,7 +20,7 @@ obj-$(CONFIG_EFI_VARS_PSTORE)		+= efi-pstore.o
 obj-$(CONFIG_UEFI_CPER)			+= cper.o
 obj-$(CONFIG_EFI_RUNTIME_MAP)		+= runtime-map.o
 obj-$(CONFIG_EFI_RUNTIME_WRAPPERS)	+= runtime-wrappers.o
-obj-$(CONFIG_EFI_STUB)			+= libstub/
+subdir-$(CONFIG_EFI_STUB)		+= libstub
 obj-$(CONFIG_EFI_FAKE_MEMMAP)		+= fake_map.o
 obj-$(CONFIG_EFI_BOOTLOADER_CONTROL)	+= efibc.o
 obj-$(CONFIG_EFI_TEST)			+= test/
-- 
2.17.1


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

* [PATCH 23/28] efi: fix a race and a buffer overflow while reading efivars via sysfs
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (21 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 22/28] efi/libstub: avoid linking libstub/lib-ksyms.o into vmlinux Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 24/28] efi: add a sanity check to efivar_store_raw() Ard Biesheuvel
                   ` (5 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Vladis Dronov <vdronov@redhat.com>

There is a race and a buffer overflow corrupting a kernel memory while
reading an efi variable with a size more than 1024 bytes via the older
sysfs method. This happens because accessing struct efi_variable in
efivar_{attr,size,data}_read() and friends is not protected from
a concurrent access leading to a kernel memory corruption and, at best,
to a crash. The race scenario is the following:

CPU0:                                CPU1:
efivar_attr_read()
  var->DataSize = 1024;
  efivar_entry_get(... &var->DataSize)
    down_interruptible(&efivars_lock)
                                     efivar_attr_read() // same efi var
                                       var->DataSize = 1024;
                                       efivar_entry_get(... &var->DataSize)
                                         down_interruptible(&efivars_lock)
    virt_efi_get_variable()
    // returns EFI_BUFFER_TOO_SMALL but
    // var->DataSize is set to a real
    // var size more than 1024 bytes
    up(&efivars_lock)
                                         virt_efi_get_variable()
                                         // called with var->DataSize set
                                         // to a real var size, returns
                                         // successfully and overwrites
                                         // a 1024-bytes kernel buffer
                                         up(&efivars_lock)

This can be reproduced by concurrent reading of an efi variable which size
is more than 1024 bytes:

ts# for cpu in $(seq 0 $(nproc --ignore=1)); do ( taskset -c $cpu \
cat /sys/firmware/efi/vars/KEKDefault*/size & ) ; done

Fix this by using a local variable for a var's data buffer size so it
does not get overwritten.

Fixes: e14ab23dde12b80d ("efivars: efivar_entry API")
Reported-by: Bob Sanders <bob.sanders@hpe.com> and the LTP testsuite
Signed-off-by: Vladis Dronov <vdronov@redhat.com>
Link: https://lore.kernel.org/r/20200305084041.24053-2-vdronov@redhat.com
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/efivars.c | 29 ++++++++++++++++++++---------
 1 file changed, 20 insertions(+), 9 deletions(-)

diff --git a/drivers/firmware/efi/efivars.c b/drivers/firmware/efi/efivars.c
index d309abca5091..485c592d7990 100644
--- a/drivers/firmware/efi/efivars.c
+++ b/drivers/firmware/efi/efivars.c
@@ -83,13 +83,16 @@ static ssize_t
 efivar_attr_read(struct efivar_entry *entry, char *buf)
 {
 	struct efi_variable *var = &entry->var;
+	unsigned long size = sizeof(var->Data);
 	char *str = buf;
+	int ret;
 
 	if (!entry || !buf)
 		return -EINVAL;
 
-	var->DataSize = 1024;
-	if (efivar_entry_get(entry, &var->Attributes, &var->DataSize, var->Data))
+	ret = efivar_entry_get(entry, &var->Attributes, &size, var->Data);
+	var->DataSize = size;
+	if (ret)
 		return -EIO;
 
 	if (var->Attributes & EFI_VARIABLE_NON_VOLATILE)
@@ -116,13 +119,16 @@ static ssize_t
 efivar_size_read(struct efivar_entry *entry, char *buf)
 {
 	struct efi_variable *var = &entry->var;
+	unsigned long size = sizeof(var->Data);
 	char *str = buf;
+	int ret;
 
 	if (!entry || !buf)
 		return -EINVAL;
 
-	var->DataSize = 1024;
-	if (efivar_entry_get(entry, &var->Attributes, &var->DataSize, var->Data))
+	ret = efivar_entry_get(entry, &var->Attributes, &size, var->Data);
+	var->DataSize = size;
+	if (ret)
 		return -EIO;
 
 	str += sprintf(str, "0x%lx\n", var->DataSize);
@@ -133,12 +139,15 @@ static ssize_t
 efivar_data_read(struct efivar_entry *entry, char *buf)
 {
 	struct efi_variable *var = &entry->var;
+	unsigned long size = sizeof(var->Data);
+	int ret;
 
 	if (!entry || !buf)
 		return -EINVAL;
 
-	var->DataSize = 1024;
-	if (efivar_entry_get(entry, &var->Attributes, &var->DataSize, var->Data))
+	ret = efivar_entry_get(entry, &var->Attributes, &size, var->Data);
+	var->DataSize = size;
+	if (ret)
 		return -EIO;
 
 	memcpy(buf, var->Data, var->DataSize);
@@ -250,14 +259,16 @@ efivar_show_raw(struct efivar_entry *entry, char *buf)
 {
 	struct efi_variable *var = &entry->var;
 	struct compat_efi_variable *compat;
+	unsigned long datasize = sizeof(var->Data);
 	size_t size;
+	int ret;
 
 	if (!entry || !buf)
 		return 0;
 
-	var->DataSize = 1024;
-	if (efivar_entry_get(entry, &entry->var.Attributes,
-			     &entry->var.DataSize, entry->var.Data))
+	ret = efivar_entry_get(entry, &var->Attributes, &datasize, var->Data);
+	var->DataSize = datasize;
+	if (ret)
 		return -EIO;
 
 	if (in_compat_syscall()) {
-- 
2.17.1


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

* [PATCH 24/28] efi: add a sanity check to efivar_store_raw()
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (22 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 23/28] efi: fix a race and a buffer overflow while reading efivars via sysfs Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 25/28] efi: fix a mistype in comments mentioning efivar_entry_iter_begin() Ard Biesheuvel
                   ` (4 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Vladis Dronov <vdronov@redhat.com>

Add a sanity check to efivar_store_raw() the same way
efivar_{attr,size,data}_read() and efivar_show_raw() have it.

Signed-off-by: Vladis Dronov <vdronov@redhat.com>
Link: https://lore.kernel.org/r/20200305084041.24053-3-vdronov@redhat.com
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/efivars.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/drivers/firmware/efi/efivars.c b/drivers/firmware/efi/efivars.c
index 485c592d7990..78ad1ba8c987 100644
--- a/drivers/firmware/efi/efivars.c
+++ b/drivers/firmware/efi/efivars.c
@@ -208,6 +208,9 @@ efivar_store_raw(struct efivar_entry *entry, const char *buf, size_t count)
 	u8 *data;
 	int err;
 
+	if (!entry || !buf)
+		return -EINVAL;
+
 	if (in_compat_syscall()) {
 		struct compat_efi_variable *compat;
 
-- 
2.17.1


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

* [PATCH 25/28] efi: fix a mistype in comments mentioning efivar_entry_iter_begin()
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (23 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 24/28] efi: add a sanity check to efivar_store_raw() Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 26/28] efi/libstub/x86: use ULONG_MAX as upper bound for all allocations Ard Biesheuvel
                   ` (3 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Vladis Dronov <vdronov@redhat.com>

Signed-off-by: Vladis Dronov <vdronov@redhat.com>
Link: https://lore.kernel.org/r/20200305084041.24053-4-vdronov@redhat.com
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/efi-pstore.c | 2 +-
 drivers/firmware/efi/vars.c       | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/firmware/efi/efi-pstore.c b/drivers/firmware/efi/efi-pstore.c
index d2f6855d205b..c2f1d4e6630b 100644
--- a/drivers/firmware/efi/efi-pstore.c
+++ b/drivers/firmware/efi/efi-pstore.c
@@ -161,7 +161,7 @@ static int efi_pstore_scan_sysfs_exit(struct efivar_entry *pos,
  *
  * @record: pstore record to pass to callback
  *
- * You MUST call efivar_enter_iter_begin() before this function, and
+ * You MUST call efivar_entry_iter_begin() before this function, and
  * efivar_entry_iter_end() afterwards.
  *
  */
diff --git a/drivers/firmware/efi/vars.c b/drivers/firmware/efi/vars.c
index 436d1776bc7b..5f2a4d162795 100644
--- a/drivers/firmware/efi/vars.c
+++ b/drivers/firmware/efi/vars.c
@@ -1071,7 +1071,7 @@ EXPORT_SYMBOL_GPL(efivar_entry_iter_end);
  * entry on the list. It is safe for @func to remove entries in the
  * list via efivar_entry_delete().
  *
- * You MUST call efivar_enter_iter_begin() before this function, and
+ * You MUST call efivar_entry_iter_begin() before this function, and
  * efivar_entry_iter_end() afterwards.
  *
  * It is possible to begin iteration from an arbitrary entry within
-- 
2.17.1


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

* [PATCH 26/28] efi/libstub/x86: use ULONG_MAX as upper bound for all allocations
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (24 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 25/28] efi: fix a mistype in comments mentioning efivar_entry_iter_begin() Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 27/28] efi/x86: Fix cast of image argument Ard Biesheuvel
                   ` (2 subsequent siblings)
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

The header flag XLF_CAN_BE_LOADED_ABOVE_4G will inform us whether
allocations above 4 GiB for kernel, command line, etc are permitted,
so we take it into account when calling efi_allocate_pages() etc.

However, CONFIG_EFI_STUB implies CONFIG_RELOCATABLE, and so the flag
is guaranteed to be set on x86_64 builds, whereas i386 builds are
guaranteed to run under firmware that will not allocate above 4 GB
in the first place.

So drop the check, and just pass ULONG_MAX as the upper bound for
all allocations.

Link: https://lore.kernel.org/r/20200303225054.28741-1-ardb@kernel.org
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/libstub/x86-stub.c | 17 ++++-------------
 1 file changed, 4 insertions(+), 13 deletions(-)

diff --git a/drivers/firmware/efi/libstub/x86-stub.c b/drivers/firmware/efi/libstub/x86-stub.c
index 064941ecc36f..bf0c3f60762a 100644
--- a/drivers/firmware/efi/libstub/x86-stub.c
+++ b/drivers/firmware/efi/libstub/x86-stub.c
@@ -376,7 +376,6 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 	char *cmdline_ptr;
 	unsigned long ramdisk_addr;
 	unsigned long ramdisk_size;
-	bool above4g;
 
 	sys_table = sys_table_arg;
 
@@ -394,10 +393,8 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 	image_offset = (void *)startup_32 - image_base;
 
 	hdr = &((struct boot_params *)image_base)->hdr;
-	above4g = hdr->xloadflags & XLF_CAN_BE_LOADED_ABOVE_4G;
 
-	status = efi_allocate_pages(0x4000, (unsigned long *)&boot_params,
-				    above4g ? ULONG_MAX : UINT_MAX);
+	status = efi_allocate_pages(0x4000, (unsigned long *)&boot_params, ULONG_MAX);
 	if (status != EFI_SUCCESS) {
 		efi_printk("Failed to allocate lowmem for boot params\n");
 		efi_exit(handle, status);
@@ -421,8 +418,7 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 	hdr->type_of_loader = 0x21;
 
 	/* Convert unicode cmdline to ascii */
-	cmdline_ptr = efi_convert_cmdline(image, &options_size,
-					  above4g ? ULONG_MAX : UINT_MAX);
+	cmdline_ptr = efi_convert_cmdline(image, &options_size, ULONG_MAX);
 	if (!cmdline_ptr)
 		goto fail;
 
@@ -442,8 +438,7 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 			status = efi_load_initrd(image, &ramdisk_addr,
 						 &ramdisk_size,
 						 hdr->initrd_addr_max,
-						 above4g ? ULONG_MAX
-							 : hdr->initrd_addr_max);
+						 ULONG_MAX);
 			if (status != EFI_SUCCESS)
 				goto fail2;
 			hdr->ramdisk_image = ramdisk_addr & 0xffffffff;
@@ -795,12 +790,8 @@ unsigned long efi_main(efi_handle_t handle,
 	 */
 	if (!noinitrd()) {
 		unsigned long addr, size;
-		unsigned long max_addr = hdr->initrd_addr_max;
 
-		if (hdr->xloadflags & XLF_CAN_BE_LOADED_ABOVE_4G)
-			max_addr = ULONG_MAX;
-
-		status = efi_load_initrd_dev_path(&addr, &size, max_addr);
+		status = efi_load_initrd_dev_path(&addr, &size, ULONG_MAX);
 		if (status == EFI_SUCCESS) {
 			hdr->ramdisk_image		= (u32)addr;
 			hdr->ramdisk_size 		= (u32)size;
-- 
2.17.1


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

* [PATCH 27/28] efi/x86: Fix cast of image argument
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (25 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 26/28] efi/libstub/x86: use ULONG_MAX as upper bound for all allocations Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  8:08 ` [PATCH 28/28] partitions/efi: Fix partition name parsing in GUID partition entry Ard Biesheuvel
  2020-03-08  9:00 ` [GIT PULL 00/28] More EFI fixes for v5.7 Ingo Molnar
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Arvind Sankar <nivedita@alum.mit.edu>

handle_protocol expects void **, not void *.

Signed-off-by: Arvind Sankar <nivedita@alum.mit.edu>
Link: https://lore.kernel.org/r/20200305143642.820865-1-nivedita@alum.mit.edu
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 drivers/firmware/efi/libstub/x86-stub.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/firmware/efi/libstub/x86-stub.c b/drivers/firmware/efi/libstub/x86-stub.c
index bf0c3f60762a..e61782849ebd 100644
--- a/drivers/firmware/efi/libstub/x86-stub.c
+++ b/drivers/firmware/efi/libstub/x86-stub.c
@@ -383,7 +383,7 @@ efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
 	if (sys_table->hdr.signature != EFI_SYSTEM_TABLE_SIGNATURE)
 		efi_exit(handle, EFI_INVALID_PARAMETER);
 
-	status = efi_bs_call(handle_protocol, handle, &proto, (void *)&image);
+	status = efi_bs_call(handle_protocol, handle, &proto, (void **)&image);
 	if (status != EFI_SUCCESS) {
 		efi_printk("Failed to get handle for LOADED_IMAGE_PROTOCOL\n");
 		efi_exit(handle, status);
-- 
2.17.1


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

* [PATCH 28/28] partitions/efi: Fix partition name parsing in GUID partition entry
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (26 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 27/28] efi/x86: Fix cast of image argument Ard Biesheuvel
@ 2020-03-08  8:08 ` Ard Biesheuvel
  2020-03-08  9:00 ` [GIT PULL 00/28] More EFI fixes for v5.7 Ingo Molnar
  28 siblings, 0 replies; 30+ messages in thread
From: Ard Biesheuvel @ 2020-03-08  8:08 UTC (permalink / raw)
  To: linux-efi, Ingo Molnar, Thomas Gleixner
  Cc: Ard Biesheuvel, linux-kernel, Arvind Sankar, Christoph Hellwig,
	David Hildenbrand, Davidlohr Bueso, Guenter Roeck,
	Heinrich Schuchardt, Jonathan Corbet, Lukas Bulwahn,
	Masahiro Yamada, Nikolai Merinov, Tom Lendacky, Vladis Dronov

From: Nikolai Merinov <n.merinov@inango-systems.com>

GUID partition entry defined to have a partition name as 36 UTF-16LE
code units. This means that on big-endian platforms ASCII symbols
would be read with 0xXX00 efi_char16_t character code. In order to
correctly extract ASCII characters from a partition name field we
should be converted from 16LE to CPU architecture.

The problem exists on all big endian platforms.

Cc: Davidlohr Bueso <dave@stgolabs.net>
Signed-off-by: Nikolai Merinov <n.merinov@inango-systems.com>
Fixes: eec7ecfede74 ("genhd, efi: add efi partition metadata to hd_structs")
Reviewed-by: Christoph Hellwig <hch@lst.de>
Link: https://lore.kernel.org/r/797777312.1324734.1582544319435.JavaMail.zimbra@inango-systems.com/
Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 block/partitions/efi.c | 35 ++++++++++++++++++++++++++---------
 block/partitions/efi.h |  2 +-
 2 files changed, 27 insertions(+), 10 deletions(-)

diff --git a/block/partitions/efi.c b/block/partitions/efi.c
index db2fef7dfc47..d26a0654d7ca 100644
--- a/block/partitions/efi.c
+++ b/block/partitions/efi.c
@@ -656,6 +656,30 @@ static int find_valid_gpt(struct parsed_partitions *state, gpt_header **gpt,
         return 0;
 }
 
+/**
+ * utf16_le_to_7bit(): Naively converts UTF-16LE string to 7bit characters
+ * @in: input UTF-16LE string
+ * @size: size of the input string
+ * @out: output string ptr, should be capable to store @size+1 characters
+ *
+ * Description: Converts @size UTF16-LE symbols from @in string to 7bit
+ * characters and store them to @out. Adds trailing zero to @out array.
+ */
+static void utf16_le_to_7bit(const __le16 *in, unsigned int size, u8 *out)
+{
+	unsigned int i = 0;
+
+	out[size] = 0;
+	while (i < size) {
+		u8 c = le16_to_cpu(in[i]) & 0xff;
+
+		if (c && !isprint(c))
+			c = '!';
+		out[i] = c;
+		i++;
+	}
+}
+
 /**
  * efi_partition(struct parsed_partitions *state)
  * @state: disk parsed partitions
@@ -692,7 +716,6 @@ int efi_partition(struct parsed_partitions *state)
 
 	for (i = 0; i < le32_to_cpu(gpt->num_partition_entries) && i < state->limit-1; i++) {
 		struct partition_meta_info *info;
-		unsigned label_count = 0;
 		unsigned label_max;
 		u64 start = le64_to_cpu(ptes[i].starting_lba);
 		u64 size = le64_to_cpu(ptes[i].ending_lba) -
@@ -713,14 +736,8 @@ int efi_partition(struct parsed_partitions *state)
 		/* Naively convert UTF16-LE to 7 bits. */
 		label_max = min(ARRAY_SIZE(info->volname) - 1,
 				ARRAY_SIZE(ptes[i].partition_name));
-		info->volname[label_max] = 0;
-		while (label_count < label_max) {
-			u8 c = ptes[i].partition_name[label_count] & 0xff;
-			if (c && !isprint(c))
-				c = '!';
-			info->volname[label_count] = c;
-			label_count++;
-		}
+		utf16_le_to_7bit(ptes[i].partition_name, label_max,
+				 info->volname);
 		state->parts[i + 1].has_info = true;
 	}
 	kfree(ptes);
diff --git a/block/partitions/efi.h b/block/partitions/efi.h
index 3e8576157575..0b6d5b7be111 100644
--- a/block/partitions/efi.h
+++ b/block/partitions/efi.h
@@ -88,7 +88,7 @@ typedef struct _gpt_entry {
 	__le64 starting_lba;
 	__le64 ending_lba;
 	gpt_entry_attributes attributes;
-	efi_char16_t partition_name[72 / sizeof (efi_char16_t)];
+	__le16 partition_name[72 / sizeof (__le16)];
 } __packed gpt_entry;
 
 typedef struct _gpt_mbr_record {
-- 
2.17.1


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

* Re: [GIT PULL 00/28] More EFI fixes for v5.7
  2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
                   ` (27 preceding siblings ...)
  2020-03-08  8:08 ` [PATCH 28/28] partitions/efi: Fix partition name parsing in GUID partition entry Ard Biesheuvel
@ 2020-03-08  9:00 ` Ingo Molnar
  28 siblings, 0 replies; 30+ messages in thread
From: Ingo Molnar @ 2020-03-08  9:00 UTC (permalink / raw)
  To: Ard Biesheuvel
  Cc: linux-efi, Thomas Gleixner, linux-kernel, Arvind Sankar,
	Christoph Hellwig, David Hildenbrand, Davidlohr Bueso,
	Guenter Roeck, Heinrich Schuchardt, Jonathan Corbet,
	Lukas Bulwahn, Masahiro Yamada, Nikolai Merinov, Tom Lendacky,
	Vladis Dronov


* Ard Biesheuvel <ardb@kernel.org> wrote:

> The following changes since commit b9d8b63e340392d7f3ad79881f36a550566cbbbe:
> 
>   Merge tag 'stable-shared-branch-for-driver-tree' into HEAD (2020-03-05 09:58:20 +0100)
> 
> are available in the Git repository at:
> 
>   git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi.git tags/efi-next
> 
> for you to fetch changes up to dfb2a1c61fcdc8be5dd74608c411c78008a0f078:
> 
>   partitions/efi: Fix partition name parsing in GUID partition entry (2020-03-06 11:17:42 +0100)
> 
> ----------------------------------------------------------------
> More EFI updates for v5.7
> 
> - a fix for a boot regression in the IMA code on x86 booting without UEFI
> - memory encryption fixes for x86, so that the TPM tables and the RNG
>   config table created by the stub are correctly identified as living in
>   unencrypted memory
> - style tweak and doc update from Heinrich
> - followup to the ARM EFI entry code simplifications to ensure that we
>   don't rely on EFI_LOADER_DATA memory being RWX
> - fixes from Arvind to ensure that the new mixed mode approach works as
>   expected regardless of where the image is loaded in memory by the UEFI
>   PE/COFF loader
> - more fixes from Arvind to make it more likely that the image can be
>   decompressed in place, regardless of where it was loaded in memory
> - efivars bugfix and some cleanup from Vladis
> - incorporate a stable branch with the EFI pieces of Hans's work on
>   loading device firmware from EFI boot service memory regions
> - some followup fixes for the EFI stub changes that are queued for
>   v5.7 already
> - an endianness fix for the EFI GPT partition table driver

>  22 files changed, 319 insertions(+), 141 deletions(-)

Applied, thanks Ard!

	Ingo

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

end of thread, other threads:[~2020-03-08  9:00 UTC | newest]

Thread overview: 30+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-03-08  8:08 [GIT PULL 00/28] More EFI fixes for v5.7 Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 01/28] efi/x86: Add TPM related EFI tables to unencrypted mapping checks Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 02/28] efi/x86: Add RNG seed EFI table to unencrypted mapping check Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 03/28] efi: don't shadow i in efi_config_parse_tables() Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 04/28] efi/arm: clean EFI stub exit code from cache instead of avoiding it Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 05/28] efi/arm64: " Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 06/28] efi: mark all EFI runtime services as unsupported on non-EFI boot Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 07/28] MAINTAINERS: adjust EFI entry to removing eboot.c Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 08/28] efi/libstub: add libstub/mem.c to documentation tree Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 09/28] efi/x86: Annotate the LOADED_IMAGE_PROTOCOL_GUID with SYM_DATA Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 10/28] efi/x86: Respect 32-bit ABI in efi32_pe_entry Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 11/28] efi/x86: Make efi32_pe_entry more readable Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 12/28] efi/x86: Avoid using code32_start Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 13/28] x86/boot: Use unsigned comparison for addresses Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 14/28] efi/libstub/x86: deal with exit() boot service returning Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 15/28] x86/boot/compressed/32: Save the output address instead of recalculating it Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 16/28] efi/x86: Decompress at start of PE image load address Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 17/28] efi/x86: Add kernel preferred address to PE header Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 18/28] efi/x86: Remove extra headroom for setup block Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 19/28] efi/x86: Don't relocate the kernel unless necessary Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 20/28] efi/x86: ignore memory attributes table on i386 Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 21/28] efi/x86: preserve %ebx correctly in efi_set_virtual_address_map() Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 22/28] efi/libstub: avoid linking libstub/lib-ksyms.o into vmlinux Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 23/28] efi: fix a race and a buffer overflow while reading efivars via sysfs Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 24/28] efi: add a sanity check to efivar_store_raw() Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 25/28] efi: fix a mistype in comments mentioning efivar_entry_iter_begin() Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 26/28] efi/libstub/x86: use ULONG_MAX as upper bound for all allocations Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 27/28] efi/x86: Fix cast of image argument Ard Biesheuvel
2020-03-08  8:08 ` [PATCH 28/28] partitions/efi: Fix partition name parsing in GUID partition entry Ard Biesheuvel
2020-03-08  9:00 ` [GIT PULL 00/28] More EFI fixes for v5.7 Ingo Molnar

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).