All of lore.kernel.org
 help / color / mirror / Atom feed
From: David Gibson <david@gibson.dropbear.id.au>
To: groug@kaod.org, abologna@redhat.com
Cc: aik@ozlabs.ru, qemu-ppc@nongnu.org, qemu-devel@nongnu.org,
	clg@kaod.org, David Gibson <david@gibson.dropbear.id.au>
Subject: [Qemu-devel] [RFC for-2.13 2/7] spapr: Use maximum page size capability to simplify memory backend checking
Date: Thu, 19 Apr 2018 16:29:12 +1000	[thread overview]
Message-ID: <20180419062917.31486-3-david@gibson.dropbear.id.au> (raw)
In-Reply-To: <20180419062917.31486-1-david@gibson.dropbear.id.au>

The way we used to handle KVM allowable guest pagesizes for PAPR guests
required some convoluted checking of memory attached to the guest.

The allowable pagesizes advertised to the guest cpus depended on the memory
which was attached at boot, but then we needed to ensure that any memory
later hotplugged didn't change which pagesizes were allowed.

Now that we have an explicit machine option to control the allowable
maximum pagesize we can simplify this.  We just check all memory backends
against that declared pagesize.  We check base and cold-plugged memory at
reset time, and hotplugged memory at pre_plug() time.

Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
---
 hw/ppc/spapr.c         | 17 +++++++----------
 hw/ppc/spapr_caps.c    | 20 ++++++++++++++++++++
 include/hw/ppc/spapr.h |  3 +++
 target/ppc/kvm.c       | 19 ++++++++++---------
 target/ppc/kvm_ppc.h   |  6 +++---
 5 files changed, 43 insertions(+), 22 deletions(-)

diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c
index 36e41aff71..0a0fec4140 100644
--- a/hw/ppc/spapr.c
+++ b/hw/ppc/spapr.c
@@ -3035,11 +3035,13 @@ out:
 static void spapr_memory_pre_plug(HotplugHandler *hotplug_dev, DeviceState *dev,
                                   Error **errp)
 {
+    sPAPRMachineState *spapr = SPAPR_MACHINE(hotplug_dev);
     PCDIMMDevice *dimm = PC_DIMM(dev);
     PCDIMMDeviceClass *ddc = PC_DIMM_GET_CLASS(dimm);
     MemoryRegion *mr;
     uint64_t size;
-    char *mem_dev;
+    Object *memdev;
+    hwaddr pagesize;
 
     mr = ddc->get_memory_region(dimm, errp);
     if (!mr) {
@@ -3053,15 +3055,10 @@ static void spapr_memory_pre_plug(HotplugHandler *hotplug_dev, DeviceState *dev,
         return;
     }
 
-    mem_dev = object_property_get_str(OBJECT(dimm), PC_DIMM_MEMDEV_PROP, NULL);
-    if (mem_dev && !kvmppc_is_mem_backend_page_size_ok(mem_dev)) {
-        error_setg(errp, "Memory backend has bad page size. "
-                   "Use 'memory-backend-file' with correct mem-path.");
-        goto out;
-    }
-
-out:
-    g_free(mem_dev);
+    memdev = object_property_get_link(OBJECT(dimm), PC_DIMM_MEMDEV_PROP,
+                                      &error_abort);
+    pagesize = host_memory_backend_pagesize(MEMORY_BACKEND(memdev));
+    spapr_check_pagesize(spapr, pagesize, errp);
 }
 
 struct sPAPRDIMMState {
diff --git a/hw/ppc/spapr_caps.c b/hw/ppc/spapr_caps.c
index cbc41f5b20..5762b88689 100644
--- a/hw/ppc/spapr_caps.c
+++ b/hw/ppc/spapr_caps.c
@@ -26,6 +26,7 @@
 #include "qapi/error.h"
 #include "qapi/visitor.h"
 #include "sysemu/hw_accel.h"
+#include "exec/ram_addr.h"
 #include "target/ppc/cpu.h"
 #include "target/ppc/mmu-hash64.h"
 #include "cpu-models.h"
@@ -299,6 +300,23 @@ static void cap_safe_indirect_branch_apply(sPAPRMachineState *spapr,
 
 #define VALUE_DESC_TRISTATE     " (broken, workaround, fixed)"
 
+void spapr_check_pagesize(sPAPRMachineState *spapr, hwaddr pagesize,
+                          Error **errp)
+{
+    hwaddr maxpagesize = (1ULL << spapr->eff.caps[SPAPR_CAP_HPT_MPS]);
+
+    if (!kvmppc_hpt_needs_host_contiguous_pages()) {
+        return;
+    }
+
+    if (maxpagesize > pagesize) {
+        error_setg(errp,
+                   "Can't support %"HWADDR_PRIu" kiB guest pages with %"
+                   HWADDR_PRIu" kiB host pages with this KVM implementation",
+                   maxpagesize >> 10, pagesize >> 10);
+    }
+}
+
 static void cap_hpt_mps_apply(sPAPRMachineState *spapr,
                               uint8_t val, Error **errp)
 {
@@ -307,6 +325,8 @@ static void cap_hpt_mps_apply(sPAPRMachineState *spapr,
     } else if (val < 16) {
         warn_report("Many PAPR guests require 64kiB pages (cap-hpt-mps >= 16)");
     }
+
+    spapr_check_pagesize(spapr, qemu_getrampagesize(), errp);
 }
 
 sPAPRCapabilityInfo capability_table[SPAPR_CAP_NUM] = {
diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h
index 60ed3a5657..a3d616c612 100644
--- a/include/hw/ppc/spapr.h
+++ b/include/hw/ppc/spapr.h
@@ -805,4 +805,7 @@ void spapr_caps_reset(sPAPRMachineState *spapr);
 void spapr_caps_add_properties(sPAPRMachineClass *smc, Error **errp);
 int spapr_caps_post_migration(sPAPRMachineState *spapr);
 
+void spapr_check_pagesize(sPAPRMachineState *spapr, hwaddr pagesize,
+                          Error **errp);
+
 #endif /* HW_SPAPR_H */
diff --git a/target/ppc/kvm.c b/target/ppc/kvm.c
index e4341d6ff7..defbb08931 100644
--- a/target/ppc/kvm.c
+++ b/target/ppc/kvm.c
@@ -490,12 +490,18 @@ static void kvm_fixup_page_sizes(PowerPCCPU *cpu)
     }
 }
 
-bool kvmppc_is_mem_backend_page_size_ok(const char *obj_path)
+bool kvmppc_hpt_needs_host_contiguous_pages(void)
 {
-    Object *mem_obj = object_resolve_path(obj_path, NULL);
-    long pagesize = host_memory_backend_pagesize(MEMORY_BACKEND(mem_obj));
+    PowerPCCPU *cpu = POWERPC_CPU(first_cpu);
+    static struct kvm_ppc_smmu_info smmu_info;
+
+    if (!kvm_enabled()) {
+        return false;
+    }
 
-    return pagesize >= max_cpu_page_size;
+    kvm_get_smmu_info(cpu, &smmu_info);
+
+    return !!(smmu_info.flags & KVM_PPC_PAGE_SIZES_REAL);
 }
 
 #else /* defined (TARGET_PPC64) */
@@ -504,11 +510,6 @@ static inline void kvm_fixup_page_sizes(PowerPCCPU *cpu)
 {
 }
 
-bool kvmppc_is_mem_backend_page_size_ok(const char *obj_path)
-{
-    return true;
-}
-
 #endif /* !defined (TARGET_PPC64) */
 
 unsigned long kvm_arch_vcpu_id(CPUState *cpu)
diff --git a/target/ppc/kvm_ppc.h b/target/ppc/kvm_ppc.h
index e2840e1d33..443fca0a4e 100644
--- a/target/ppc/kvm_ppc.h
+++ b/target/ppc/kvm_ppc.h
@@ -70,7 +70,7 @@ int kvmppc_resize_hpt_prepare(PowerPCCPU *cpu, target_ulong flags, int shift);
 int kvmppc_resize_hpt_commit(PowerPCCPU *cpu, target_ulong flags, int shift);
 bool kvmppc_pvr_workaround_required(PowerPCCPU *cpu);
 
-bool kvmppc_is_mem_backend_page_size_ok(const char *obj_path);
+bool kvmppc_hpt_needs_host_contiguous_pages(void);
 
 #else
 
@@ -222,9 +222,9 @@ static inline uint64_t kvmppc_rma_size(uint64_t current_size,
     return ram_size;
 }
 
-static inline bool kvmppc_is_mem_backend_page_size_ok(const char *obj_path)
+static inline bool kvmppc_hpt_needs_host_contiguous_pages(void)
 {
-    return true;
+    return false;
 }
 
 static inline bool kvmppc_has_cap_spapr_vfio(void)
-- 
2.14.3

  parent reply	other threads:[~2018-04-19  6:29 UTC|newest]

Thread overview: 28+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-04-19  6:29 [Qemu-devel] [RFC for-2.13 0/7] spapr: Clean up pagesize handling David Gibson
2018-04-19  6:29 ` [Qemu-devel] [RFC for-2.13 1/7] spapr: Maximum (HPT) pagesize property David Gibson
2018-05-02 21:06   ` Murilo Opsfelder Araujo
2018-05-03  1:34     ` David Gibson
2018-04-19  6:29 ` David Gibson [this message]
2018-04-19  6:29 ` [Qemu-devel] [RFC for-2.13 3/7] target/ppc: Add ppc_hash64_filter_pagesizes() David Gibson
2018-05-03 15:57   ` Murilo Opsfelder Araujo
2018-05-04  6:30     ` David Gibson
2018-04-19  6:29 ` [Qemu-devel] [RFC for-2.13 4/7] spapr: Add cpu_apply hook to capabilities David Gibson
2018-04-19  6:29 ` [Qemu-devel] [RFC for-2.13 5/7] spapr: Limit available pagesizes to provide a consistent guest environment David Gibson
2018-04-19  6:29 ` [Qemu-devel] [RFC for-2.13 6/7] spapr: Don't rewrite mmu capabilities in KVM mode David Gibson
2018-04-19  6:29 ` [Qemu-devel] [RFC for-2.13 7/7] spapr_pci: Remove unhelpful pagesize warning David Gibson
2018-04-19 15:30 ` [Qemu-devel] [RFC for-2.13 0/7] spapr: Clean up pagesize handling Andrea Bolognani
2018-04-20  2:35   ` David Gibson
2018-04-20  9:31     ` Andrea Bolognani
2018-04-20 10:21       ` David Gibson
2018-04-23  8:31         ` Andrea Bolognani
2018-04-24  1:26           ` David Gibson
2018-04-24 15:35         ` Andrea Bolognani
2018-04-25  6:32           ` David Gibson
2018-04-25 16:09         ` Andrea Bolognani
2018-04-26  0:55           ` David Gibson
2018-04-26  8:45             ` Andrea Bolognani
2018-04-27  2:14               ` David Gibson
2018-04-27  8:31                 ` Andrea Bolognani
2018-04-27 12:17                   ` David Gibson
2018-05-07 13:48                     ` Andrea Bolognani
2018-06-14  1:52                       ` David Gibson

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20180419062917.31486-3-david@gibson.dropbear.id.au \
    --to=david@gibson.dropbear.id.au \
    --cc=abologna@redhat.com \
    --cc=aik@ozlabs.ru \
    --cc=clg@kaod.org \
    --cc=groug@kaod.org \
    --cc=qemu-devel@nongnu.org \
    --cc=qemu-ppc@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.