From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1754154AbbGXLus (ORCPT ); Fri, 24 Jul 2015 07:50:48 -0400 Received: from smtp02.citrix.com ([66.165.176.63]:21764 "EHLO SMTP02.CITRIX.COM" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752284AbbGXLsC (ORCPT ); Fri, 24 Jul 2015 07:48:02 -0400 X-IronPort-AV: E=Sophos;i="5.15,538,1432598400"; d="scan'208";a="287230488" From: David Vrabel To: CC: David Vrabel , Konrad Rzeszutek Wilk , Boris Ostrovsky , , , Daniel Kiper Subject: [PATCHv2 04/10] xen/balloon: find non-conflicting regions to place hotplugged memory Date: Fri, 24 Jul 2015 12:47:42 +0100 Message-ID: <1437738468-24110-5-git-send-email-david.vrabel@citrix.com> X-Mailer: git-send-email 2.1.4 In-Reply-To: <1437738468-24110-1-git-send-email-david.vrabel@citrix.com> References: <1437738468-24110-1-git-send-email-david.vrabel@citrix.com> MIME-Version: 1.0 Content-Type: text/plain X-DLP: MIA1 Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Instead of placing hotplugged memory at the end of RAM (which may conflict with PCI devices or reserved regions) use allocate_resource() to get a new, suitably aligned resource that does not conflict. Signed-off-by: David Vrabel Reviewed-by: Daniel Kiper --- drivers/xen/balloon.c | 64 +++++++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 54 insertions(+), 10 deletions(-) diff --git a/drivers/xen/balloon.c b/drivers/xen/balloon.c index fd93369..29aeb8f 100644 --- a/drivers/xen/balloon.c +++ b/drivers/xen/balloon.c @@ -54,6 +54,7 @@ #include #include #include +#include #include #include @@ -208,6 +209,43 @@ static bool balloon_is_inflated(void) return false; } +static struct resource *additional_memory_resource(phys_addr_t size) +{ + struct resource *res; + int ret; + + res = kzalloc(sizeof(*res), GFP_KERNEL); + if (!res) + return NULL; + + res->name = "System RAM"; + res->flags = IORESOURCE_MEM | IORESOURCE_BUSY; + + ret = allocate_resource(&iomem_resource, res, + size, 0, -1, + PAGES_PER_SECTION * PAGE_SIZE, NULL, NULL); + if (ret < 0) { + pr_err("Cannot allocate new System RAM resource\n"); + kfree(res); + return NULL; + } + + return res; +} + +static void release_memory_resource(struct resource *resource) +{ + if (!resource) + return; + + /* + * No need to reset region to identity mapped since we now + * know that no I/O can be in this region + */ + release_resource(resource); + kfree(resource); +} + /* * reserve_additional_memory() adds memory region of size >= credit above * max_pfn. New region is section aligned and size is modified to be multiple @@ -221,13 +259,17 @@ static bool balloon_is_inflated(void) static enum bp_state reserve_additional_memory(long credit) { + struct resource *resource; int nid, rc; - u64 hotplug_start_paddr; - unsigned long balloon_hotplug = credit; + unsigned long balloon_hotplug; + + balloon_hotplug = round_up(credit, PAGES_PER_SECTION); + + resource = additional_memory_resource(balloon_hotplug * PAGE_SIZE); + if (!resource) + goto err; - hotplug_start_paddr = PFN_PHYS(SECTION_ALIGN_UP(max_pfn)); - balloon_hotplug = round_up(balloon_hotplug, PAGES_PER_SECTION); - nid = memory_add_physaddr_to_nid(hotplug_start_paddr); + nid = memory_add_physaddr_to_nid(resource->start); #ifdef CONFIG_XEN_HAVE_PVMMU /* @@ -242,21 +284,20 @@ static enum bp_state reserve_additional_memory(long credit) if (!xen_feature(XENFEAT_auto_translated_physmap)) { unsigned long pfn, i; - pfn = PFN_DOWN(hotplug_start_paddr); + pfn = PFN_DOWN(resource->start); for (i = 0; i < balloon_hotplug; i++) { if (!set_phys_to_machine(pfn + i, INVALID_P2M_ENTRY)) { pr_warn("set_phys_to_machine() failed, no memory added\n"); - return BP_ECANCELED; + goto err; } } } #endif - rc = add_memory(nid, hotplug_start_paddr, balloon_hotplug << PAGE_SHIFT); - + rc = add_memory_resource(nid, resource); if (rc) { pr_warn("Cannot add additional memory (%i)\n", rc); - return BP_ECANCELED; + goto err; } balloon_hotplug -= credit; @@ -265,6 +306,9 @@ static enum bp_state reserve_additional_memory(long credit) balloon_stats.balloon_hotplug = balloon_hotplug; return BP_DONE; + err: + release_memory_resource(resource); + return BP_ECANCELED; } static void xen_online_page(struct page *page) -- 2.1.4 From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail-yk0-f176.google.com (mail-yk0-f176.google.com [209.85.160.176]) by kanga.kvack.org (Postfix) with ESMTP id 80C6F9003C7 for ; Fri, 24 Jul 2015 07:48:02 -0400 (EDT) Received: by ykdu72 with SMTP id u72so17385908ykd.2 for ; Fri, 24 Jul 2015 04:48:02 -0700 (PDT) Received: from SMTP02.CITRIX.COM (smtp02.citrix.com. [66.165.176.63]) by mx.google.com with ESMTPS id y139si5871632yke.97.2015.07.24.04.48.01 for (version=TLSv1 cipher=ECDHE-RSA-RC4-SHA bits=128/128); Fri, 24 Jul 2015 04:48:01 -0700 (PDT) From: David Vrabel Subject: [PATCHv2 04/10] xen/balloon: find non-conflicting regions to place hotplugged memory Date: Fri, 24 Jul 2015 12:47:42 +0100 Message-ID: <1437738468-24110-5-git-send-email-david.vrabel@citrix.com> In-Reply-To: <1437738468-24110-1-git-send-email-david.vrabel@citrix.com> References: <1437738468-24110-1-git-send-email-david.vrabel@citrix.com> MIME-Version: 1.0 Content-Type: text/plain Sender: owner-linux-mm@kvack.org List-ID: To: xen-devel@lists.xenproject.org Cc: David Vrabel , Konrad Rzeszutek Wilk , Boris Ostrovsky , linux-kernel@vger.kernel.org, linux-mm@kvack.org, Daniel Kiper Instead of placing hotplugged memory at the end of RAM (which may conflict with PCI devices or reserved regions) use allocate_resource() to get a new, suitably aligned resource that does not conflict. Signed-off-by: David Vrabel Reviewed-by: Daniel Kiper --- drivers/xen/balloon.c | 64 +++++++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 54 insertions(+), 10 deletions(-) diff --git a/drivers/xen/balloon.c b/drivers/xen/balloon.c index fd93369..29aeb8f 100644 --- a/drivers/xen/balloon.c +++ b/drivers/xen/balloon.c @@ -54,6 +54,7 @@ #include #include #include +#include #include #include @@ -208,6 +209,43 @@ static bool balloon_is_inflated(void) return false; } +static struct resource *additional_memory_resource(phys_addr_t size) +{ + struct resource *res; + int ret; + + res = kzalloc(sizeof(*res), GFP_KERNEL); + if (!res) + return NULL; + + res->name = "System RAM"; + res->flags = IORESOURCE_MEM | IORESOURCE_BUSY; + + ret = allocate_resource(&iomem_resource, res, + size, 0, -1, + PAGES_PER_SECTION * PAGE_SIZE, NULL, NULL); + if (ret < 0) { + pr_err("Cannot allocate new System RAM resource\n"); + kfree(res); + return NULL; + } + + return res; +} + +static void release_memory_resource(struct resource *resource) +{ + if (!resource) + return; + + /* + * No need to reset region to identity mapped since we now + * know that no I/O can be in this region + */ + release_resource(resource); + kfree(resource); +} + /* * reserve_additional_memory() adds memory region of size >= credit above * max_pfn. New region is section aligned and size is modified to be multiple @@ -221,13 +259,17 @@ static bool balloon_is_inflated(void) static enum bp_state reserve_additional_memory(long credit) { + struct resource *resource; int nid, rc; - u64 hotplug_start_paddr; - unsigned long balloon_hotplug = credit; + unsigned long balloon_hotplug; + + balloon_hotplug = round_up(credit, PAGES_PER_SECTION); + + resource = additional_memory_resource(balloon_hotplug * PAGE_SIZE); + if (!resource) + goto err; - hotplug_start_paddr = PFN_PHYS(SECTION_ALIGN_UP(max_pfn)); - balloon_hotplug = round_up(balloon_hotplug, PAGES_PER_SECTION); - nid = memory_add_physaddr_to_nid(hotplug_start_paddr); + nid = memory_add_physaddr_to_nid(resource->start); #ifdef CONFIG_XEN_HAVE_PVMMU /* @@ -242,21 +284,20 @@ static enum bp_state reserve_additional_memory(long credit) if (!xen_feature(XENFEAT_auto_translated_physmap)) { unsigned long pfn, i; - pfn = PFN_DOWN(hotplug_start_paddr); + pfn = PFN_DOWN(resource->start); for (i = 0; i < balloon_hotplug; i++) { if (!set_phys_to_machine(pfn + i, INVALID_P2M_ENTRY)) { pr_warn("set_phys_to_machine() failed, no memory added\n"); - return BP_ECANCELED; + goto err; } } } #endif - rc = add_memory(nid, hotplug_start_paddr, balloon_hotplug << PAGE_SHIFT); - + rc = add_memory_resource(nid, resource); if (rc) { pr_warn("Cannot add additional memory (%i)\n", rc); - return BP_ECANCELED; + goto err; } balloon_hotplug -= credit; @@ -265,6 +306,9 @@ static enum bp_state reserve_additional_memory(long credit) balloon_stats.balloon_hotplug = balloon_hotplug; return BP_DONE; + err: + release_memory_resource(resource); + return BP_ECANCELED; } static void xen_online_page(struct page *page) -- 2.1.4 -- To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to majordomo@kvack.org. For more info on Linux MM, see: http://www.linux-mm.org/ . Don't email: email@kvack.org