Received: by 10.213.65.68 with SMTP id h4csp88314imn; Fri, 30 Mar 2018 01:18:10 -0700 (PDT) X-Google-Smtp-Source: AIpwx4/ZX60h3tAUjvFCc+9EOYgulrCbirXQdiz69SVBuH4JDuM3N6KNPWIfhcqV6Xy5xL+UZ1+n X-Received: by 10.98.253.17 with SMTP id p17mr9065362pfh.105.1522397890197; Fri, 30 Mar 2018 01:18:10 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1522397890; cv=none; d=google.com; s=arc-20160816; b=mHRK/h7hCLcU6IKl7PuSPTkmuqxZRMvtwQ8kKIlW+Kfl3zgIyeSzU1R/ix3ttHhntJ Z0dZgI57lsXn+pt7g4dhc9mC3N264lJpMNnDjWpf/R48oKhCbz/240khY0yf3lJ0c4T5 LLYjIEL1RpwOA1WIZt3YE0pbziVtL6dfcZ690oIN4Mv0F53wAzB5JcSp+h6LQ0OZUj2N sSphQcf00VGJQE+53K56DJ7RGzUQpCDPBJyZkfMeOl/DWJ/hC+74LHVI5tVyJL7sBbs9 2+jhCD0xkzj6gXLRY8b/DWL1lyohTFbRyXnB7rO23R/oJF1srjzIE0IvZHxEs0d6bvrq Ynpw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:references:in-reply-to:message-id:date :subject:cc:to:from:dkim-signature:arc-authentication-results; bh=wG4eG8g85RYT7S7ST1+KqNO2x+rwpOwBbjh5gR0j/YI=; b=no0qlvTsnin0rv7DK1oWCdEfzX7gz4BJaRyzmjj7383nUQqtiAj0L61VuHn6dA5W6s bQT+Pyj8SzaYtVf61q0MXZkROEHnN2AY1nw+CDpmhuUbdtU7L2RkHoTUiWyKpxsX9vyN tl7i+CKRr7s3G44rYjMm1VQn2M2dAend2rMxxUCfOehP4Ty+gQhdhvL77DwYAsSeNJTv 7aiNKbQag5EDsQEkNvZ/rWp0gO6rqskxhu4729MocE6Wa0p9WJC7OIrSVvsUeSa7i1gE LGo0d54j0toGXOAfrOLQLjkt5bRzsKMAbjtJSnHah6mufzDilvMFiV7HOdLcSagmMrDm r+Bw== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@gmail.com header.s=20161025 header.b=kcHeXujA; 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=QUARANTINE dis=NONE) header.from=gmail.com Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id r1-v6si8084126plb.430.2018.03.30.01.17.56; Fri, 30 Mar 2018 01:18:10 -0700 (PDT) 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=@gmail.com header.s=20161025 header.b=kcHeXujA; 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=QUARANTINE dis=NONE) header.from=gmail.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751243AbeC3IQl (ORCPT + 99 others); Fri, 30 Mar 2018 04:16:41 -0400 Received: from mail-pg0-f66.google.com ([74.125.83.66]:37397 "EHLO mail-pg0-f66.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751167AbeC3IQh (ORCPT ); Fri, 30 Mar 2018 04:16:37 -0400 Received: by mail-pg0-f66.google.com with SMTP id n11so4707241pgp.4 for ; Fri, 30 Mar 2018 01:16:36 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=wG4eG8g85RYT7S7ST1+KqNO2x+rwpOwBbjh5gR0j/YI=; b=kcHeXujA8vwTzp/eroUXZgw+XBwqHx5c3X1bVlefyyRupPMYSYl9thCTyzJ2hwoFlU oSwigB5WaImBi0WmwgmP6ASAwKJpcDUEo4/MyQpLMUDVRPSqQsnWG82w8uwP9r9aO06p j9BRwohpm85O6pJTiiF1ZmOHPbEebwwmP6HXBn+OTZLYN/kxN2c0HAtCCt5p4i6cnBBh cfDkBIcCj8fIigAJp3QmZCniRSjlHTXc/Wuq0Wgs/3fpuLIfK+rD2PFcb4mBOlsmY2ht A0Zfjibh+t1mCqmP6PMDDkHYmtctb1CMSMlokE/a8PelpjayAkAUH1MI3ztKaHZIkmpb lcWA== 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=wG4eG8g85RYT7S7ST1+KqNO2x+rwpOwBbjh5gR0j/YI=; b=TG2+feUyrsxFvxr3SKRTYdwP90HNtyrhhdHtVJcT2J/Shgqk+qn0WnhKN2bK1XyuK0 Nk2T26bPIUT5F/TjVCeZVQhPSmzvYaHiYHpIlGDbCxGvSxbl+2luLm58qu+fcQNRAvas /FopwKgomvqLDL3AvxXR/pt7J/8RSOtetcwIen0EEXirmOsrGlPmJ/qbZ+VI8hDJdy6u ZVXr6ODQFbh3jhVwtzlGsKYWUD6qvItH9b7r2QYYYc/9FwFvCEKAZCi/g8XMJUlQ56pV xBBGmbthr47rBtW3tMJB+zTr+y392phaLfJ3fsJRY3tdWt74+I8Ry23L0YgE4r4w4h1b pB+Q== X-Gm-Message-State: AElRT7GYDBvlS4xmt007f8Ad40YkF4vGVJbaHXeH90ix0Euf8iicNpcg qcvGZMt1irxZCK+grwUH8vg= X-Received: by 10.101.75.81 with SMTP id k17mr7978167pgt.335.1522397795820; Fri, 30 Mar 2018 01:16:35 -0700 (PDT) Received: from localhost.localdomain ([38.106.11.25]) by smtp.gmail.com with ESMTPSA id l8sm4269837pff.126.2018.03.30.01.16.22 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Fri, 30 Mar 2018 01:16:35 -0700 (PDT) From: Jia He To: Russell King , Andrew Morton , Michal Hocko , Catalin Marinas , Mel Gorman , Will Deacon , Mark Rutland , "H. Peter Anvin" Cc: Pavel Tatashin , Daniel Jordan , AKASHI Takahiro , Gioh Kim , Steven Sistare , Daniel Vacek , Eugeniu Rosca , Vlastimil Babka , linux-kernel@vger.kernel.org, linux-mm@kvack.org, James Morse , Ard Biesheuvel , Steve Capper , Thomas Gleixner , Ingo Molnar , x86@kernel.org, Greg Kroah-Hartman , Kate Stewart , Philippe Ombredanne , Johannes Weiner , Kemi Wang , Petr Tesarik , YASUAKI ISHIMATSU , Andrey Ryabinin , Nikolay Borisov , richard.weiyang@gmail.com, Jia He , Jia He Subject: [PATCH v4 1/5] mm: page_alloc: remain memblock_next_valid_pfn() on arm and arm64 Date: Fri, 30 Mar 2018 01:15:51 -0700 Message-Id: <1522397755-33393-2-git-send-email-hejianet@gmail.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1522397755-33393-1-git-send-email-hejianet@gmail.com> References: <1522397755-33393-1-git-send-email-hejianet@gmail.com> Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Commit b92df1de5d28 ("mm: page_alloc: skip over regions of invalid pfns where possible") optimized the loop in memmap_init_zone(). But it causes possible panic bug. So Daniel Vacek reverted it later. But as suggested by Daniel Vacek, it is fine to using memblock to skip gaps and finding next valid frame with CONFIG_HAVE_ARCH_PFN_VALID. On arm and arm64, memblock is used by default. But generic version of pfn_valid() is based on mem sections and memblock_next_valid_pfn() does not always return the next valid one but skips more resulting in some valid frames to be skipped (as if they were invalid). And that's why kernel was eventually crashing on some !arm machines. And as verified by Eugeniu Rosca, arm can benifit from commit b92df1de5d28. So remain the memblock_next_valid_pfn on arm{,64} and move the related codes to arm64 arch directory. Suggested-by: Daniel Vacek Signed-off-by: Jia He --- arch/arm/mm/init.c | 31 ++++++++++++++++++++++++++++++- arch/arm64/mm/init.c | 31 ++++++++++++++++++++++++++++++- mm/page_alloc.c | 13 ++++++++++++- 3 files changed, 72 insertions(+), 3 deletions(-) diff --git a/arch/arm/mm/init.c b/arch/arm/mm/init.c index a1f11a7..0fb85ca 100644 --- a/arch/arm/mm/init.c +++ b/arch/arm/mm/init.c @@ -198,7 +198,36 @@ int pfn_valid(unsigned long pfn) return memblock_is_map_memory(__pfn_to_phys(pfn)); } EXPORT_SYMBOL(pfn_valid); -#endif + +/* HAVE_MEMBLOCK is always enabled on arm */ +unsigned long __init_memblock memblock_next_valid_pfn(unsigned long pfn) +{ + struct memblock_type *type = &memblock.memory; + unsigned int right = type->cnt; + unsigned int mid, left = 0; + phys_addr_t addr = PFN_PHYS(++pfn); + + do { + mid = (right + left) / 2; + + if (addr < type->regions[mid].base) + right = mid; + else if (addr >= (type->regions[mid].base + + type->regions[mid].size)) + left = mid + 1; + else { + /* addr is within the region, so pfn is valid */ + return pfn; + } + } while (left < right); + + if (right == type->cnt) + return -1UL; + else + return PHYS_PFN(type->regions[right].base); +} +EXPORT_SYMBOL(memblock_next_valid_pfn); +#endif /*CONFIG_HAVE_ARCH_PFN_VALID*/ #ifndef CONFIG_SPARSEMEM static void __init arm_memory_present(void) diff --git a/arch/arm64/mm/init.c b/arch/arm64/mm/init.c index 00e7b90..13e43ff 100644 --- a/arch/arm64/mm/init.c +++ b/arch/arm64/mm/init.c @@ -290,7 +290,36 @@ int pfn_valid(unsigned long pfn) return memblock_is_map_memory(pfn << PAGE_SHIFT); } EXPORT_SYMBOL(pfn_valid); -#endif + +/* HAVE_MEMBLOCK is always enabled on arm64 */ +unsigned long __init_memblock memblock_next_valid_pfn(unsigned long pfn) +{ + struct memblock_type *type = &memblock.memory; + unsigned int right = type->cnt; + unsigned int mid, left = 0; + phys_addr_t addr = PFN_PHYS(++pfn); + + do { + mid = (right + left) / 2; + + if (addr < type->regions[mid].base) + right = mid; + else if (addr >= (type->regions[mid].base + + type->regions[mid].size)) + left = mid + 1; + else { + /* addr is within the region, so pfn is valid */ + return pfn; + } + } while (left < right); + + if (right == type->cnt) + return -1UL; + else + return PHYS_PFN(type->regions[right].base); +} +EXPORT_SYMBOL(memblock_next_valid_pfn); +#endif /*CONFIG_HAVE_ARCH_PFN_VALID*/ #ifndef CONFIG_SPARSEMEM static void __init arm64_memory_present(void) diff --git a/mm/page_alloc.c b/mm/page_alloc.c index c19f5ac..8a92df7 100644 --- a/mm/page_alloc.c +++ b/mm/page_alloc.c @@ -5452,6 +5452,15 @@ void __ref build_all_zonelists(pg_data_t *pgdat) * up by free_all_bootmem() once the early boot process is * done. Non-atomic initialization, single-pass. */ +#if (defined CONFIG_HAVE_MEMBLOCK) && (defined CONFIG_HAVE_ARCH_PFN_VALID) +extern unsigned long memblock_next_valid_pfn(unsigned long pfn); +#define skip_to_last_invalid_pfn(pfn) (memblock_next_valid_pfn(pfn) - 1) +#endif + +#ifndef skip_to_last_invalid_pfn +#define skip_to_last_invalid_pfn(pfn) (pfn) +#endif + void __meminit memmap_init_zone(unsigned long size, int nid, unsigned long zone, unsigned long start_pfn, enum memmap_context context, struct vmem_altmap *altmap) @@ -5483,8 +5492,10 @@ void __meminit memmap_init_zone(unsigned long size, int nid, unsigned long zone, if (context != MEMMAP_EARLY) goto not_early; - if (!early_pfn_valid(pfn)) + if (!early_pfn_valid(pfn)) { + pfn = skip_to_last_invalid_pfn(pfn); continue; + } if (!early_pfn_in_nid(pfn, nid)) continue; if (!update_defer_init(pgdat, pfn, end_pfn, &nr_initialised)) -- 2.7.4