Received: by 2002:a6b:500f:0:0:0:0:0 with SMTP id e15csp3280169iob; Mon, 16 May 2022 18:01:09 -0700 (PDT) X-Google-Smtp-Source: ABdhPJxOW/7qE8gvANt1vV/PMxnfE6dlfgPnW+0T2WalNqKaOFkGmFcO4BCwpz0EKNP5i0cjneGS X-Received: by 2002:a17:906:2319:b0:6f3:ad55:8fee with SMTP id l25-20020a170906231900b006f3ad558feemr17407538eja.26.1652749269568; Mon, 16 May 2022 18:01:09 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1652749269; cv=none; d=google.com; s=arc-20160816; b=EPtkLf3eRrdGfJV/mZ5uMJuwrx5HzT4DnwbPLRLT6eu9u5VDGcaiDPKyueGyF0AZxk 2eQrzIjewayo7mfBZY6gM3Q4ZYu5RtS3Tc1h4go8RsexpLR+3VvMjy6qDY1iQlBf3Uvt UYZPWcKTYlRyVR1KeZhBHLmyw4UsOh6X3Y08J65tuValcABWV4E+Dc5elPHriYJwBqr8 sF6J0kRlk0AKOSd8h2cBo7+ucZ29dCUrC5kekYmWsWzlt5JaA0mDbP3BaIOH3qe4/hOk Amx1KQxVJYqZkODMd7S9O1nlyZ9EVReqI/iwCvavHnsIoFGCBBv8eOWxWN6CQMnbcOkT 7PYQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :user-agent:references:in-reply-to:message-id:date:subject:cc:to :from:dkim-signature; bh=fG2M6iwwmNI7JU0WT1L+AbKkVcaVrdxmrbuP8R9RuFI=; b=d1UGyCTGBpdfyECjYWFu3ZKlHHEcanrP4zSNNzFuj6MwI2QAjJz5hUNnPsqG3rlM8G mIwBwgz+RsP/2YF/SjFoKNY3S0Z34gdwx7KcphKC/6eIR9ZHFzvG6OyGgHRNX2p27zEV Aod9E6Z9YUWwYPhgCHBUAVEhk+K8X1M5/NW15L44W8XlVzhXAHJe3RqPmgJGwMbm5aJ/ AuN2CbQao4Sa6TF6lTK2o80lq3tIiMTMRXby3xXkgaibUOOsQgGI37Gj1OOH1glbM9/v tZvZZgo0pMcpAwS5w6Z8cXU/twXdA+BJAwZO69/yti2/94SdtIWQvbVbCLWzd38xQA8m OgfA== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@linuxfoundation.org header.s=korg header.b=LvDSy+v+; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linuxfoundation.org Return-Path: Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id d21-20020a056402517500b0042ab983c22csi2578713ede.172.2022.05.16.18.00.43; Mon, 16 May 2022 18:01:09 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@linuxfoundation.org header.s=korg header.b=LvDSy+v+; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linuxfoundation.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S234778AbiEPUUJ (ORCPT + 99 others); Mon, 16 May 2022 16:20:09 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:43292 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1348899AbiEPT7C (ORCPT ); Mon, 16 May 2022 15:59:02 -0400 Received: from dfw.source.kernel.org (dfw.source.kernel.org [IPv6:2604:1380:4641:c500::1]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 1513C11A25; Mon, 16 May 2022 12:52:19 -0700 (PDT) Received: from smtp.kernel.org (relay.kernel.org [52.25.139.140]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by dfw.source.kernel.org (Postfix) with ESMTPS id A4EBA60EC4; Mon, 16 May 2022 19:52:18 +0000 (UTC) Received: by smtp.kernel.org (Postfix) with ESMTPSA id 7CB94C34100; Mon, 16 May 2022 19:52:17 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=linuxfoundation.org; s=korg; t=1652730738; bh=QXojrCr7nRJCNk0udtwkEUMobSAQqpoeUp8T8wc32mo=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=LvDSy+v+/8XHAv/knhv3HA9h8SXRjNI5hDPrGc4W8qXQ4Rcu7Xm/kuH2H3BdD2HMV XUs0BOkie08M8jpZ64ye/tekr3EYeDkUIRevQ+Sbdba44RWi2NqTLQlU+jLTv3dy8X EuxLFcdnFjF7H88+wCOUau+lpNMYOXUY+XrDuPsI= From: Greg Kroah-Hartman To: linux-kernel@vger.kernel.org Cc: Greg Kroah-Hartman , stable@vger.kernel.org, Mike Rapoport , "kernelci.org bot" , Mark Brown , Ard Biesheuvel , Catalin Marinas , Mark-PK Tsai , Russell King , Tony Lindgren , Will Deacon , Andrew Morton Subject: [PATCH 5.15 091/102] arm[64]/memremap: dont abuse pfn_valid() to ensure presence of linear map Date: Mon, 16 May 2022 21:37:05 +0200 Message-Id: <20220516193626.610488471@linuxfoundation.org> X-Mailer: git-send-email 2.36.1 In-Reply-To: <20220516193623.989270214@linuxfoundation.org> References: <20220516193623.989270214@linuxfoundation.org> User-Agent: quilt/0.66 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-Spam-Status: No, score=-7.4 required=5.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,RCVD_IN_DNSWL_HI, SPF_HELO_NONE,SPF_PASS,T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: Mike Rapoport commit 260364d112bc822005224667c0c9b1b17a53eafd upstream. The semantics of pfn_valid() is to check presence of the memory map for a PFN and not whether a PFN is covered by the linear map. The memory map may be present for NOMAP memory regions, but they won't be mapped in the linear mapping. Accessing such regions via __va() when they are memremap()'ed will cause a crash. On v5.4.y the crash happens on qemu-arm with UEFI [1]: <1>[ 0.084476] 8<--- cut here --- <1>[ 0.084595] Unable to handle kernel paging request at virtual address dfb76000 <1>[ 0.084938] pgd = (ptrval) <1>[ 0.085038] [dfb76000] *pgd=5f7fe801, *pte=00000000, *ppte=00000000 ... <4>[ 0.093923] [] (memcpy) from [] (dmi_setup+0x60/0x418) <4>[ 0.094204] [] (dmi_setup) from [] (arm_dmi_init+0x8/0x10) <4>[ 0.094408] [] (arm_dmi_init) from [] (do_one_initcall+0x50/0x228) <4>[ 0.094619] [] (do_one_initcall) from [] (kernel_init_freeable+0x15c/0x1f8) <4>[ 0.094841] [] (kernel_init_freeable) from [] (kernel_init+0x8/0x10c) <4>[ 0.095057] [] (kernel_init) from [] (ret_from_fork+0x14/0x2c) On kernels v5.10.y and newer the same crash won't reproduce on ARM because commit b10d6bca8720 ("arch, drivers: replace for_each_membock() with for_each_mem_range()") changed the way memory regions are registered in the resource tree, but that merely covers up the problem. On ARM64 memory resources registered in yet another way and there the issue of wrong usage of pfn_valid() to ensure availability of the linear map is also covered. Implement arch_memremap_can_ram_remap() on ARM and ARM64 to prevent access to NOMAP regions via the linear mapping in memremap(). Link: https://lore.kernel.org/all/Yl65zxGgFzF1Okac@sirena.org.uk Link: https://lkml.kernel.org/r/20220426060107.7618-1-rppt@kernel.org Signed-off-by: Mike Rapoport Reported-by: "kernelci.org bot" Tested-by: Mark Brown Reviewed-by: Ard Biesheuvel Acked-by: Catalin Marinas Cc: Greg Kroah-Hartman Cc: Mark Brown Cc: Mark-PK Tsai Cc: Russell King Cc: Tony Lindgren Cc: Will Deacon Cc: [5.4+] Signed-off-by: Andrew Morton Signed-off-by: Greg Kroah-Hartman --- arch/arm/include/asm/io.h | 3 +++ arch/arm/mm/ioremap.c | 8 ++++++++ arch/arm64/include/asm/io.h | 4 ++++ arch/arm64/mm/ioremap.c | 8 ++++++++ 4 files changed, 23 insertions(+) --- a/arch/arm/include/asm/io.h +++ b/arch/arm/include/asm/io.h @@ -436,6 +436,9 @@ extern void pci_iounmap(struct pci_dev * #define ARCH_HAS_VALID_PHYS_ADDR_RANGE extern int valid_phys_addr_range(phys_addr_t addr, size_t size); extern int valid_mmap_phys_addr_range(unsigned long pfn, size_t size); +extern bool arch_memremap_can_ram_remap(resource_size_t offset, size_t size, + unsigned long flags); +#define arch_memremap_can_ram_remap arch_memremap_can_ram_remap #endif /* --- a/arch/arm/mm/ioremap.c +++ b/arch/arm/mm/ioremap.c @@ -479,3 +479,11 @@ void __init early_ioremap_init(void) { early_ioremap_setup(); } + +bool arch_memremap_can_ram_remap(resource_size_t offset, size_t size, + unsigned long flags) +{ + unsigned long pfn = PHYS_PFN(offset); + + return memblock_is_map_memory(pfn); +} --- a/arch/arm64/include/asm/io.h +++ b/arch/arm64/include/asm/io.h @@ -192,4 +192,8 @@ extern void __iomem *ioremap_cache(phys_ extern int valid_phys_addr_range(phys_addr_t addr, size_t size); extern int valid_mmap_phys_addr_range(unsigned long pfn, size_t size); +extern bool arch_memremap_can_ram_remap(resource_size_t offset, size_t size, + unsigned long flags); +#define arch_memremap_can_ram_remap arch_memremap_can_ram_remap + #endif /* __ASM_IO_H */ --- a/arch/arm64/mm/ioremap.c +++ b/arch/arm64/mm/ioremap.c @@ -99,3 +99,11 @@ void __init early_ioremap_init(void) { early_ioremap_setup(); } + +bool arch_memremap_can_ram_remap(resource_size_t offset, size_t size, + unsigned long flags) +{ + unsigned long pfn = PHYS_PFN(offset); + + return pfn_is_map_memory(pfn); +}