From 27eb9d65ff5121ed11979dd57d9ec2b6c2315c01 Mon Sep 17 00:00:00 2001 From: Richard Henderson Date: Mon, 22 Mar 2021 12:24:25 +0100 Subject: exec: Extract 'page-vary.h' header MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit In the next commit we will extract the generic code out of page-vary.c, only keeping the target specific code. Both files will use the same TargetPageBits structure, so make its declaration in a shared header. As the common header can not use target specific types, use a uint64_t to hold the page mask value, and add a cast back to target_long in the TARGET_PAGE_MASK definitions. Signed-off-by: Philippe Mathieu-Daudé Message-Id: <20210322112427.4045204-3-f4bug@amsat.org> Signed-off-by: Richard Henderson --- include/exec/cpu-all.h | 11 ++++------- include/exec/page-vary.h | 29 +++++++++++++++++++++++++++++ 2 files changed, 33 insertions(+), 7 deletions(-) create mode 100644 include/exec/page-vary.h (limited to 'include') diff --git a/include/exec/cpu-all.h b/include/exec/cpu-all.h index 76443eb..b0a422c 100644 --- a/include/exec/cpu-all.h +++ b/include/exec/cpu-all.h @@ -215,11 +215,7 @@ static inline void stl_phys_notdirty(AddressSpace *as, hwaddr addr, uint32_t val /* page related stuff */ #ifdef TARGET_PAGE_BITS_VARY -typedef struct { - bool decided; - int bits; - target_long mask; -} TargetPageBits; +# include "exec/page-vary.h" #if defined(CONFIG_ATTRIBUTE_ALIAS) || !defined(IN_EXEC_VARY) extern const TargetPageBits target_page; #else @@ -227,10 +223,11 @@ extern TargetPageBits target_page; #endif #ifdef CONFIG_DEBUG_TCG #define TARGET_PAGE_BITS ({ assert(target_page.decided); target_page.bits; }) -#define TARGET_PAGE_MASK ({ assert(target_page.decided); target_page.mask; }) +#define TARGET_PAGE_MASK ({ assert(target_page.decided); \ + (target_long)target_page.mask; }) #else #define TARGET_PAGE_BITS target_page.bits -#define TARGET_PAGE_MASK target_page.mask +#define TARGET_PAGE_MASK ((target_long)target_page.mask) #endif #define TARGET_PAGE_SIZE (-(int)TARGET_PAGE_MASK) #else diff --git a/include/exec/page-vary.h b/include/exec/page-vary.h new file mode 100644 index 0000000..799d631 --- /dev/null +++ b/include/exec/page-vary.h @@ -0,0 +1,29 @@ +/* + * Definitions for cpus with variable page sizes. + * + * Copyright (c) 2003 Fabrice Bellard + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ + +#ifndef EXEC_PAGE_VARY_H +#define EXEC_PAGE_VARY_H + +typedef struct { + bool decided; + int bits; + uint64_t mask; +} TargetPageBits; + +#endif /* EXEC_PAGE_VARY_H */ -- cgit v1.1 From 44b99a6d5f24afcd8476d0d2701e1ca4ab9b35c1 Mon Sep 17 00:00:00 2001 From: Richard Henderson Date: Mon, 22 Mar 2021 12:24:26 +0100 Subject: exec: Build page-vary-common.c with -fno-lto MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit In bbc17caf81f, we used an alias attribute to allow target_page to be declared const, and yet be initialized late. This fails when using LTO with several versions of gcc. The compiler looks through the alias and decides that the const variable is statically initialized to zero, then propagates that zero to many uses of the variable. This can be avoided by compiling one object file with -fno-lto. In this way, any initializer cannot be seen, and the constant propagation does not occur. Since we are certain to have this separate compilation unit, we can drop the alias attribute as well. We simply have differing declarations for target_page in different compilation units. Drop the use of init_target_page, and drop the configure detection for CONFIG_ATTRIBUTE_ALIAS. In order to change the compilation flags for a file with meson, we must use a static_library. This runs into specific_ss, where we would need to create many static_library instances. Fix this by splitting page-vary.c: the page-vary-common.c part is compiled once as a static_library, while the page-vary.c part is left in specific_ss in order to handle the target-specific value of TARGET_PAGE_BITS_MIN. Reported-by: Gavin Shan Signed-off-by: Richard Henderson Message-Id: <20210321211534.2101231-1-richard.henderson@linaro.org> [PMD: Fix typo in subject, split original patch in 3] Signed-off-by: Philippe Mathieu-Daudé Tested-by: Gavin Shan Message-Id: <20210322112427.4045204-4-f4bug@amsat.org> [rth: Update MAINTAINERS] Signed-off-by: Richard Henderson --- include/exec/cpu-all.h | 4 ---- include/exec/page-vary.h | 5 +++++ 2 files changed, 5 insertions(+), 4 deletions(-) (limited to 'include') diff --git a/include/exec/cpu-all.h b/include/exec/cpu-all.h index b0a422c..d76b0b9 100644 --- a/include/exec/cpu-all.h +++ b/include/exec/cpu-all.h @@ -216,11 +216,7 @@ static inline void stl_phys_notdirty(AddressSpace *as, hwaddr addr, uint32_t val #ifdef TARGET_PAGE_BITS_VARY # include "exec/page-vary.h" -#if defined(CONFIG_ATTRIBUTE_ALIAS) || !defined(IN_EXEC_VARY) extern const TargetPageBits target_page; -#else -extern TargetPageBits target_page; -#endif #ifdef CONFIG_DEBUG_TCG #define TARGET_PAGE_BITS ({ assert(target_page.decided); target_page.bits; }) #define TARGET_PAGE_MASK ({ assert(target_page.decided); \ diff --git a/include/exec/page-vary.h b/include/exec/page-vary.h index 799d631..c22a7a7 100644 --- a/include/exec/page-vary.h +++ b/include/exec/page-vary.h @@ -26,4 +26,9 @@ typedef struct { uint64_t mask; } TargetPageBits; +#ifdef IN_PAGE_VARY +extern bool set_preferred_target_page_bits_common(int bits); +extern void finalize_target_page_bits_common(int min); +#endif + #endif /* EXEC_PAGE_VARY_H */ -- cgit v1.1