From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753793AbcIIPTj (ORCPT ); Fri, 9 Sep 2016 11:19:39 -0400 Received: from mail-wm0-f51.google.com ([74.125.82.51]:36588 "EHLO mail-wm0-f51.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1753534AbcIIPTZ (ORCPT ); Fri, 9 Sep 2016 11:19:25 -0400 From: Matt Fleming To: Ingo Molnar , Thomas Gleixner , "H . Peter Anvin" Cc: Ricardo Neri , Ard Biesheuvel , linux-kernel@vger.kernel.org, linux-efi@vger.kernel.org, Matt Fleming , Peter Jones , Scott Lawson Subject: [PATCH 24/29] x86/efi: Defer efi_esrt_init until after memblock_x86_fill Date: Fri, 9 Sep 2016 16:18:46 +0100 Message-Id: <20160909151851.27577-25-matt@codeblueprint.co.uk> X-Mailer: git-send-email 2.9.3 In-Reply-To: <20160909151851.27577-1-matt@codeblueprint.co.uk> References: <20160909151851.27577-1-matt@codeblueprint.co.uk> Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: Ricardo Neri Commit 7b02d53e7852 ("efi: Allow drivers to reserve boot services forever") introduced a new efi_mem_reserve to reserve the boot services memory regions forever. This reservation involves allocating a new EFI memory range descriptor. However, allocation can only succeed if there is memory available for the allocation. Otherwise, error such as the following may occur: esrt: Reserving ESRT space from 0x000000003dd6a000 to 0x000000003dd6a010. Kernel panic - not syncing: ERROR: Failed to allocate 0x9f0 bytes below \ 0x0. CPU: 0 PID: 0 Comm: swapper Not tainted 4.7.0-rc5+ #503 0000000000000000 ffffffff81e03ce0 ffffffff8131dae8 ffffffff81bb6c50 ffffffff81e03d70 ffffffff81e03d60 ffffffff8111f4df 0000000000000018 ffffffff81e03d70 ffffffff81e03d08 00000000000009f0 00000000000009f0 Call Trace: [] dump_stack+0x4d/0x65 [] panic+0xc5/0x206 [] memblock_alloc_base+0x29/0x2e [] memblock_alloc+0xb/0xd [] efi_arch_mem_reserve+0xbc/0x134 [] efi_mem_reserve+0x2c/0x31 [] ? efi_mem_reserve+0x2c/0x31 [] efi_esrt_init+0x19e/0x1b4 [] efi_init+0x398/0x44a [] setup_arch+0x415/0xc30 [] start_kernel+0x5b/0x3ef [] x86_64_start_reservations+0x2f/0x31 [] x86_64_start_kernel+0xea/0xed ---[ end Kernel panic - not syncing: ERROR: Failed to allocate 0x9f0 bytes below 0x0. An inspection of the memblock configuration reveals that there is no memory available for the allocation: MEMBLOCK configuration: memory size = 0x0 reserved size = 0x4f339c0 memory.cnt = 0x1 memory[0x0] [0x00000000000000-0xffffffffffffffff], 0x0 bytes on node 0\ flags: 0x0 reserved.cnt = 0x4 reserved[0x0] [0x0000000008c000-0x0000000008c9bf], 0x9c0 bytes flags: 0x0 reserved[0x1] [0x0000000009f000-0x000000000fffff], 0x61000 bytes\ flags: 0x0 reserved[0x2] [0x00000002800000-0x0000000394bfff], 0x114c000 bytes\ flags: 0x0 reserved[0x3] [0x000000304e4000-0x00000034269fff], 0x3d86000 bytes\ flags: 0x0 This situation can be avoided if we call efi_esrt_init after memblock has memory regions for the allocation. Also, the EFI ESRT driver makes use of early_memremap'pings. Therfore, we do not want to defer efi_esrt_init for too long. We must call such function while calls to early_memremap are still valid. A good place to meet the two aforementioned conditions is right after memblock_x86_fill, grouped with other EFI-related functions. Reported-by: Scott Lawson Signed-off-by: Ricardo Neri Cc: Ard Biesheuvel Cc: Peter Jones Signed-off-by: Matt Fleming --- arch/x86/kernel/setup.c | 1 + arch/x86/platform/efi/efi.c | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/arch/x86/kernel/setup.c b/arch/x86/kernel/setup.c index 4fd69e532c15..528b8eb24a04 100644 --- a/arch/x86/kernel/setup.c +++ b/arch/x86/kernel/setup.c @@ -1101,6 +1101,7 @@ void __init setup_arch(char **cmdline_p) if (efi_enabled(EFI_MEMMAP)) { efi_fake_memmap(); efi_find_mirror(); + efi_esrt_init(); /* * The EFI specification says that boot service code won't be diff --git a/arch/x86/platform/efi/efi.c b/arch/x86/platform/efi/efi.c index 342cebd1e17c..0955c70897ae 100644 --- a/arch/x86/platform/efi/efi.c +++ b/arch/x86/platform/efi/efi.c @@ -474,8 +474,6 @@ void __init efi_init(void) if (efi_enabled(EFI_DBG)) efi_print_memmap(); - - efi_esrt_init(); } void __init efi_late_init(void) -- 2.9.3 From mboxrd@z Thu Jan 1 00:00:00 1970 From: Matt Fleming Subject: [PATCH 24/29] x86/efi: Defer efi_esrt_init until after memblock_x86_fill Date: Fri, 9 Sep 2016 16:18:46 +0100 Message-ID: <20160909151851.27577-25-matt@codeblueprint.co.uk> References: <20160909151851.27577-1-matt@codeblueprint.co.uk> Return-path: In-Reply-To: <20160909151851.27577-1-matt-mF/unelCI9GS6iBeEJttW/XRex20P6io@public.gmane.org> Sender: linux-efi-owner-u79uwXL29TY76Z2rM5mHXA@public.gmane.org To: Ingo Molnar , Thomas Gleixner , "H . Peter Anvin" Cc: Ricardo Neri , Ard Biesheuvel , linux-kernel-u79uwXL29TY76Z2rM5mHXA@public.gmane.org, linux-efi-u79uwXL29TY76Z2rM5mHXA@public.gmane.org, Matt Fleming , Peter Jones , Scott Lawson List-Id: linux-efi@vger.kernel.org From: Ricardo Neri Commit 7b02d53e7852 ("efi: Allow drivers to reserve boot services forever") introduced a new efi_mem_reserve to reserve the boot services memory regions forever. This reservation involves allocating a new EFI memory range descriptor. However, allocation can only succeed if there is memory available for the allocation. Otherwise, error such as the following may occur: esrt: Reserving ESRT space from 0x000000003dd6a000 to 0x000000003dd6a010. Kernel panic - not syncing: ERROR: Failed to allocate 0x9f0 bytes below \ 0x0. CPU: 0 PID: 0 Comm: swapper Not tainted 4.7.0-rc5+ #503 0000000000000000 ffffffff81e03ce0 ffffffff8131dae8 ffffffff81bb6c50 ffffffff81e03d70 ffffffff81e03d60 ffffffff8111f4df 0000000000000018 ffffffff81e03d70 ffffffff81e03d08 00000000000009f0 00000000000009f0 Call Trace: [] dump_stack+0x4d/0x65 [] panic+0xc5/0x206 [] memblock_alloc_base+0x29/0x2e [] memblock_alloc+0xb/0xd [] efi_arch_mem_reserve+0xbc/0x134 [] efi_mem_reserve+0x2c/0x31 [] ? efi_mem_reserve+0x2c/0x31 [] efi_esrt_init+0x19e/0x1b4 [] efi_init+0x398/0x44a [] setup_arch+0x415/0xc30 [] start_kernel+0x5b/0x3ef [] x86_64_start_reservations+0x2f/0x31 [] x86_64_start_kernel+0xea/0xed ---[ end Kernel panic - not syncing: ERROR: Failed to allocate 0x9f0 bytes below 0x0. An inspection of the memblock configuration reveals that there is no memory available for the allocation: MEMBLOCK configuration: memory size = 0x0 reserved size = 0x4f339c0 memory.cnt = 0x1 memory[0x0] [0x00000000000000-0xffffffffffffffff], 0x0 bytes on node 0\ flags: 0x0 reserved.cnt = 0x4 reserved[0x0] [0x0000000008c000-0x0000000008c9bf], 0x9c0 bytes flags: 0x0 reserved[0x1] [0x0000000009f000-0x000000000fffff], 0x61000 bytes\ flags: 0x0 reserved[0x2] [0x00000002800000-0x0000000394bfff], 0x114c000 bytes\ flags: 0x0 reserved[0x3] [0x000000304e4000-0x00000034269fff], 0x3d86000 bytes\ flags: 0x0 This situation can be avoided if we call efi_esrt_init after memblock has memory regions for the allocation. Also, the EFI ESRT driver makes use of early_memremap'pings. Therfore, we do not want to defer efi_esrt_init for too long. We must call such function while calls to early_memremap are still valid. A good place to meet the two aforementioned conditions is right after memblock_x86_fill, grouped with other EFI-related functions. Reported-by: Scott Lawson Signed-off-by: Ricardo Neri Cc: Ard Biesheuvel Cc: Peter Jones Signed-off-by: Matt Fleming --- arch/x86/kernel/setup.c | 1 + arch/x86/platform/efi/efi.c | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/arch/x86/kernel/setup.c b/arch/x86/kernel/setup.c index 4fd69e532c15..528b8eb24a04 100644 --- a/arch/x86/kernel/setup.c +++ b/arch/x86/kernel/setup.c @@ -1101,6 +1101,7 @@ void __init setup_arch(char **cmdline_p) if (efi_enabled(EFI_MEMMAP)) { efi_fake_memmap(); efi_find_mirror(); + efi_esrt_init(); /* * The EFI specification says that boot service code won't be diff --git a/arch/x86/platform/efi/efi.c b/arch/x86/platform/efi/efi.c index 342cebd1e17c..0955c70897ae 100644 --- a/arch/x86/platform/efi/efi.c +++ b/arch/x86/platform/efi/efi.c @@ -474,8 +474,6 @@ void __init efi_init(void) if (efi_enabled(EFI_DBG)) efi_print_memmap(); - - efi_esrt_init(); } void __init efi_late_init(void) -- 2.9.3