From: Greg Kroah-Hartman Date: Thu, 4 Nov 2021 08:35:14 +0000 (+0100) Subject: 4.19-stable patches X-Git-Tag: v4.19.216~18 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=3acb3524d55e2d87015b53941c79b23965609697;p=thirdparty%2Fkernel%2Fstable-queue.git 4.19-stable patches added patches: arch-pgtable-define-max_possible_physmem_bits-where-needed.patch --- diff --git a/queue-4.19/arch-pgtable-define-max_possible_physmem_bits-where-needed.patch b/queue-4.19/arch-pgtable-define-max_possible_physmem_bits-where-needed.patch new file mode 100644 index 00000000000..890baf647a7 --- /dev/null +++ b/queue-4.19/arch-pgtable-define-max_possible_physmem_bits-where-needed.patch @@ -0,0 +1,188 @@ +From cef397038167ac15d085914493d6c86385773709 Mon Sep 17 00:00:00 2001 +From: Arnd Bergmann +Date: Wed, 11 Nov 2020 17:52:58 +0100 +Subject: arch: pgtable: define MAX_POSSIBLE_PHYSMEM_BITS where needed + +From: Arnd Bergmann + +commit cef397038167ac15d085914493d6c86385773709 upstream. + +Stefan Agner reported a bug when using zsram on 32-bit Arm machines +with RAM above the 4GB address boundary: + + Unable to handle kernel NULL pointer dereference at virtual address 00000000 + pgd = a27bd01c + [00000000] *pgd=236a0003, *pmd=1ffa64003 + Internal error: Oops: 207 [#1] SMP ARM + Modules linked in: mdio_bcm_unimac(+) brcmfmac cfg80211 brcmutil raspberrypi_hwmon hci_uart crc32_arm_ce bcm2711_thermal phy_generic genet + CPU: 0 PID: 123 Comm: mkfs.ext4 Not tainted 5.9.6 #1 + Hardware name: BCM2711 + PC is at zs_map_object+0x94/0x338 + LR is at zram_bvec_rw.constprop.0+0x330/0xa64 + pc : [] lr : [] psr: 60000013 + sp : e376bbe0 ip : 00000000 fp : c1e2921c + r10: 00000002 r9 : c1dda730 r8 : 00000000 + r7 : e8ff7a00 r6 : 00000000 r5 : 02f9ffa0 r4 : e3710000 + r3 : 000fdffe r2 : c1e0ce80 r1 : ebf979a0 r0 : 00000000 + Flags: nZCv IRQs on FIQs on Mode SVC_32 ISA ARM Segment user + Control: 30c5383d Table: 235c2a80 DAC: fffffffd + Process mkfs.ext4 (pid: 123, stack limit = 0x495a22e6) + Stack: (0xe376bbe0 to 0xe376c000) + +As it turns out, zsram needs to know the maximum memory size, which +is defined in MAX_PHYSMEM_BITS when CONFIG_SPARSEMEM is set, or in +MAX_POSSIBLE_PHYSMEM_BITS on the x86 architecture. + +The same problem will be hit on all 32-bit architectures that have a +physical address space larger than 4GB and happen to not enable sparsemem +and include asm/sparsemem.h from asm/pgtable.h. + +After the initial discussion, I suggested just always defining +MAX_POSSIBLE_PHYSMEM_BITS whenever CONFIG_PHYS_ADDR_T_64BIT is +set, or provoking a build error otherwise. This addresses all +configurations that can currently have this runtime bug, but +leaves all other configurations unchanged. + +I looked up the possible number of bits in source code and +datasheets, here is what I found: + + - on ARC, CONFIG_ARC_HAS_PAE40 controls whether 32 or 40 bits are used + - on ARM, CONFIG_LPAE enables 40 bit addressing, without it we never + support more than 32 bits, even though supersections in theory allow + up to 40 bits as well. + - on MIPS, some MIPS32r1 or later chips support 36 bits, and MIPS32r5 + XPA supports up to 60 bits in theory, but 40 bits are more than + anyone will ever ship + - On PowerPC, there are three different implementations of 36 bit + addressing, but 32-bit is used without CONFIG_PTE_64BIT + - On RISC-V, the normal page table format can support 34 bit + addressing. There is no highmem support on RISC-V, so anything + above 2GB is unused, but it might be useful to eventually support + CONFIG_ZRAM for high pages. + +Fixes: 61989a80fb3a ("staging: zsmalloc: zsmalloc memory allocation library") +Fixes: 02390b87a945 ("mm/zsmalloc: Prepare to variable MAX_PHYSMEM_BITS") +Acked-by: Thomas Bogendoerfer +Reviewed-by: Stefan Agner +Tested-by: Stefan Agner +Acked-by: Mike Rapoport +Link: https://lore.kernel.org/linux-mm/bdfa44bf1c570b05d6c70898e2bbb0acf234ecdf.1604762181.git.stefan@agner.ch/ +Signed-off-by: Arnd Bergmann +[florian: patch arch/powerpc/include/asm/pte-common.h for 4.19.y] +Signed-off-by: Florian Fainelli +Signed-off-by: Greg Kroah-Hartman +--- + arch/arc/include/asm/pgtable.h | 2 ++ + arch/arm/include/asm/pgtable-2level.h | 2 ++ + arch/arm/include/asm/pgtable-3level.h | 2 ++ + arch/mips/include/asm/pgtable-32.h | 3 +++ + arch/powerpc/include/asm/pte-common.h | 2 ++ + arch/riscv/include/asm/pgtable-32.h | 2 ++ + include/asm-generic/pgtable.h | 13 +++++++++++++ + 7 files changed, 26 insertions(+) + +--- a/arch/arc/include/asm/pgtable.h ++++ b/arch/arc/include/asm/pgtable.h +@@ -138,8 +138,10 @@ + + #ifdef CONFIG_ARC_HAS_PAE40 + #define PTE_BITS_NON_RWX_IN_PD1 (0xff00000000 | PAGE_MASK | _PAGE_CACHEABLE) ++#define MAX_POSSIBLE_PHYSMEM_BITS 40 + #else + #define PTE_BITS_NON_RWX_IN_PD1 (PAGE_MASK | _PAGE_CACHEABLE) ++#define MAX_POSSIBLE_PHYSMEM_BITS 32 + #endif + + /************************************************************************** +--- a/arch/arm/include/asm/pgtable-2level.h ++++ b/arch/arm/include/asm/pgtable-2level.h +@@ -78,6 +78,8 @@ + #define PTE_HWTABLE_OFF (PTE_HWTABLE_PTRS * sizeof(pte_t)) + #define PTE_HWTABLE_SIZE (PTRS_PER_PTE * sizeof(u32)) + ++#define MAX_POSSIBLE_PHYSMEM_BITS 32 ++ + /* + * PMD_SHIFT determines the size of the area a second-level page table can map + * PGDIR_SHIFT determines what a third-level page table entry can map +--- a/arch/arm/include/asm/pgtable-3level.h ++++ b/arch/arm/include/asm/pgtable-3level.h +@@ -37,6 +37,8 @@ + #define PTE_HWTABLE_OFF (0) + #define PTE_HWTABLE_SIZE (PTRS_PER_PTE * sizeof(u64)) + ++#define MAX_POSSIBLE_PHYSMEM_BITS 40 ++ + /* + * PGDIR_SHIFT determines the size a top-level page table entry can map. + */ +--- a/arch/mips/include/asm/pgtable-32.h ++++ b/arch/mips/include/asm/pgtable-32.h +@@ -111,6 +111,7 @@ static inline void pmd_clear(pmd_t *pmdp + + #if defined(CONFIG_XPA) + ++#define MAX_POSSIBLE_PHYSMEM_BITS 40 + #define pte_pfn(x) (((unsigned long)((x).pte_high >> _PFN_SHIFT)) | (unsigned long)((x).pte_low << _PAGE_PRESENT_SHIFT)) + static inline pte_t + pfn_pte(unsigned long pfn, pgprot_t prot) +@@ -126,6 +127,7 @@ pfn_pte(unsigned long pfn, pgprot_t prot + + #elif defined(CONFIG_PHYS_ADDR_T_64BIT) && defined(CONFIG_CPU_MIPS32) + ++#define MAX_POSSIBLE_PHYSMEM_BITS 36 + #define pte_pfn(x) ((unsigned long)((x).pte_high >> 6)) + + static inline pte_t pfn_pte(unsigned long pfn, pgprot_t prot) +@@ -140,6 +142,7 @@ static inline pte_t pfn_pte(unsigned lon + + #else + ++#define MAX_POSSIBLE_PHYSMEM_BITS 32 + #ifdef CONFIG_CPU_VR41XX + #define pte_pfn(x) ((unsigned long)((x).pte >> (PAGE_SHIFT + 2))) + #define pfn_pte(pfn, prot) __pte(((pfn) << (PAGE_SHIFT + 2)) | pgprot_val(prot)) +--- a/arch/powerpc/include/asm/pte-common.h ++++ b/arch/powerpc/include/asm/pte-common.h +@@ -110,8 +110,10 @@ static inline bool pte_user(pte_t pte) + */ + #if defined(CONFIG_PPC32) && defined(CONFIG_PTE_64BIT) + #define PTE_RPN_MASK (~((1ULL<