From patchwork Tue Jan 24 16:16:39 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ard Biesheuvel X-Patchwork-Id: 92371 Delivered-To: patch@linaro.org Received: by 10.182.3.34 with SMTP id 2csp1774394obz; Tue, 24 Jan 2017 08:16:59 -0800 (PST) X-Received: by 10.98.192.72 with SMTP id x69mr40247581pff.129.1485274619100; Tue, 24 Jan 2017 08:16:59 -0800 (PST) Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id 16si19745573pfw.94.2017.01.24.08.16.58; Tue, 24 Jan 2017 08:16:59 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; dkim=pass header.i=@linaro.org; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linaro.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751211AbdAXQQ4 (ORCPT + 25 others); Tue, 24 Jan 2017 11:16:56 -0500 Received: from mail-wm0-f48.google.com ([74.125.82.48]:34032 "EHLO mail-wm0-f48.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751179AbdAXQQw (ORCPT ); Tue, 24 Jan 2017 11:16:52 -0500 Received: by mail-wm0-f48.google.com with SMTP id f73so44020164wmf.1 for ; Tue, 24 Jan 2017 08:16:51 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=Xm4wNHikED+4yRYlD55Gr7MLURhwa1TupfQRHXqIjHc=; b=LaLoEvtoBMG/ykOx6cVvlQBoI3ix+0dFP8nZ+EUSQt0U440vbhUDpWliiPg2DHtY1Y HRsT+p+jz7XTB/jmerXPHQPXs7ZUoEsvBJEN9hoO42jC/vXlHJNg3WHVPpzxJ7GavQDP dCJcl5EBOeDMFfB16OQ9e6MlDPwQZmxz4mRiI= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=Xm4wNHikED+4yRYlD55Gr7MLURhwa1TupfQRHXqIjHc=; b=WU+sNLy8nc6VsQbxCAGH9tffKMjGl+hFjwG2xWnLBJonEYH3nrG4Ac9a2ykLDpGmNF BW2dtlOgi3vqRJEzfOJjeUK6AYc/cC350MXzrhHc9TxN19QoyfJX2f31yczAjD4DlvTg o7eEHex+sS9K8Skj/KbMMUxjXPpYKjdBKjEaZYm2DHtF5LAfXmTI3K2dyLxhAgKs4SWj 5iJMKE6jtHqfjGwJrTZLRpTn69utqE/NmLiJramllwxAF9gcCssM1fLMAbbdkP0vm6ZK 4DHr29fRX0P+CLwQFkkDMBCNgamMpnmSv5Z+c2QfzoYa/JEtbv0Dwh6bA/gwGbFgwMxt JK1w== X-Gm-Message-State: AIkVDXLmqJjzfOPdDqgrP4I7LDhIpcphVt4Mk46W4ThZx5h9q9oZFv5WOsZW5u824h4k2mv3 X-Received: by 10.223.135.146 with SMTP id b18mr28631353wrb.189.1485274611039; Tue, 24 Jan 2017 08:16:51 -0800 (PST) Received: from localhost.localdomain ([160.163.215.165]) by smtp.gmail.com with ESMTPSA id n13sm17142511wrn.40.2017.01.24.08.16.48 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Tue, 24 Jan 2017 08:16:50 -0800 (PST) From: Ard Biesheuvel To: linux-kernel@vger.kernel.org Cc: linuxppc-dev@lists.ozlabs.org, akpm@linux-foundation.org, torvalds@linux-foundation.org, arnd@arndb.de, rusty@rustcorp.com.au, jeyu@redhat.com, mpe@ellerman.id.au, viro@zeniv.linux.org.uk, linux-arm-kernel@lists.infradead.org, linux@armlinux.org.uk, linux-arch@vger.kernel.org, Ard Biesheuvel Subject: [PATCH v4 1/2] kbuild: modversions: add infrastructure for emitting relative CRCs Date: Tue, 24 Jan 2017 16:16:39 +0000 Message-Id: <1485274600-21976-2-git-send-email-ard.biesheuvel@linaro.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1485274600-21976-1-git-send-email-ard.biesheuvel@linaro.org> References: <1485274600-21976-1-git-send-email-ard.biesheuvel@linaro.org> Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org This add the kbuild infrastructure that will allow architectures to emit vmlinux symbol CRCs as 32-bit offsets to other locations in the kernel where the actual values are stored. This works around problems with CRCs being mistaken for relocatable symbols on kernels that self relocate at runtime (i.e., powerpc with CONFIG_RELOCATABLE=y) For the kbuild side of things, this comes down to the following: - introducing a Kconfig symbol MODULE_REL_CRCS - adding a -R switch to genksyms to instruct it to emit the CRC symbols as references into the .rodata section, and emitting the actual value into it - making modpost distinguish such references from absolute CRC symbols by the section index (SHN_ABS) - making kallsyms disregard non-absolute symbols with a __crc_ prefix Signed-off-by: Ard Biesheuvel --- init/Kconfig | 4 ++++ scripts/Makefile.build | 2 ++ scripts/genksyms/genksyms.c | 19 ++++++++++++++----- scripts/kallsyms.c | 12 ++++++++++++ scripts/mod/modpost.c | 10 ++++++++++ 5 files changed, 42 insertions(+), 5 deletions(-) -- 2.7.4 diff --git a/init/Kconfig b/init/Kconfig index e1a937348a3e..4dd8bd232a1d 100644 --- a/init/Kconfig +++ b/init/Kconfig @@ -1987,6 +1987,10 @@ config MODVERSIONS make them incompatible with the kernel you are running. If unsure, say N. +config MODULE_REL_CRCS + bool + depends on MODVERSIONS + config MODULE_SRCVERSION_ALL bool "Source checksum for all modules" help diff --git a/scripts/Makefile.build b/scripts/Makefile.build index eadcd4d359d9..a9cfab2ee7c1 100644 --- a/scripts/Makefile.build +++ b/scripts/Makefile.build @@ -164,6 +164,7 @@ cmd_gensymtypes_c = \ $(CPP) -D__GENKSYMS__ $(c_flags) $< | \ $(GENKSYMS) $(if $(1), -T $(2)) \ $(patsubst y,-s _,$(CONFIG_HAVE_UNDERSCORE_SYMBOL_PREFIX)) \ + $(if $(part-of-module),,$(patsubst y,-R,$(CONFIG_MODULE_REL_CRCS))) \ $(if $(KBUILD_PRESERVE),-p) \ -r $(firstword $(wildcard $(2:.symtypes=.symref) /dev/null)) @@ -337,6 +338,7 @@ cmd_gensymtypes_S = \ $(CPP) -D__GENKSYMS__ $(c_flags) -xc - | \ $(GENKSYMS) $(if $(1), -T $(2)) \ $(patsubst y,-s _,$(CONFIG_HAVE_UNDERSCORE_SYMBOL_PREFIX)) \ + $(if $(part-of-module),,$(patsubst y,-R,$(CONFIG_MODULE_REL_CRCS))) \ $(if $(KBUILD_PRESERVE),-p) \ -r $(firstword $(wildcard $(2:.symtypes=.symref) /dev/null)) diff --git a/scripts/genksyms/genksyms.c b/scripts/genksyms/genksyms.c index 06121ce524a7..c9235d8340f1 100644 --- a/scripts/genksyms/genksyms.c +++ b/scripts/genksyms/genksyms.c @@ -44,7 +44,7 @@ char *cur_filename, *source_file; int in_source_file; static int flag_debug, flag_dump_defs, flag_reference, flag_dump_types, - flag_preserve, flag_warnings; + flag_preserve, flag_warnings, flag_rel_crcs; static const char *mod_prefix = ""; static int errors; @@ -693,7 +693,10 @@ void export_symbol(const char *name) fputs(">\n", debugfile); /* Used as a linker script. */ - printf("%s__crc_%s = 0x%08lx ;\n", mod_prefix, name, crc); + printf(!flag_rel_crcs ? "%s__crc_%s = 0x%08lx;\n" : + "SECTIONS { .rodata : ALIGN(4) { " + "%s__crc_%s = .; LONG(0x%08lx); } }\n", + mod_prefix, name, crc); } } @@ -730,7 +733,7 @@ void error_with_pos(const char *fmt, ...) static void genksyms_usage(void) { - fputs("Usage:\n" "genksyms [-adDTwqhV] > /path/to/.tmp_obj.ver\n" "\n" + fputs("Usage:\n" "genksyms [-adDTwqhVR] > /path/to/.tmp_obj.ver\n" "\n" #ifdef __GNU_LIBRARY__ " -s, --symbol-prefix Select symbol prefix\n" " -d, --debug Increment the debug level (repeatable)\n" @@ -742,6 +745,7 @@ static void genksyms_usage(void) " -q, --quiet Disable warnings (default)\n" " -h, --help Print this message\n" " -V, --version Print the release version\n" + " -R, --relative-crc Emit section relative symbol CRCs\n" #else /* __GNU_LIBRARY__ */ " -s Select symbol prefix\n" " -d Increment the debug level (repeatable)\n" @@ -753,6 +757,7 @@ static void genksyms_usage(void) " -q Disable warnings (default)\n" " -h Print this message\n" " -V Print the release version\n" + " -R Emit section relative symbol CRCs\n" #endif /* __GNU_LIBRARY__ */ , stderr); } @@ -774,13 +779,14 @@ int main(int argc, char **argv) {"preserve", 0, 0, 'p'}, {"version", 0, 0, 'V'}, {"help", 0, 0, 'h'}, + {"relative-crc", 0, 0, 'R'}, {0, 0, 0, 0} }; - while ((o = getopt_long(argc, argv, "s:dwqVDr:T:ph", + while ((o = getopt_long(argc, argv, "s:dwqVDr:T:phR", &long_opts[0], NULL)) != EOF) #else /* __GNU_LIBRARY__ */ - while ((o = getopt(argc, argv, "s:dwqVDr:T:ph")) != EOF) + while ((o = getopt(argc, argv, "s:dwqVDr:T:phR")) != EOF) #endif /* __GNU_LIBRARY__ */ switch (o) { case 's': @@ -823,6 +829,9 @@ int main(int argc, char **argv) case 'h': genksyms_usage(); return 0; + case 'R': + flag_rel_crcs = 1; + break; default: genksyms_usage(); return 1; diff --git a/scripts/kallsyms.c b/scripts/kallsyms.c index 299b92ca1ae0..5d554419170b 100644 --- a/scripts/kallsyms.c +++ b/scripts/kallsyms.c @@ -219,6 +219,10 @@ static int symbol_valid(struct sym_entry *s) "_SDA2_BASE_", /* ppc */ NULL }; + static char *special_prefixes[] = { + "__crc_", /* modversions */ + NULL }; + static char *special_suffixes[] = { "_veneer", /* arm */ "_from_arm", /* arm */ @@ -259,6 +263,14 @@ static int symbol_valid(struct sym_entry *s) if (strcmp(sym_name, special_symbols[i]) == 0) return 0; + for (i = 0; special_prefixes[i]; i++) { + int l = strlen(special_prefixes[i]); + + if (l <= strlen(sym_name) && + strncmp(sym_name, special_prefixes[i], l) == 0) + return 0; + } + for (i = 0; special_suffixes[i]; i++) { int l = strlen(sym_name) - strlen(special_suffixes[i]); diff --git a/scripts/mod/modpost.c b/scripts/mod/modpost.c index 29c89a6bad3d..ba89e5e953b5 100644 --- a/scripts/mod/modpost.c +++ b/scripts/mod/modpost.c @@ -619,8 +619,18 @@ static void handle_modversions(struct module *mod, struct elf_info *info, /* CRC'd symbol */ if (strncmp(symname, CRC_PFX, strlen(CRC_PFX)) == 0) { + unsigned int *crcp = NULL; + is_crc = true; crc = (unsigned int) sym->st_value; + if (sym->st_shndx != SHN_UNDEF && sym->st_shndx != SHN_ABS) { + /* symbol points to the CRC in the ELF object */ + crcp = (void *)info->hdr + sym->st_value + + info->sechdrs[sym->st_shndx].sh_offset - + (info->hdr->e_type != ET_REL ? + info->sechdrs[sym->st_shndx].sh_addr : 0); + crc = crcp ? *crcp : 0; + } sym_update_crc(symname + strlen(CRC_PFX), mod, crc, export); }