Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1756627AbcJPPRQ (ORCPT ); Sun, 16 Oct 2016 11:17:16 -0400 Received: from aserp1040.oracle.com ([141.146.126.69]:41161 "EHLO aserp1040.oracle.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752904AbcJPPRG (ORCPT ); Sun, 16 Oct 2016 11:17:06 -0400 From: Vegard Nossum To: linux-kernel@vger.kernel.org, Greg Kroah-Hartman Cc: Jiri Slaby , Linus Torvalds , "Luis R . Rodriguez" , Vegard Nossum , Dmitry Torokhov , stable@vger.kernel.org Subject: [PATCH 02/12] firmware: declare {__start,__end}_builtin_fw as external array Date: Sun, 16 Oct 2016 17:16:06 +0200 Message-Id: <20161016151616.31451-3-vegard.nossum@oracle.com> X-Mailer: git-send-email 2.10.0.479.g221bd91 In-Reply-To: <20161016151616.31451-1-vegard.nossum@oracle.com> References: <20161016151616.31451-1-vegard.nossum@oracle.com> X-Source-IP: userv0021.oracle.com [156.151.31.71] Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Length: 3297 Lines: 102 The test in this loop: for (b_fw = __start_builtin_fw; b_fw != __end_builtin_fw; b_fw++) { was getting completely compiled out by my gcc, 7.0.0 20160520. The result was that the loop was going beyond the end of the builtin_fw array and giving me a page fault when trying to dereference b_fw->name inside strcmp(). By using the new external array helper macros we get the expected behaviour. Reported-by: Jiri Slaby Cc: Dmitry Torokhov Cc: Linus Torvalds Cc: stable@vger.kernel.org Signed-off-by: Vegard Nossum --- arch/x86/kernel/cpu/microcode/core.c | 5 ++--- drivers/base/firmware_class.c | 9 +++++---- include/asm-generic/vmlinux.lds.h | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/arch/x86/kernel/cpu/microcode/core.c b/arch/x86/kernel/cpu/microcode/core.c index 5ce5155..6669746 100644 --- a/arch/x86/kernel/cpu/microcode/core.c +++ b/arch/x86/kernel/cpu/microcode/core.c @@ -91,15 +91,14 @@ static bool __init check_loader_disabled_bsp(void) return *res; } -extern struct builtin_fw __start_builtin_fw[]; -extern struct builtin_fw __end_builtin_fw[]; +DECLARE_EXTARRAY(struct builtin_fw, builtin_fw); bool get_builtin_firmware(struct cpio_data *cd, const char *name) { #ifdef CONFIG_FW_LOADER struct builtin_fw *b_fw; - for (b_fw = __start_builtin_fw; b_fw != __end_builtin_fw; b_fw++) { + ext_for_each(b_fw, builtin_fw) { if (!strcmp(name, b_fw->name)) { cd->size = b_fw->size; cd->data = b_fw->data; diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index 22d1760..b85d943e6 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -9,6 +9,7 @@ #include #include +#include #include #include #include @@ -43,15 +44,14 @@ MODULE_LICENSE("GPL"); #ifdef CONFIG_FW_LOADER -extern struct builtin_fw __start_builtin_fw[]; -extern struct builtin_fw __end_builtin_fw[]; +DECLARE_EXTARRAY(struct builtin_fw, builtin_fw) static bool fw_get_builtin_firmware(struct firmware *fw, const char *name, void *buf, size_t size) { struct builtin_fw *b_fw; - for (b_fw = __start_builtin_fw; b_fw != __end_builtin_fw; b_fw++) { + ext_for_each(b_fw, builtin_fw) { if (strcmp(name, b_fw->name) == 0) { fw->size = b_fw->size; fw->data = b_fw->data; @@ -69,9 +69,10 @@ static bool fw_is_builtin_firmware(const struct firmware *fw) { struct builtin_fw *b_fw; - for (b_fw = __start_builtin_fw; b_fw != __end_builtin_fw; b_fw++) + ext_for_each(b_fw, builtin_fw) { if (fw->data == b_fw->data) return true; + } return false; } diff --git a/include/asm-generic/vmlinux.lds.h b/include/asm-generic/vmlinux.lds.h index 3074796..d6121ac 100644 --- a/include/asm-generic/vmlinux.lds.h +++ b/include/asm-generic/vmlinux.lds.h @@ -317,7 +317,7 @@ .builtin_fw : AT(ADDR(.builtin_fw) - LOAD_OFFSET) { \ VMLINUX_SYMBOL(__start_builtin_fw) = .; \ *(.builtin_fw) \ - VMLINUX_SYMBOL(__end_builtin_fw) = .; \ + VMLINUX_SYMBOL(__stop_builtin_fw) = .; \ } \ \ TRACEDATA \ -- 2.10.0.479.g221bd91