From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500274710337481.0661443442799; Sun, 16 Jul 2017 23:58:30 -0700 (PDT) Received: from localhost ([::1]:48290 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzzB-0003s8-41 for importer@patchew.org; Mon, 17 Jul 2017 02:58:29 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40524) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxK-0002aB-4o for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:35 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxG-0001Wx-KE for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:34 -0400 Received: from ozlabs.org ([103.22.144.67]:39783) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxG-0001TY-9D; Mon, 17 Jul 2017 02:56:30 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGK52lPz9t1t; Mon, 17 Jul 2017 16:56:24 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274585; bh=zNgO/B6wEt/fCB/FbTtdUwb6lKZ0eeSmLj59MY9rY6c=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=l0aS6344Epl8N38osxjPH/RB9F0T2HC4adIuGx113VrJ8gs3uhjMxCXcolW5yWNb0 NPZsTb6u3hIfI1R10aZTUfAKJaW0jd9+HKO4G/JuLDMwDPdOok4ITaa3ri3loVuop+ hWCiHuOi+zs92xWL8vtEwJ0wIKHzcOMkIxj+bkaE= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:01 +1000 Message-Id: <20170717065621.4688-2-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 01/21] spapr: Remove unnecessary instance_size specifications from DRC subtypes X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" All the DRC subtypes explicitly list instance_size in TypeInfo (all as sizeof(sPAPRDRConnector). This isn't necessary, since if it's not listed it will be derived from the parent type. Worse, this is dangerous, because if a subtype is changed in future to have a larger structure, then subtypes of that subtype also need to have instance_size changed, or it will lead to hard to track memory corruption bugs. Signed-off-by: David Gibson --- hw/ppc/spapr_drc.c | 5 ----- 1 file changed, 5 deletions(-) diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index f34355dad1..7f71c77015 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -653,7 +653,6 @@ static const TypeInfo spapr_dr_connector_info =3D { static const TypeInfo spapr_drc_physical_info =3D { .name =3D TYPE_SPAPR_DRC_PHYSICAL, .parent =3D TYPE_SPAPR_DR_CONNECTOR, - .instance_size =3D sizeof(sPAPRDRConnector), .class_init =3D spapr_drc_physical_class_init, .abstract =3D true, }; @@ -661,7 +660,6 @@ static const TypeInfo spapr_drc_physical_info =3D { static const TypeInfo spapr_drc_logical_info =3D { .name =3D TYPE_SPAPR_DRC_LOGICAL, .parent =3D TYPE_SPAPR_DR_CONNECTOR, - .instance_size =3D sizeof(sPAPRDRConnector), .class_init =3D spapr_drc_logical_class_init, .abstract =3D true, }; @@ -669,21 +667,18 @@ static const TypeInfo spapr_drc_logical_info =3D { static const TypeInfo spapr_drc_cpu_info =3D { .name =3D TYPE_SPAPR_DRC_CPU, .parent =3D TYPE_SPAPR_DRC_LOGICAL, - .instance_size =3D sizeof(sPAPRDRConnector), .class_init =3D spapr_drc_cpu_class_init, }; =20 static const TypeInfo spapr_drc_pci_info =3D { .name =3D TYPE_SPAPR_DRC_PCI, .parent =3D TYPE_SPAPR_DRC_PHYSICAL, - .instance_size =3D sizeof(sPAPRDRConnector), .class_init =3D spapr_drc_pci_class_init, }; =20 static const TypeInfo spapr_drc_lmb_info =3D { .name =3D TYPE_SPAPR_DRC_LMB, .parent =3D TYPE_SPAPR_DRC_LOGICAL, - .instance_size =3D sizeof(sPAPRDRConnector), .class_init =3D spapr_drc_lmb_class_init, }; =20 --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275019412661.3654277605204; Mon, 17 Jul 2017 00:03:39 -0700 (PDT) Received: from localhost ([::1]:48317 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX048-0008Rv-Dm for importer@patchew.org; Mon, 17 Jul 2017 03:03:36 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40525) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxK-0002aC-5U for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:37 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxG-0001Wl-EU for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:34 -0400 Received: from ozlabs.org ([103.22.144.67]:51067) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxF-0001SH-Q9; Mon, 17 Jul 2017 02:56:30 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGK0R1xz9sRg; Mon, 17 Jul 2017 16:56:25 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274585; bh=yOoRhXbpiS1lkpw2Ax8XGhkHTYVF5ddM3VsZoTHtPOk=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=hDdD3ElJJqFAyAIyiq6BujjLtSeRVY1yWC8/WdhX9gRGbAHpzZ8EcWeYInnjJrBF6 Ilbgn2yVKhvcUlDNVOLSUZ2JQzFA7k5Qj7wr52xU+k6PS091RNzcgarp8TSe18JpvE py1Y1jGI8REid1ZsiQTtUY3ny3r5Wvf6i4s0W0Y8= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:02 +1000 Message-Id: <20170717065621.4688-3-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 02/21] spapr: migrate pending_events of spapr state X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, Daniel Henrique Barboza , David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" From: Daniel Henrique Barboza In racing situations between hotplug events and migration operation, a rtas hotplug event could have not yet be delivered to the source guest when migration is started. In this case the pending_events of spapr state need be transmitted to the target so that the hotplug event can be finished on the target. To achieve the minimal VMSD possible to migrate the pending_events list, this patch makes the changes in spapr_events.c: - 'log_type' of sPAPREventLogEntry struct deleted. This information can be derived by inspecting the rtas_error_log summary field. A new function called 'spapr_event_log_entry_type' was added to retrieve the type of a given sPAPREventLogEntry. - sPAPREventLogEntry, epow_log_full and hp_log_full were redesigned. The only data we're going to migrate in the VMSD is the event log data itself, which can be divided in two parts: a rtas_error_log header and an extended event log field. The rtas_error_log header contains information about the size of the extended log field, which can be used inside VMSD as the size parameter of the VBUFFER_ALOC field that will store it. To allow this use, the header.extended_length field must be exposed inline to the VMSD instead of embedded into a 'data' field that holds everything. With this in mind, the following changes were done: * a new 'header' field was added to sPAPREventLogEntry. This field hold= s a a struct rtas_error_log inline. * the declaration of the 'rtas_error_log' struct was moved to spapr.h to be visible to the VMSD macros. * 'data' field of sPAPREventLogEntry was renamed to 'extended_log' and now holds only the contents of the extended event log. * 'struct rtas_error_log hdr' were taken away from both epow_log_full and hp_log_full. This information is now available at the header field of sPAPREventLogEntry. * epow_log_full and hp_log_full were renamed to epow_extended_log and hp_extended_log respectively. This rename makes it clearer to understand the new purpose of both structures: hold the information of an extended event log field. * spapr_powerdown_req and spapr_hotplug_req_event now creates a sPAPREventLogEntry structure that contains the full rtas log entry. * rtas_event_log_queue and rtas_event_log_dequeue now receives a sPAPREventLogEntry pointer as a parameter instead of a void pointer. - the endianess of the sPAPREventLogEntry header is now native instead of be32. We can use the fields in native endianess internally and write them in be32 in the guest physical memory inside 'check_exception'. This allows the VMSD inside spapr.c to read the correct size of the entended_log field. - inside spapr.c, pending_events is put in a subsection in the spapr state VMSD to make sure migration across different versions is not broken. A small change in rtas_event_log_queue and rtas_event_log_dequeue were also made: instead of calling qdev_get_machine(), both functions now receive a pointer to the sPAPRMachineState. This pointer is already available in the callers of these functions and we don't need to waste resources calling qdev() again. Signed-off-by: Daniel Henrique Barboza Signed-off-by: David Gibson --- hw/ppc/spapr.c | 32 ++++++++++++++++ hw/ppc/spapr_events.c | 99 +++++++++++++++++++++++++++-------------------= ---- include/hw/ppc/spapr.h | 9 ++++- 3 files changed, 92 insertions(+), 48 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 16638ce80c..b451d856b8 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -1517,6 +1517,37 @@ static bool version_before_3(void *opaque, int versi= on_id) return version_id < 3; } =20 +static bool spapr_pending_events_needed(void *opaque) +{ + sPAPRMachineState *spapr =3D (sPAPRMachineState *)opaque; + return !QTAILQ_EMPTY(&spapr->pending_events); +} + +static const VMStateDescription vmstate_spapr_event_entry =3D { + .name =3D "spapr_event_log_entry", + .version_id =3D 1, + .minimum_version_id =3D 1, + .fields =3D (VMStateField[]) { + VMSTATE_UINT32(header.summary, sPAPREventLogEntry), + VMSTATE_UINT32(header.extended_length, sPAPREventLogEntry), + VMSTATE_VBUFFER_ALLOC_UINT32(extended_log, sPAPREventLogEntry, 0, + NULL, header.extended_length), + VMSTATE_END_OF_LIST() + }, +}; + +static const VMStateDescription vmstate_spapr_pending_events =3D { + .name =3D "spapr_pending_events", + .version_id =3D 1, + .minimum_version_id =3D 1, + .needed =3D spapr_pending_events_needed, + .fields =3D (VMStateField[]) { + VMSTATE_QTAILQ_V(pending_events, sPAPRMachineState, 1, + vmstate_spapr_event_entry, sPAPREventLogEntry, ne= xt), + VMSTATE_END_OF_LIST() + }, +}; + static bool spapr_ov5_cas_needed(void *opaque) { sPAPRMachineState *spapr =3D opaque; @@ -1615,6 +1646,7 @@ static const VMStateDescription vmstate_spapr =3D { .subsections =3D (const VMStateDescription*[]) { &vmstate_spapr_ov5_cas, &vmstate_spapr_patb_entry, + &vmstate_spapr_pending_events, NULL } }; diff --git a/hw/ppc/spapr_events.c b/hw/ppc/spapr_events.c index 587a3dacb2..ce41e74665 100644 --- a/hw/ppc/spapr_events.c +++ b/hw/ppc/spapr_events.c @@ -42,8 +42,7 @@ #include "hw/ppc/spapr_ovec.h" #include =20 -struct rtas_error_log { - uint32_t summary; +/* Macros related to rtas_error_log struct defined in spapr.h */ #define RTAS_LOG_VERSION_MASK 0xff000000 #define RTAS_LOG_VERSION_6 0x06000000 #define RTAS_LOG_SEVERITY_MASK 0x00e00000 @@ -85,8 +84,6 @@ struct rtas_error_log { #define RTAS_LOG_TYPE_ECC_CORR 0x0000000a #define RTAS_LOG_TYPE_EPOW 0x00000040 #define RTAS_LOG_TYPE_HOTPLUG 0x000000e5 - uint32_t extended_length; -} QEMU_PACKED; =20 struct rtas_event_log_v6 { uint8_t b0; @@ -166,8 +163,7 @@ struct rtas_event_log_v6_epow { uint64_t reason_code; } QEMU_PACKED; =20 -struct epow_log_full { - struct rtas_error_log hdr; +struct epow_extended_log { struct rtas_event_log_v6 v6hdr; struct rtas_event_log_v6_maina maina; struct rtas_event_log_v6_mainb mainb; @@ -205,8 +201,7 @@ struct rtas_event_log_v6_hp { union drc_identifier drc_id; } QEMU_PACKED; =20 -struct hp_log_full { - struct rtas_error_log hdr; +struct hp_extended_log { struct rtas_event_log_v6 v6hdr; struct rtas_event_log_v6_maina maina; struct rtas_event_log_v6_mainb mainb; @@ -341,25 +336,26 @@ static int rtas_event_log_to_irq(sPAPRMachineState *s= papr, int log_type) return source->irq; } =20 -static void rtas_event_log_queue(int log_type, void *data) +static uint32_t spapr_event_log_entry_type(sPAPREventLogEntry *entry) { - sPAPRMachineState *spapr =3D SPAPR_MACHINE(qdev_get_machine()); - sPAPREventLogEntry *entry =3D g_new(sPAPREventLogEntry, 1); + return entry->header.summary & RTAS_LOG_TYPE_MASK; +} =20 - g_assert(data); - entry->log_type =3D log_type; - entry->data =3D data; +static void rtas_event_log_queue(sPAPRMachineState *spapr, + sPAPREventLogEntry *entry) +{ QTAILQ_INSERT_TAIL(&spapr->pending_events, entry, next); } =20 -static sPAPREventLogEntry *rtas_event_log_dequeue(uint32_t event_mask) +static sPAPREventLogEntry *rtas_event_log_dequeue(sPAPRMachineState *spapr, + uint32_t event_mask) { - sPAPRMachineState *spapr =3D SPAPR_MACHINE(qdev_get_machine()); sPAPREventLogEntry *entry =3D NULL; =20 QTAILQ_FOREACH(entry, &spapr->pending_events, next) { const sPAPREventSource *source =3D - rtas_event_log_to_source(spapr, entry->log_type); + rtas_event_log_to_source(spapr, + spapr_event_log_entry_type(entry)); =20 if (source->mask & event_mask) { break; @@ -380,7 +376,8 @@ static bool rtas_event_log_contains(uint32_t event_mask) =20 QTAILQ_FOREACH(entry, &spapr->pending_events, next) { const sPAPREventSource *source =3D - rtas_event_log_to_source(spapr, entry->log_type); + rtas_event_log_to_source(spapr, + spapr_event_log_entry_type(entry)); =20 if (source->mask & event_mask) { return true; @@ -428,27 +425,30 @@ static void spapr_init_maina(struct rtas_event_log_v6= _maina *maina, static void spapr_powerdown_req(Notifier *n, void *opaque) { sPAPRMachineState *spapr =3D SPAPR_MACHINE(qdev_get_machine()); + sPAPREventLogEntry *entry; struct rtas_error_log *hdr; struct rtas_event_log_v6 *v6hdr; struct rtas_event_log_v6_maina *maina; struct rtas_event_log_v6_mainb *mainb; struct rtas_event_log_v6_epow *epow; - struct epow_log_full *new_epow; + struct epow_extended_log *new_epow; =20 + entry =3D g_new(sPAPREventLogEntry, 1); new_epow =3D g_malloc0(sizeof(*new_epow)); - hdr =3D &new_epow->hdr; + entry->extended_log =3D new_epow; + + hdr =3D &entry->header; v6hdr =3D &new_epow->v6hdr; maina =3D &new_epow->maina; mainb =3D &new_epow->mainb; epow =3D &new_epow->epow; =20 - hdr->summary =3D cpu_to_be32(RTAS_LOG_VERSION_6 - | RTAS_LOG_SEVERITY_EVENT - | RTAS_LOG_DISPOSITION_NOT_RECOVERED - | RTAS_LOG_OPTIONAL_PART_PRESENT - | RTAS_LOG_TYPE_EPOW); - hdr->extended_length =3D cpu_to_be32(sizeof(*new_epow) - - sizeof(new_epow->hdr)); + hdr->summary =3D RTAS_LOG_VERSION_6 + | RTAS_LOG_SEVERITY_EVENT + | RTAS_LOG_DISPOSITION_NOT_RECOVERED + | RTAS_LOG_OPTIONAL_PART_PRESENT + | RTAS_LOG_TYPE_EPOW; + hdr->extended_length =3D sizeof(*new_epow); =20 spapr_init_v6hdr(v6hdr); spapr_init_maina(maina, 3 /* Main-A, Main-B and EPOW */); @@ -468,7 +468,7 @@ static void spapr_powerdown_req(Notifier *n, void *opaq= ue) epow->event_modifier =3D RTAS_LOG_V6_EPOW_MODIFIER_NORMAL; epow->extended_modifier =3D RTAS_LOG_V6_EPOW_XMODIFIER_PARTITION_SPECI= FIC; =20 - rtas_event_log_queue(RTAS_LOG_TYPE_EPOW, new_epow); + rtas_event_log_queue(spapr, entry); =20 qemu_irq_pulse(xics_get_qirq(XICS_FABRIC(spapr), rtas_event_log_to_irq(spapr, @@ -480,28 +480,31 @@ static void spapr_hotplug_req_event(uint8_t hp_id, ui= nt8_t hp_action, union drc_identifier *drc_id) { sPAPRMachineState *spapr =3D SPAPR_MACHINE(qdev_get_machine()); - struct hp_log_full *new_hp; + sPAPREventLogEntry *entry; + struct hp_extended_log *new_hp; struct rtas_error_log *hdr; struct rtas_event_log_v6 *v6hdr; struct rtas_event_log_v6_maina *maina; struct rtas_event_log_v6_mainb *mainb; struct rtas_event_log_v6_hp *hp; =20 - new_hp =3D g_malloc0(sizeof(struct hp_log_full)); - hdr =3D &new_hp->hdr; + entry =3D g_new(sPAPREventLogEntry, 1); + new_hp =3D g_malloc0(sizeof(struct hp_extended_log)); + entry->extended_log =3D new_hp; + + hdr =3D &entry->header; v6hdr =3D &new_hp->v6hdr; maina =3D &new_hp->maina; mainb =3D &new_hp->mainb; hp =3D &new_hp->hp; =20 - hdr->summary =3D cpu_to_be32(RTAS_LOG_VERSION_6 - | RTAS_LOG_SEVERITY_EVENT - | RTAS_LOG_DISPOSITION_NOT_RECOVERED - | RTAS_LOG_OPTIONAL_PART_PRESENT - | RTAS_LOG_INITIATOR_HOTPLUG - | RTAS_LOG_TYPE_HOTPLUG); - hdr->extended_length =3D cpu_to_be32(sizeof(*new_hp) - - sizeof(new_hp->hdr)); + hdr->summary =3D RTAS_LOG_VERSION_6 + | RTAS_LOG_SEVERITY_EVENT + | RTAS_LOG_DISPOSITION_NOT_RECOVERED + | RTAS_LOG_OPTIONAL_PART_PRESENT + | RTAS_LOG_INITIATOR_HOTPLUG + | RTAS_LOG_TYPE_HOTPLUG; + hdr->extended_length =3D sizeof(*new_hp); =20 spapr_init_v6hdr(v6hdr); spapr_init_maina(maina, 3 /* Main-A, Main-B, HP */); @@ -551,7 +554,7 @@ static void spapr_hotplug_req_event(uint8_t hp_id, uint= 8_t hp_action, cpu_to_be32(drc_id->count_indexed.index); } =20 - rtas_event_log_queue(RTAS_LOG_TYPE_HOTPLUG, new_hp); + rtas_event_log_queue(spapr, entry); =20 qemu_irq_pulse(xics_get_qirq(XICS_FABRIC(spapr), rtas_event_log_to_irq(spapr, @@ -625,10 +628,10 @@ static void check_exception(PowerPCCPU *cpu, sPAPRMac= hineState *spapr, target_ulong args, uint32_t nret, target_ulong rets) { + CPUState *cs =3D CPU(cpu); uint32_t mask, buf, len, event_len; uint64_t xinfo; sPAPREventLogEntry *event; - struct rtas_error_log *hdr; int i; =20 if ((nargs < 6) || (nargs > 7) || nret !=3D 1) { @@ -644,21 +647,25 @@ static void check_exception(PowerPCCPU *cpu, sPAPRMac= hineState *spapr, xinfo |=3D (uint64_t)rtas_ld(args, 6) << 32; } =20 - event =3D rtas_event_log_dequeue(mask); + event =3D rtas_event_log_dequeue(spapr, mask); if (!event) { goto out_no_events; } =20 - hdr =3D event->data; - event_len =3D be32_to_cpu(hdr->extended_length) + sizeof(*hdr); + event_len =3D event->header.extended_length + sizeof(event->header); =20 if (event_len < len) { len =3D event_len; } =20 - cpu_physical_memory_write(buf, event->data, len); + stl_be_phys(cs->as, buf, event->header.summary); + stl_be_phys(cs->as, buf + sizeof(event->header.summary), + event->header.extended_length); + cpu_physical_memory_write(buf + sizeof(event->header), + event->extended_log, + event->header.extended_length); rtas_st(rets, 0, RTAS_OUT_SUCCESS); - g_free(event->data); + g_free(event->extended_log); g_free(event); =20 /* according to PAPR+, the IRQ must be left asserted, or re-asserted, = if diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 5f708eec23..2718b90db7 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -606,9 +606,14 @@ struct sPAPRTCETable { =20 sPAPRTCETable *spapr_tce_find_by_liobn(target_ulong liobn); =20 +struct rtas_error_log { + uint32_t summary; + uint32_t extended_length; +} QEMU_PACKED; + struct sPAPREventLogEntry { - int log_type; - void *data; + struct rtas_error_log header; + void *extended_log; QTAILQ_ENTRY(sPAPREventLogEntry) next; }; =20 --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275187676737.6547026630307; Mon, 17 Jul 2017 00:06:27 -0700 (PDT) Received: from localhost ([::1]:48331 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX06p-0002X4-H8 for importer@patchew.org; Mon, 17 Jul 2017 03:06:23 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40568) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxL-0002ap-Bv for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:38 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxJ-0001ZR-BR for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:35 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:39279) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxI-0001X3-N2; Mon, 17 Jul 2017 02:56:33 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGL5Djgz9t24; Mon, 17 Jul 2017 16:56:25 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274586; bh=fEKfoXx3tBeKE+CZOXo3ZVWlRLCF47R+yoMZvGHqS6E=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=W951uiT4aI7DtjiWCje59dVNuf6zwJzpkck3AdkDlUprurgL1hjUiYUESYsEeXF6j 9kzyraAQ6HGyrdSieWWzjujVbtH70qB/+ezqEr/vNn246nfTJMZnWkeJ9d/dpOcAZJ dAKpt4b8S5M8FluCjPld1MmhBAB8ggHSy4IdWanY= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:03 +1000 Message-Id: <20170717065621.4688-4-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 03/21] spapr: Minor cleanups to events handling X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" The rtas_error_log structure is marked packed, which strongly suggests its precise layout is important to match an external interface. Along with that one could expect it to have a fixed endianness to match the same interface. That used to be the case - matching the layout of PAPR RTAS event format and requiring BE fields. Now, however, it's only used embedded within sPAPREventLogEntry with the fields in native order, since they're processed internally. Clear that up by removing the nested structure in sPAPREventLogEntry. struct rtas_error_log is moved back to spapr_events.c where it is used as a temporary to help convert the fields in sPAPREventLogEntry to the correct in memory format when delivering an event to the guest. Signed-off-by: David Gibson --- hw/ppc/spapr.c | 6 +++--- hw/ppc/spapr_events.c | 45 ++++++++++++++++++++++----------------------- include/hw/ppc/spapr.h | 6 +----- 3 files changed, 26 insertions(+), 31 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index b451d856b8..8528c30ad7 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -1528,10 +1528,10 @@ static const VMStateDescription vmstate_spapr_event= _entry =3D { .version_id =3D 1, .minimum_version_id =3D 1, .fields =3D (VMStateField[]) { - VMSTATE_UINT32(header.summary, sPAPREventLogEntry), - VMSTATE_UINT32(header.extended_length, sPAPREventLogEntry), + VMSTATE_UINT32(summary, sPAPREventLogEntry), + VMSTATE_UINT32(extended_length, sPAPREventLogEntry), VMSTATE_VBUFFER_ALLOC_UINT32(extended_log, sPAPREventLogEntry, 0, - NULL, header.extended_length), + NULL, extended_length), VMSTATE_END_OF_LIST() }, }; diff --git a/hw/ppc/spapr_events.c b/hw/ppc/spapr_events.c index ce41e74665..f952b78237 100644 --- a/hw/ppc/spapr_events.c +++ b/hw/ppc/spapr_events.c @@ -42,7 +42,6 @@ #include "hw/ppc/spapr_ovec.h" #include =20 -/* Macros related to rtas_error_log struct defined in spapr.h */ #define RTAS_LOG_VERSION_MASK 0xff000000 #define RTAS_LOG_VERSION_6 0x06000000 #define RTAS_LOG_SEVERITY_MASK 0x00e00000 @@ -85,6 +84,11 @@ #define RTAS_LOG_TYPE_EPOW 0x00000040 #define RTAS_LOG_TYPE_HOTPLUG 0x000000e5 =20 +struct rtas_error_log { + uint32_t summary; + uint32_t extended_length; +} QEMU_PACKED; + struct rtas_event_log_v6 { uint8_t b0; #define RTAS_LOG_V6_B0_VALID 0x80 @@ -338,7 +342,7 @@ static int rtas_event_log_to_irq(sPAPRMachineState *spa= pr, int log_type) =20 static uint32_t spapr_event_log_entry_type(sPAPREventLogEntry *entry) { - return entry->header.summary & RTAS_LOG_TYPE_MASK; + return entry->summary & RTAS_LOG_TYPE_MASK; } =20 static void rtas_event_log_queue(sPAPRMachineState *spapr, @@ -426,7 +430,6 @@ static void spapr_powerdown_req(Notifier *n, void *opaq= ue) { sPAPRMachineState *spapr =3D SPAPR_MACHINE(qdev_get_machine()); sPAPREventLogEntry *entry; - struct rtas_error_log *hdr; struct rtas_event_log_v6 *v6hdr; struct rtas_event_log_v6_maina *maina; struct rtas_event_log_v6_mainb *mainb; @@ -437,18 +440,17 @@ static void spapr_powerdown_req(Notifier *n, void *op= aque) new_epow =3D g_malloc0(sizeof(*new_epow)); entry->extended_log =3D new_epow; =20 - hdr =3D &entry->header; v6hdr =3D &new_epow->v6hdr; maina =3D &new_epow->maina; mainb =3D &new_epow->mainb; epow =3D &new_epow->epow; =20 - hdr->summary =3D RTAS_LOG_VERSION_6 + entry->summary =3D RTAS_LOG_VERSION_6 | RTAS_LOG_SEVERITY_EVENT | RTAS_LOG_DISPOSITION_NOT_RECOVERED | RTAS_LOG_OPTIONAL_PART_PRESENT | RTAS_LOG_TYPE_EPOW; - hdr->extended_length =3D sizeof(*new_epow); + entry->extended_length =3D sizeof(*new_epow); =20 spapr_init_v6hdr(v6hdr); spapr_init_maina(maina, 3 /* Main-A, Main-B and EPOW */); @@ -482,7 +484,6 @@ static void spapr_hotplug_req_event(uint8_t hp_id, uint= 8_t hp_action, sPAPRMachineState *spapr =3D SPAPR_MACHINE(qdev_get_machine()); sPAPREventLogEntry *entry; struct hp_extended_log *new_hp; - struct rtas_error_log *hdr; struct rtas_event_log_v6 *v6hdr; struct rtas_event_log_v6_maina *maina; struct rtas_event_log_v6_mainb *mainb; @@ -492,19 +493,18 @@ static void spapr_hotplug_req_event(uint8_t hp_id, ui= nt8_t hp_action, new_hp =3D g_malloc0(sizeof(struct hp_extended_log)); entry->extended_log =3D new_hp; =20 - hdr =3D &entry->header; v6hdr =3D &new_hp->v6hdr; maina =3D &new_hp->maina; mainb =3D &new_hp->mainb; hp =3D &new_hp->hp; =20 - hdr->summary =3D RTAS_LOG_VERSION_6 - | RTAS_LOG_SEVERITY_EVENT - | RTAS_LOG_DISPOSITION_NOT_RECOVERED - | RTAS_LOG_OPTIONAL_PART_PRESENT - | RTAS_LOG_INITIATOR_HOTPLUG - | RTAS_LOG_TYPE_HOTPLUG; - hdr->extended_length =3D sizeof(*new_hp); + entry->summary =3D RTAS_LOG_VERSION_6 + | RTAS_LOG_SEVERITY_EVENT + | RTAS_LOG_DISPOSITION_NOT_RECOVERED + | RTAS_LOG_OPTIONAL_PART_PRESENT + | RTAS_LOG_INITIATOR_HOTPLUG + | RTAS_LOG_TYPE_HOTPLUG; + entry->extended_length =3D sizeof(*new_hp); =20 spapr_init_v6hdr(v6hdr); spapr_init_maina(maina, 3 /* Main-A, Main-B, HP */); @@ -628,10 +628,10 @@ static void check_exception(PowerPCCPU *cpu, sPAPRMac= hineState *spapr, target_ulong args, uint32_t nret, target_ulong rets) { - CPUState *cs =3D CPU(cpu); uint32_t mask, buf, len, event_len; uint64_t xinfo; sPAPREventLogEntry *event; + struct rtas_error_log header; int i; =20 if ((nargs < 6) || (nargs > 7) || nret !=3D 1) { @@ -652,18 +652,17 @@ static void check_exception(PowerPCCPU *cpu, sPAPRMac= hineState *spapr, goto out_no_events; } =20 - event_len =3D event->header.extended_length + sizeof(event->header); + event_len =3D event->extended_length + sizeof(header); =20 if (event_len < len) { len =3D event_len; } =20 - stl_be_phys(cs->as, buf, event->header.summary); - stl_be_phys(cs->as, buf + sizeof(event->header.summary), - event->header.extended_length); - cpu_physical_memory_write(buf + sizeof(event->header), - event->extended_log, - event->header.extended_length); + header.summary =3D cpu_to_be32(event->summary); + header.extended_length =3D cpu_to_be32(event->extended_length); + cpu_physical_memory_write(buf, &header, sizeof(header)); + cpu_physical_memory_write(buf + sizeof(header), event->extended_log, + event->extended_length); rtas_st(rets, 0, RTAS_OUT_SUCCESS); g_free(event->extended_log); g_free(event); diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 2718b90db7..2ddec025d2 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -606,13 +606,9 @@ struct sPAPRTCETable { =20 sPAPRTCETable *spapr_tce_find_by_liobn(target_ulong liobn); =20 -struct rtas_error_log { +struct sPAPREventLogEntry { uint32_t summary; uint32_t extended_length; -} QEMU_PACKED; - -struct sPAPREventLogEntry { - struct rtas_error_log header; void *extended_log; QTAILQ_ENTRY(sPAPREventLogEntry) next; }; --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500274708158384.21261711249394; Sun, 16 Jul 2017 23:58:28 -0700 (PDT) Received: from localhost ([::1]:48289 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzz7-0003pF-NN for importer@patchew.org; Mon, 17 Jul 2017 02:58:25 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40479) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxH-0002a1-At for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:32 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxG-0001Wd-6f for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:31 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:42859) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxF-0001U2-QI; Mon, 17 Jul 2017 02:56:30 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGL41gtz9t2H; Mon, 17 Jul 2017 16:56:25 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274586; bh=mGWHIaSq1+Z1qSVRwO31v8VxJZJJHlghpGtlnskPZHM=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=j2W/FhkPi5rJgA6IHhW3SaAKfciu/5VDHP5CiZ3gb5mBWsj+SeHpQUY4MU894gv6c j2ZCpcK1tbcyr/suLFj8lDisbqyzCOLmoqF0bhZaAMqbNH8sH7UubOEHX6HEr3SKce 5KC2xGoio24Tv0Q1bcAOkTUhgXqgSNSAi7FP4hvk= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:04 +1000 Message-Id: <20170717065621.4688-5-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 04/21] spapr: Treat devices added before inbound migration as coldplugged X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Laurent Vivier , qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" From: Laurent Vivier When migrating a guest which has already had devices hotplugged, libvirt typically starts the destination qemu with -incoming defer, adds those hotplugged devices with qmp, then initiates the incoming migration. This causes problems for the management of spapr DRC state. Because the device is treated as hotplugged, it goes into a DRC state for a device immediately after it's plugged, but before the guest has acknowledged its presence. However, chances are the guest on the source machine *has* acknowledged the device's presence and configured it. If the source has fully configured the device, then DRC state won't be sent in the migration stream: for maximum migration compatibility with earlier versions we don't migrate DRCs in coldplug-equivalent state. That means that the DRC effectively changes state over the migrate, causing problems later on. In addition, logging hotplug events for these devices isn't what we want because a) those events should already have been issued on the source host and b) the event queue should get wiped out by the incoming state anyway. In short, what we really want is to treat devices added before an incoming migration as if they were coldplugged. To do this, we first add a spapr_drc_hotplugged() helper which determines if the device is hotplugged in the sense relevant for DRC state management. We only send hotplug events when this is true. Second, when we add a device which isn't hotplugged in this sense, we force a reset of the DRC state - this ensures the DRC is in a coldplug-equivalent state (there isn't usually a system reset between these device adds and the incoming migration). This is based on an earlier patch by Laurent Vivier, cleaned up and extended. Signed-off-by: Laurent Vivier Signed-off-by: David Gibson Reviewed-by: Greg Kurz Tested-by: Daniel Barboza --- hw/ppc/spapr.c | 24 ++++++++++++++++-------- hw/ppc/spapr_drc.c | 9 ++++++--- hw/ppc/spapr_pci.c | 4 +++- include/hw/ppc/spapr_drc.h | 8 ++++++++ 4 files changed, 33 insertions(+), 12 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 8528c30ad7..cb61d3d36b 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -2636,6 +2636,7 @@ static void spapr_add_lmbs(DeviceState *dev, uint64_t= addr_start, uint64_t size, int i, fdt_offset, fdt_size; void *fdt; uint64_t addr =3D addr_start; + bool hotplugged =3D spapr_drc_hotplugged(dev); Error *local_err =3D NULL; =20 for (i =3D 0; i < nr_lmbs; i++) { @@ -2659,12 +2660,15 @@ static void spapr_add_lmbs(DeviceState *dev, uint64= _t addr_start, uint64_t size, error_propagate(errp, local_err); return; } + if (!hotplugged) { + spapr_drc_reset(drc); + } addr +=3D SPAPR_MEMORY_BLOCK_SIZE; } /* send hotplug notification to the * guest only in case of hotplugged memory */ - if (dev->hotplugged) { + if (hotplugged) { if (dedicated_hp_event_source) { drc =3D spapr_drc_by_id(TYPE_SPAPR_DRC_LMB, addr_start / SPAPR_MEMORY_BLOCK_SIZE); @@ -2998,6 +3002,7 @@ static void spapr_core_plug(HotplugHandler *hotplug_d= ev, DeviceState *dev, int smt =3D kvmppc_smt_threads(); CPUArchId *core_slot; int index; + bool hotplugged =3D spapr_drc_hotplugged(dev); =20 core_slot =3D spapr_find_cpu_slot(MACHINE(hotplug_dev), cc->core_id, &= index); if (!core_slot) { @@ -3018,15 +3023,18 @@ static void spapr_core_plug(HotplugHandler *hotplug= _dev, DeviceState *dev, error_propagate(errp, local_err); return; } - } =20 - if (dev->hotplugged) { - /* - * Send hotplug notification interrupt to the guest only in case - * of hotplugged CPUs. - */ - spapr_hotplug_req_add_by_index(drc); + if (hotplugged) { + /* + * Send hotplug notification interrupt to the guest only + * in case of hotplugged CPUs. + */ + spapr_hotplug_req_add_by_index(drc); + } else { + spapr_drc_reset(drc); + } } + core_slot->cpu =3D OBJECT(dev); =20 if (smc->pre_2_10_has_unused_icps) { diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 7f71c77015..31181dab1d 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -412,10 +412,8 @@ static bool release_pending(sPAPRDRConnector *drc) return drc->awaiting_release; } =20 -static void drc_reset(void *opaque) +void spapr_drc_reset(sPAPRDRConnector *drc) { - sPAPRDRConnector *drc =3D SPAPR_DR_CONNECTOR(opaque); - trace_spapr_drc_reset(spapr_drc_index(drc)); =20 g_free(drc->ccs); @@ -447,6 +445,11 @@ static void drc_reset(void *opaque) } } =20 +static void drc_reset(void *opaque) +{ + spapr_drc_reset(SPAPR_DR_CONNECTOR(opaque)); +} + static bool spapr_drc_needed(void *opaque) { sPAPRDRConnector *drc =3D (sPAPRDRConnector *)opaque; diff --git a/hw/ppc/spapr_pci.c b/hw/ppc/spapr_pci.c index a52dcf8ec0..1e84c552d8 100644 --- a/hw/ppc/spapr_pci.c +++ b/hw/ppc/spapr_pci.c @@ -1443,7 +1443,9 @@ static void spapr_pci_plug(HotplugHandler *plug_handl= er, /* If this is function 0, signal hotplug for all the device functions. * Otherwise defer sending the hotplug event. */ - if (plugged_dev->hotplugged && PCI_FUNC(pdev->devfn) =3D=3D 0) { + if (!spapr_drc_hotplugged(plugged_dev)) { + spapr_drc_reset(drc); + } else if (PCI_FUNC(pdev->devfn) =3D=3D 0) { int i; =20 for (i =3D 0; i < 8; i++) { diff --git a/include/hw/ppc/spapr_drc.h b/include/hw/ppc/spapr_drc.h index d15e9eb3b4..715016b052 100644 --- a/include/hw/ppc/spapr_drc.h +++ b/include/hw/ppc/spapr_drc.h @@ -15,6 +15,7 @@ =20 #include #include "qom/object.h" +#include "sysemu/sysemu.h" #include "hw/qdev.h" =20 #define TYPE_SPAPR_DR_CONNECTOR "spapr-dr-connector" @@ -223,6 +224,13 @@ typedef struct sPAPRDRConnectorClass { bool (*release_pending)(sPAPRDRConnector *drc); } sPAPRDRConnectorClass; =20 +static inline bool spapr_drc_hotplugged(DeviceState *dev) +{ + return dev->hotplugged && !runstate_check(RUN_STATE_INMIGRATE); +} + +void spapr_drc_reset(sPAPRDRConnector *drc); + uint32_t spapr_drc_index(sPAPRDRConnector *drc); sPAPRDRConnectorType spapr_drc_type(sPAPRDRConnector *drc); =20 --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275050018928.7061391940023; Mon, 17 Jul 2017 00:04:10 -0700 (PDT) Received: from localhost ([::1]:48319 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX04A-0008UN-WA for importer@patchew.org; Mon, 17 Jul 2017 03:03:39 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40528) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxK-0002aD-60 for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:36 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxG-0001Wr-HR for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:34 -0400 Received: from ozlabs.org ([103.22.144.67]:41029) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxG-0001Tw-6M; Mon, 17 Jul 2017 02:56:30 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGL2Yrzz9t16; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274586; bh=tiu9pSePm5XWDja4+DBnw7p1xYOcniO3FR97vquLDjY=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=ebUb3n5mzQuGG4Rd+sedujl/9cpnKjcm1kdjn613SC9wNEluTxoHhSTCYx4rhN6+7 Z95v8/rIav3JGs3jfvnf7D6XbiWP2n0OhZ6YbMNuxjidAf6YUKpQKmRWeIAZiVu7qB MCe1NVD+pKlawOG4c8eOoN3J/wTJUlg6L6hq04vE= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:05 +1000 Message-Id: <20170717065621.4688-6-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 05/21] spapr: Remove 'awaiting_allocation' DRC flag X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" The awaiting_allocation flag in the DRC was introduced by aab9913 "spapr_drc: Prevent detach racing against attach for CPU DR", allegedly to prevent a guest crash on racing attach and detach. Except.. information from the BZ actually suggests a qemu crash, not a guest crash. And there shouldn't be a problem here anyway: if the guest has already moved the DRC away from UNUSABLE state, the detach would already be deferred, and if it hadn't it should be safe to detach it (the guest should fail gracefully when it attempts to change the allocation state). I think this was probably just a bandaid for some other problem in the state management. So, remove awaiting_allocation and associated code. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz Tested-by: Greg Kurz Tested-by: Daniel Barboza --- hw/ppc/spapr_drc.c | 25 +++---------------------- include/hw/ppc/spapr_drc.h | 1 - 2 files changed, 3 insertions(+), 23 deletions(-) diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 31181dab1d..7f872a4803 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -170,19 +170,13 @@ static uint32_t drc_set_usable(sPAPRDRConnector *drc) if (!drc->dev) { return RTAS_OUT_NO_SUCH_INDICATOR; } - if (drc->awaiting_release && drc->awaiting_allocation) { - /* kernel is acknowledging a previous hotplug event - * while we are already removing it. - * it's safe to ignore awaiting_allocation here since we know the - * situation is predicated on the guest either already having done - * so (boot-time hotplug), or never being able to acquire in the - * first place (hotplug followed by immediate unplug). - */ + if (drc->awaiting_release) { + /* Don't allow the guest to move a device away from UNUSABLE + * state when we want to unplug it */ return RTAS_OUT_NO_SUCH_INDICATOR; } =20 drc->allocation_state =3D SPAPR_DR_ALLOCATION_STATE_USABLE; - drc->awaiting_allocation =3D false; =20 return RTAS_OUT_SUCCESS; } @@ -357,10 +351,6 @@ void spapr_drc_attach(sPAPRDRConnector *drc, DeviceSta= te *d, void *fdt, drc->fdt =3D fdt; drc->fdt_start_offset =3D fdt_start_offset; =20 - if (spapr_drc_type(drc) !=3D SPAPR_DR_CONNECTOR_TYPE_PCI) { - drc->awaiting_allocation =3D true; - } - object_property_add_link(OBJECT(drc), "device", object_get_typename(OBJECT(drc->dev)), (Object **)(&drc->dev), @@ -398,12 +388,6 @@ void spapr_drc_detach(sPAPRDRConnector *drc, DeviceSta= te *d, Error **errp) return; } =20 - if (drc->awaiting_allocation) { - drc->awaiting_release =3D true; - trace_spapr_drc_awaiting_allocation(spapr_drc_index(drc)); - return; - } - spapr_drc_release(drc); } =20 @@ -426,8 +410,6 @@ void spapr_drc_reset(sPAPRDRConnector *drc) spapr_drc_release(drc); } =20 - drc->awaiting_allocation =3D false; - if (drc->dev) { /* A device present at reset is coldplugged */ drc->isolation_state =3D SPAPR_DR_ISOLATION_STATE_UNISOLATED; @@ -493,7 +475,6 @@ static const VMStateDescription vmstate_spapr_drc =3D { VMSTATE_UINT32(dr_indicator, sPAPRDRConnector), VMSTATE_BOOL(configured, sPAPRDRConnector), VMSTATE_BOOL(awaiting_release, sPAPRDRConnector), - VMSTATE_BOOL(awaiting_allocation, sPAPRDRConnector), VMSTATE_END_OF_LIST() } }; diff --git a/include/hw/ppc/spapr_drc.h b/include/hw/ppc/spapr_drc.h index 715016b052..18a196e831 100644 --- a/include/hw/ppc/spapr_drc.h +++ b/include/hw/ppc/spapr_drc.h @@ -200,7 +200,6 @@ typedef struct sPAPRDRConnector { sPAPRConfigureConnectorState *ccs; =20 bool awaiting_release; - bool awaiting_allocation; =20 /* device pointer, via link property */ DeviceState *dev; --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500274860943355.3964299389736; Mon, 17 Jul 2017 00:01:00 -0700 (PDT) Received: from localhost ([::1]:48304 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX01b-0006M1-6I for importer@patchew.org; Mon, 17 Jul 2017 03:00:59 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40539) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxK-0002aE-Ep for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:36 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxI-0001Yl-Ns for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:34 -0400 Received: from ozlabs.org ([103.22.144.67]:36601) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxI-0001X1-C2; Mon, 17 Jul 2017 02:56:32 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGL5pS6z9t1y; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274586; bh=UQ5u5LV0gjqNyNlzqwvgBp4utyt+rwVsZmc+CYyFQME=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=O4XKNgrqJtS2DQjYcI10M703hwnYOVSVUj9+NtHfZE6aP2aJihAvT5GVH9DbbHxbl CdMZWCZaDygOq9rI2XxMG8iRLR+i/muBokjbveTa+Y/egWR5LXmXTH9jY/BQBrFJ7R p/gtn7yPJeK78ZaP0gtlaruTGOOUMU9zyTYX9Z8I= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:06 +1000 Message-Id: <20170717065621.4688-7-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 06/21] spapr: Simplify unplug path X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" spapr_lmb_release() and spapr_core_release() call hotplug_handler_unplug() which after a bunch of indirection calls spapr_memory_unplug() or spapr_core_unplug(). But we already know which is the appropriate thing to call here, so we can just fold it directly into the release function. Once that's done, there's no need for an hc->unplug method in the spapr machine at all: since we also have an hc->unplug_request method, the hotplug core will never use ->unplug. Signed-off-by: David Gibson Reviewed-by: Greg Kurz Tested-by: Daniel Barboza --- hw/ppc/spapr.c | 56 ++++++++----------------------------------------------= -- 1 file changed, 8 insertions(+), 48 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index cb61d3d36b..8818647e1a 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -2816,8 +2816,10 @@ static sPAPRDIMMState *spapr_recover_pending_dimm_st= ate(sPAPRMachineState *ms, /* Callback to be called during DRC release. */ void spapr_lmb_release(DeviceState *dev) { - HotplugHandler *hotplug_ctrl =3D qdev_get_hotplug_handler(dev); - sPAPRMachineState *spapr =3D SPAPR_MACHINE(hotplug_ctrl); + sPAPRMachineState *spapr =3D SPAPR_MACHINE(qdev_get_hotplug_handler(de= v)); + PCDIMMDevice *dimm =3D PC_DIMM(dev); + PCDIMMDeviceClass *ddc =3D PC_DIMM_GET_CLASS(dimm); + MemoryRegion *mr =3D ddc->get_memory_region(dimm); sPAPRDIMMState *ds =3D spapr_pending_dimm_unplugs_find(spapr, PC_DIMM(= dev)); =20 /* This information will get lost if a migration occurs @@ -2838,18 +2840,7 @@ void spapr_lmb_release(DeviceState *dev) * Now that all the LMBs have been removed by the guest, call the * pc-dimm unplug handler to cleanup up the pc-dimm device. */ - hotplug_handler_unplug(hotplug_ctrl, dev, &error_abort); -} - -static void spapr_memory_unplug(HotplugHandler *hotplug_dev, DeviceState *= dev, - Error **errp) -{ - sPAPRMachineState *ms =3D SPAPR_MACHINE(hotplug_dev); - PCDIMMDevice *dimm =3D PC_DIMM(dev); - PCDIMMDeviceClass *ddc =3D PC_DIMM_GET_CLASS(dimm); - MemoryRegion *mr =3D ddc->get_memory_region(dimm); - - pc_dimm_memory_unplug(dev, &ms->hotplug_memory, mr); + pc_dimm_memory_unplug(dev, &spapr->hotplug_memory, mr); object_unparent(OBJECT(dev)); } =20 @@ -2918,10 +2909,10 @@ static void *spapr_populate_hotplug_cpu_dt(CPUState= *cs, int *fdt_offset, return fdt; } =20 -static void spapr_core_unplug(HotplugHandler *hotplug_dev, DeviceState *de= v, - Error **errp) +/* Callback to be called during DRC release. */ +void spapr_core_release(DeviceState *dev) { - MachineState *ms =3D MACHINE(qdev_get_machine()); + MachineState *ms =3D MACHINE(qdev_get_hotplug_handler(dev)); sPAPRMachineClass *smc =3D SPAPR_MACHINE_GET_CLASS(ms); CPUCore *cc =3D CPU_CORE(dev); CPUArchId *core_slot =3D spapr_find_cpu_slot(ms, cc->core_id, NULL); @@ -2945,15 +2936,6 @@ static void spapr_core_unplug(HotplugHandler *hotplu= g_dev, DeviceState *dev, object_unparent(OBJECT(dev)); } =20 -/* Callback to be called during DRC release. */ -void spapr_core_release(DeviceState *dev) -{ - HotplugHandler *hotplug_ctrl; - - hotplug_ctrl =3D qdev_get_hotplug_handler(dev); - hotplug_handler_unplug(hotplug_ctrl, dev, &error_abort); -} - static void spapr_core_unplug_request(HotplugHandler *hotplug_dev, DeviceState *d= ev, Error **errp) @@ -3159,27 +3141,6 @@ static void spapr_machine_device_plug(HotplugHandler= *hotplug_dev, } } =20 -static void spapr_machine_device_unplug(HotplugHandler *hotplug_dev, - DeviceState *dev, Error **errp) -{ - sPAPRMachineState *sms =3D SPAPR_MACHINE(qdev_get_machine()); - MachineClass *mc =3D MACHINE_GET_CLASS(qdev_get_machine()); - - if (object_dynamic_cast(OBJECT(dev), TYPE_PC_DIMM)) { - if (spapr_ovec_test(sms->ov5_cas, OV5_HP_EVT)) { - spapr_memory_unplug(hotplug_dev, dev, errp); - } else { - error_setg(errp, "Memory hot unplug not supported for this gue= st"); - } - } else if (object_dynamic_cast(OBJECT(dev), TYPE_SPAPR_CPU_CORE)) { - if (!mc->has_hotpluggable_cpus) { - error_setg(errp, "CPU hot unplug not supported on this machine= "); - return; - } - spapr_core_unplug(hotplug_dev, dev, errp); - } -} - static void spapr_machine_device_unplug_request(HotplugHandler *hotplug_de= v, DeviceState *dev, Error **= errp) { @@ -3397,7 +3358,6 @@ static void spapr_machine_class_init(ObjectClass *oc,= void *data) mc->get_hotplug_handler =3D spapr_get_hotplug_handler; hc->pre_plug =3D spapr_machine_device_pre_plug; hc->plug =3D spapr_machine_device_plug; - hc->unplug =3D spapr_machine_device_unplug; mc->cpu_index_to_instance_props =3D spapr_cpu_index_to_props; mc->possible_cpu_arch_ids =3D spapr_possible_cpu_arch_ids; hc->unplug_request =3D spapr_machine_device_unplug_request; --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500274710782410.80464434718976; Sun, 16 Jul 2017 23:58:30 -0700 (PDT) Received: from localhost ([::1]:48291 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzzB-0003sG-Ie for importer@patchew.org; Mon, 17 Jul 2017 02:58:29 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40515) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxJ-0002a7-Sq for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:35 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxJ-0001Z3-2j for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:33 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:51901) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxI-0001X6-Nl; Mon, 17 Jul 2017 02:56:33 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM0BBNz9t2s; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=FGLHa6yFTNbSW5ZmTH0kpVCvoSxx1a2iLTix/mRDEJ0=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=l+BACznJapV8N+5r+JbyP3H71cQeFqFU+vVojpwhZPDgSz7uMgnyowCuklnl781ET FW/9bdLyNIZq7S0cSv9qnQjuAC8+0pjzbVAZSAaR9bv8PKmBNzjQoqtGjAywT2a/JR YYq8o0dbK32t37kKbml79LAr1bcAk3ssyJyNPN5Q= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:07 +1000 Message-Id: <20170717065621.4688-8-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 07/21] spapr: Abort on delete failure in spapr_drc_release() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" We currently ignore errors from the object_property_del() in spapr_drc_release(). But the only way that could fail is if the property doesn't exist, in which case it's a bug that we're in spapr_drc_release() at all. So change from ignoring to abort()ing on errors. Signed-off-by: David Gibson --- hw/ppc/spapr_drc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 7f872a4803..fd5614094d 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -367,7 +367,7 @@ static void spapr_drc_release(sPAPRDRConnector *drc) g_free(drc->fdt); drc->fdt =3D NULL; drc->fdt_start_offset =3D 0; - object_property_del(OBJECT(drc), "device", NULL); + object_property_del(OBJECT(drc), "device", &error_abort); drc->dev =3D NULL; } =20 --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275187873347.59173582677295; Mon, 17 Jul 2017 00:06:27 -0700 (PDT) Received: from localhost ([::1]:48333 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX06q-0002Xw-Au for importer@patchew.org; Mon, 17 Jul 2017 03:06:24 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40545) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxK-0002aQ-N8 for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:36 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxJ-0001ZC-9f for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:34 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:51631) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxI-0001XD-TT; Mon, 17 Jul 2017 02:56:33 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM11wjz9t2V; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=AW8WGMvUuoeSTPdSZ5ZxEnMR/Xer3/vTxOtikFQV4XI=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=CjeeTv2BSb3sPBZ21YBvF6isHtrU+koBsGqzlBxu6CAiKDZwuOXV+IpMiOEXi8LC1 K6JnnII9PtH1++M2AwzQrheFU3QgVKFzBMcVQ/M3JOiuRInbV8ERxOMHuQZMBIqk6u Nva/rfFSJapJQ5XxNFSBgGSpFhvSD4829EDqfBOk= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:08 +1000 Message-Id: <20170717065621.4688-9-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 08/21] spapr: Refactor spapr_drc_detach() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" This function has two unused parameters - remove them. It also sets awaiting_release on all paths, except one. On that path setting it is harmless, since it will be immediately cleared by spapr_drc_release(). So factor it out of the if statements. Signed-off-by: David Gibson Reviewed-by: Greg Kurz Tested-by: Daniel Barboza --- hw/ppc/spapr.c | 11 +++-------- hw/ppc/spapr_drc.c | 12 ++++++------ hw/ppc/spapr_pci.c | 7 +------ include/hw/ppc/spapr_drc.h | 2 +- 4 files changed, 11 insertions(+), 21 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 8818647e1a..16d450f21c 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -2654,7 +2654,7 @@ static void spapr_add_lmbs(DeviceState *dev, uint64_t= addr_start, uint64_t size, addr -=3D SPAPR_MEMORY_BLOCK_SIZE; drc =3D spapr_drc_by_id(TYPE_SPAPR_DRC_LMB, addr / SPAPR_MEMORY_BLOCK_SIZE); - spapr_drc_detach(drc, dev, NULL); + spapr_drc_detach(drc); } g_free(fdt); error_propagate(errp, local_err); @@ -2876,7 +2876,7 @@ static void spapr_memory_unplug_request(HotplugHandle= r *hotplug_dev, addr / SPAPR_MEMORY_BLOCK_SIZE); g_assert(drc); =20 - spapr_drc_detach(drc, dev, errp); + spapr_drc_detach(drc); addr +=3D SPAPR_MEMORY_BLOCK_SIZE; } =20 @@ -2942,7 +2942,6 @@ void spapr_core_unplug_request(HotplugHandler *hotplu= g_dev, DeviceState *dev, { int index; sPAPRDRConnector *drc; - Error *local_err =3D NULL; CPUCore *cc =3D CPU_CORE(dev); int smt =3D kvmppc_smt_threads(); =20 @@ -2959,11 +2958,7 @@ void spapr_core_unplug_request(HotplugHandler *hotpl= ug_dev, DeviceState *dev, drc =3D spapr_drc_by_id(TYPE_SPAPR_DRC_CPU, index * smt); g_assert(drc); =20 - spapr_drc_detach(drc, dev, &local_err); - if (local_err) { - error_propagate(errp, local_err); - return; - } + spapr_drc_detach(drc); =20 spapr_hotplug_req_remove_by_index(drc); } diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index fd5614094d..15a3d00049 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -70,7 +70,7 @@ static uint32_t drc_isolate_physical(sPAPRDRConnector *dr= c) uint32_t drc_index =3D spapr_drc_index(drc); if (drc->configured) { trace_spapr_drc_set_isolation_state_finalizing(drc_index); - spapr_drc_detach(drc, DEVICE(drc->dev), NULL); + spapr_drc_detach(drc); } else { trace_spapr_drc_set_isolation_state_deferring(drc_index); } @@ -134,7 +134,7 @@ static uint32_t drc_isolate_logical(sPAPRDRConnector *d= rc) uint32_t drc_index =3D spapr_drc_index(drc); if (drc->configured) { trace_spapr_drc_set_isolation_state_finalizing(drc_index); - spapr_drc_detach(drc, DEVICE(drc->dev), NULL); + spapr_drc_detach(drc); } else { trace_spapr_drc_set_isolation_state_deferring(drc_index); } @@ -187,7 +187,7 @@ static uint32_t drc_set_unusable(sPAPRDRConnector *drc) if (drc->awaiting_release) { uint32_t drc_index =3D spapr_drc_index(drc); trace_spapr_drc_set_allocation_state_finalizing(drc_index); - spapr_drc_detach(drc, DEVICE(drc->dev), NULL); + spapr_drc_detach(drc); } =20 return RTAS_OUT_SUCCESS; @@ -371,20 +371,20 @@ static void spapr_drc_release(sPAPRDRConnector *drc) drc->dev =3D NULL; } =20 -void spapr_drc_detach(sPAPRDRConnector *drc, DeviceState *d, Error **errp) +void spapr_drc_detach(sPAPRDRConnector *drc) { trace_spapr_drc_detach(spapr_drc_index(drc)); =20 + drc->awaiting_release =3D true; + if (drc->isolation_state !=3D SPAPR_DR_ISOLATION_STATE_ISOLATED) { trace_spapr_drc_awaiting_isolated(spapr_drc_index(drc)); - drc->awaiting_release =3D true; return; } =20 if (spapr_drc_type(drc) !=3D SPAPR_DR_CONNECTOR_TYPE_PCI && drc->allocation_state !=3D SPAPR_DR_ALLOCATION_STATE_UNUSABLE) { trace_spapr_drc_awaiting_unusable(spapr_drc_index(drc)); - drc->awaiting_release =3D true; return; } =20 diff --git a/hw/ppc/spapr_pci.c b/hw/ppc/spapr_pci.c index 1e84c552d8..092a2f5f3d 100644 --- a/hw/ppc/spapr_pci.c +++ b/hw/ppc/spapr_pci.c @@ -1478,7 +1478,6 @@ static void spapr_pci_unplug_request(HotplugHandler *= plug_handler, PCIDevice *pdev =3D PCI_DEVICE(plugged_dev); sPAPRDRConnectorClass *drck; sPAPRDRConnector *drc =3D spapr_phb_get_pci_drc(phb, pdev); - Error *local_err =3D NULL; =20 if (!phb->dr_enabled) { error_setg(errp, QERR_BUS_NO_HOTPLUG, @@ -1516,11 +1515,7 @@ static void spapr_pci_unplug_request(HotplugHandler = *plug_handler, } } =20 - spapr_drc_detach(drc, DEVICE(pdev), &local_err); - if (local_err) { - error_propagate(errp, local_err); - return; - } + spapr_drc_detach(drc); =20 /* if this isn't func 0, defer unplug event. otherwise signal remo= val * for all present functions diff --git a/include/hw/ppc/spapr_drc.h b/include/hw/ppc/spapr_drc.h index 18a196e831..fc8b721639 100644 --- a/include/hw/ppc/spapr_drc.h +++ b/include/hw/ppc/spapr_drc.h @@ -242,6 +242,6 @@ int spapr_drc_populate_dt(void *fdt, int fdt_offset, Ob= ject *owner, =20 void spapr_drc_attach(sPAPRDRConnector *drc, DeviceState *d, void *fdt, int fdt_start_offset, Error **errp); -void spapr_drc_detach(sPAPRDRConnector *drc, DeviceState *d, Error **errp); +void spapr_drc_detach(sPAPRDRConnector *drc); =20 #endif /* HW_SPAPR_DRC_H */ --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 150027532454754.11961656320818; Mon, 17 Jul 2017 00:08:44 -0700 (PDT) Received: from localhost ([::1]:48346 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX08z-0004By-Rb for importer@patchew.org; Mon, 17 Jul 2017 03:08:37 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40554) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxL-0002ac-1q for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:38 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxJ-0001ZI-9l for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:35 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:44287) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxI-0001X5-Li; Mon, 17 Jul 2017 02:56:33 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGL6Sv9z9t2L; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274586; bh=RS1gUosMVRuZeA7jBL7DQJ6PXoMCDhcCE3CvD0hJXbM=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=NedrzK4QGX3jRBzvRCplxWCGiFNJs9V6uNYAbFzs9YI8QbGCuo4njzMRK84clkb2y l9/QGhi6YHHOwLLqhYXdH99di4+EXyHQK05+3rNqRcmTjtcVs67bCKuou5/8sWT1pm gZ2p91tgAZQJgafkxWyjrN3lZJh5vLd95TgwnIf4= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:09 +1000 Message-Id: <20170717065621.4688-10-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 09/21] spapr: Cleanups relating to DRC awaiting_release field X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" 'awaiting_release' indicates that the host has requested an unplug of the device attached to the DRC, but the guest has not (yet) put the device into a state where it is safe to complete removal. 1. Rename it to 'unplug_requested' which to me at least is clearer 2. Remove the ->release_pending() method used to check this from outside spapr_drc.c. The method only plausibly has one implementation, so use a plain function (spapr_drc_unplug_requested()) instead. 3. Remove it from the migration stream. Attempting to migrate mid-unplug is broken not just for spapr - in general management has no good way to determine if the device should be present on the destination or not. So, until that's fixed, there's no point adding extra things to the stream. Signed-off-by: David Gibson Reviewed-by: Greg Kurz Tested-by: Daniel Barboza --- hw/ppc/spapr_drc.c | 26 +++++++++----------------- hw/ppc/spapr_pci.c | 6 ++---- include/hw/ppc/spapr_drc.h | 11 ++++++----- 3 files changed, 17 insertions(+), 26 deletions(-) diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 15a3d00049..03ef75c70c 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -66,7 +66,7 @@ static uint32_t drc_isolate_physical(sPAPRDRConnector *dr= c) * configured state, as suggested by the state diagram from PAPR+ * 2.7, 13.4 */ - if (drc->awaiting_release) { + if (drc->unplug_requested) { uint32_t drc_index =3D spapr_drc_index(drc); if (drc->configured) { trace_spapr_drc_set_isolation_state_finalizing(drc_index); @@ -116,7 +116,7 @@ static uint32_t drc_isolate_logical(sPAPRDRConnector *d= rc) * actually being unplugged, fail the isolation request here. */ if (spapr_drc_type(drc) =3D=3D SPAPR_DR_CONNECTOR_TYPE_LMB - && !drc->awaiting_release) { + && !drc->unplug_requested) { return RTAS_OUT_HW_ERROR; } =20 @@ -130,7 +130,7 @@ static uint32_t drc_isolate_logical(sPAPRDRConnector *d= rc) * configured state, as suggested by the state diagram from PAPR+ * 2.7, 13.4 */ - if (drc->awaiting_release) { + if (drc->unplug_requested) { uint32_t drc_index =3D spapr_drc_index(drc); if (drc->configured) { trace_spapr_drc_set_isolation_state_finalizing(drc_index); @@ -170,7 +170,7 @@ static uint32_t drc_set_usable(sPAPRDRConnector *drc) if (!drc->dev) { return RTAS_OUT_NO_SUCH_INDICATOR; } - if (drc->awaiting_release) { + if (drc->unplug_requested) { /* Don't allow the guest to move a device away from UNUSABLE * state when we want to unplug it */ return RTAS_OUT_NO_SUCH_INDICATOR; @@ -184,7 +184,7 @@ static uint32_t drc_set_usable(sPAPRDRConnector *drc) static uint32_t drc_set_unusable(sPAPRDRConnector *drc) { drc->allocation_state =3D SPAPR_DR_ALLOCATION_STATE_UNUSABLE; - if (drc->awaiting_release) { + if (drc->unplug_requested) { uint32_t drc_index =3D spapr_drc_index(drc); trace_spapr_drc_set_allocation_state_finalizing(drc_index); spapr_drc_detach(drc); @@ -363,7 +363,7 @@ static void spapr_drc_release(sPAPRDRConnector *drc) =20 drck->release(drc->dev); =20 - drc->awaiting_release =3D false; + drc->unplug_requested =3D false; g_free(drc->fdt); drc->fdt =3D NULL; drc->fdt_start_offset =3D 0; @@ -375,7 +375,7 @@ void spapr_drc_detach(sPAPRDRConnector *drc) { trace_spapr_drc_detach(spapr_drc_index(drc)); =20 - drc->awaiting_release =3D true; + drc->unplug_requested =3D true; =20 if (drc->isolation_state !=3D SPAPR_DR_ISOLATION_STATE_ISOLATED) { trace_spapr_drc_awaiting_isolated(spapr_drc_index(drc)); @@ -391,11 +391,6 @@ void spapr_drc_detach(sPAPRDRConnector *drc) spapr_drc_release(drc); } =20 -static bool release_pending(sPAPRDRConnector *drc) -{ - return drc->awaiting_release; -} - void spapr_drc_reset(sPAPRDRConnector *drc) { trace_spapr_drc_reset(spapr_drc_index(drc)); @@ -406,7 +401,7 @@ void spapr_drc_reset(sPAPRDRConnector *drc) /* immediately upon reset we can safely assume DRCs whose devices * are pending removal can be safely removed. */ - if (drc->awaiting_release) { + if (drc->unplug_requested) { spapr_drc_release(drc); } =20 @@ -454,7 +449,7 @@ static bool spapr_drc_needed(void *opaque) case SPAPR_DR_CONNECTOR_TYPE_LMB: rc =3D !((drc->isolation_state =3D=3D SPAPR_DR_ISOLATION_STATE_UNI= SOLATED) && (drc->allocation_state =3D=3D SPAPR_DR_ALLOCATION_STATE_USA= BLE) && - drc->configured && !drc->awaiting_release); + drc->configured); break; case SPAPR_DR_CONNECTOR_TYPE_PHB: case SPAPR_DR_CONNECTOR_TYPE_VIO: @@ -474,7 +469,6 @@ static const VMStateDescription vmstate_spapr_drc =3D { VMSTATE_UINT32(allocation_state, sPAPRDRConnector), VMSTATE_UINT32(dr_indicator, sPAPRDRConnector), VMSTATE_BOOL(configured, sPAPRDRConnector), - VMSTATE_BOOL(awaiting_release, sPAPRDRConnector), VMSTATE_END_OF_LIST() } }; @@ -565,11 +559,9 @@ static void spapr_dr_connector_instance_init(Object *o= bj) static void spapr_dr_connector_class_init(ObjectClass *k, void *data) { DeviceClass *dk =3D DEVICE_CLASS(k); - sPAPRDRConnectorClass *drck =3D SPAPR_DR_CONNECTOR_CLASS(k); =20 dk->realize =3D realize; dk->unrealize =3D unrealize; - drck->release_pending =3D release_pending; /* * Reason: it crashes FIXME find and document the real reason */ diff --git a/hw/ppc/spapr_pci.c b/hw/ppc/spapr_pci.c index 092a2f5f3d..6ecdf29d28 100644 --- a/hw/ppc/spapr_pci.c +++ b/hw/ppc/spapr_pci.c @@ -1476,7 +1476,6 @@ static void spapr_pci_unplug_request(HotplugHandler *= plug_handler, { sPAPRPHBState *phb =3D SPAPR_PCI_HOST_BRIDGE(DEVICE(plug_handler)); PCIDevice *pdev =3D PCI_DEVICE(plugged_dev); - sPAPRDRConnectorClass *drck; sPAPRDRConnector *drc =3D spapr_phb_get_pci_drc(phb, pdev); =20 if (!phb->dr_enabled) { @@ -1488,8 +1487,7 @@ static void spapr_pci_unplug_request(HotplugHandler *= plug_handler, g_assert(drc); g_assert(drc->dev =3D=3D plugged_dev); =20 - drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(drc); - if (!drck->release_pending(drc)) { + if (!spapr_drc_unplug_requested(drc)) { PCIBus *bus =3D PCI_BUS(qdev_get_parent_bus(DEVICE(pdev))); uint32_t slotnr =3D PCI_SLOT(pdev->devfn); sPAPRDRConnector *func_drc; @@ -1505,7 +1503,7 @@ static void spapr_pci_unplug_request(HotplugHandler *= plug_handler, func_drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(func_drc); state =3D func_drck->dr_entity_sense(func_drc); if (state =3D=3D SPAPR_DR_ENTITY_SENSE_PRESENT - && !func_drck->release_pending(func_drc)) { + && !spapr_drc_unplug_requested(func_drc)) { error_setg(errp, "PCI: slot %d, function %d still present. " "Must unplug all non-0 functions first.", diff --git a/include/hw/ppc/spapr_drc.h b/include/hw/ppc/spapr_drc.h index fc8b721639..5fa502e465 100644 --- a/include/hw/ppc/spapr_drc.h +++ b/include/hw/ppc/spapr_drc.h @@ -199,10 +199,9 @@ typedef struct sPAPRDRConnector { bool configured; sPAPRConfigureConnectorState *ccs; =20 - bool awaiting_release; - /* device pointer, via link property */ DeviceState *dev; + bool unplug_requested; } sPAPRDRConnector; =20 typedef struct sPAPRDRConnectorClass { @@ -218,9 +217,6 @@ typedef struct sPAPRDRConnectorClass { uint32_t (*isolate)(sPAPRDRConnector *drc); uint32_t (*unisolate)(sPAPRDRConnector *drc); void (*release)(DeviceState *dev); - - /* QEMU interfaces for managing hotplug operations */ - bool (*release_pending)(sPAPRDRConnector *drc); } sPAPRDRConnectorClass; =20 static inline bool spapr_drc_hotplugged(DeviceState *dev) @@ -244,4 +240,9 @@ void spapr_drc_attach(sPAPRDRConnector *drc, DeviceStat= e *d, void *fdt, int fdt_start_offset, Error **errp); void spapr_drc_detach(sPAPRDRConnector *drc); =20 +static inline bool spapr_drc_unplug_requested(sPAPRDRConnector *drc) +{ + return drc->unplug_requested; +} + #endif /* HW_SPAPR_DRC_H */ --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275231909756.5237489765703; Mon, 17 Jul 2017 00:07:11 -0700 (PDT) Received: from localhost ([::1]:48336 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX07S-00033a-6S for importer@patchew.org; Mon, 17 Jul 2017 03:07:02 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40733) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxP-0002fJ-7F for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:43 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxJ-0001Zn-Ko for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:39 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:37737) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxJ-0001XC-0V; Mon, 17 Jul 2017 02:56:33 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM1jMdz9t2h; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=6FaiWPXAitzU63Chnv79s+FWm8RbZuVb4amgdZV1sEs=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=KEWs8PFA0+O9xSyz4Us8HkWKICuXm9dKtfYBmce+tUMVGG0IgoSlJ8Byx3Dj8L8SM pId1N/Zhxx4HHCzc5yVIm+EhoNOtKbhEPbM83Xm6SDEnwVI+JKaPVhIwX8Jzzp2gEN rGW2Wr6olYXFED0is6ij4FrFA7xS1rWnj3GcRito= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:10 +1000 Message-Id: <20170717065621.4688-11-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 10/21] spapr: Consolidate DRC state variables X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Each DRC has three fields describing its state: isolation_state, allocation_state and configured. At first this seems like a reasonable representation, since its based directly on the PAPR defined isolation-state and allocation-state indicators. However: * Only a few combinations of the two fields' values are permitted * allocation_state isn't used at all for physical DRCs * The indicators are write only so they don't really have a well defined current value independent of each other This replaces these variables with a single state variable, whose names and numbers are based on the diagram in LoPAPR section 13.4. Along with this we add code to check the current state on various operations and make sure the requested transition is permitted. Strictly speaking, this makes guest visible changes to behaviour (since we probably allowed some transitions we shouldn't have before). However, a hypothetical guest broken by that wasn't PAPR compliant, and probably wouldn't have worked under PowerVM. Signed-off-by: David Gibson Reviewed-by: Daniel Barboza Tested-by: Daniel Barboza --- hw/ppc/spapr_drc.c | 225 +++++++++++++++++++++++++----------------= ---- hw/ppc/trace-events | 3 +- include/hw/ppc/spapr_drc.h | 25 ++++- 3 files changed, 145 insertions(+), 108 deletions(-) diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 03ef75c70c..37d7ae7930 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -48,6 +48,17 @@ uint32_t spapr_drc_index(sPAPRDRConnector *drc) =20 static uint32_t drc_isolate_physical(sPAPRDRConnector *drc) { + switch (drc->state) { + case SPAPR_DRC_STATE_PHYSICAL_POWERON: + return RTAS_OUT_SUCCESS; /* Nothing to do */ + case SPAPR_DRC_STATE_PHYSICAL_CONFIGURED: + break; /* see below */ + case SPAPR_DRC_STATE_PHYSICAL_UNISOLATE: + return RTAS_OUT_PARAM_ERROR; /* not allowed */ + default: + g_assert_not_reached(); + } + /* if the guest is configuring a device attached to this DRC, we * should reset the configuration state at this point since it may * no longer be reliable (guest released device and needs to start @@ -56,32 +67,29 @@ static uint32_t drc_isolate_physical(sPAPRDRConnector *= drc) g_free(drc->ccs); drc->ccs =3D NULL; =20 - drc->isolation_state =3D SPAPR_DR_ISOLATION_STATE_ISOLATED; + drc->state =3D SPAPR_DRC_STATE_PHYSICAL_POWERON; =20 - /* if we're awaiting release, but still in an unconfigured state, - * it's likely the guest is still in the process of configuring - * the device and is transitioning the devices to an ISOLATED - * state as a part of that process. so we only complete the - * removal when this transition happens for a device in a - * configured state, as suggested by the state diagram from PAPR+ - * 2.7, 13.4 - */ if (drc->unplug_requested) { uint32_t drc_index =3D spapr_drc_index(drc); - if (drc->configured) { - trace_spapr_drc_set_isolation_state_finalizing(drc_index); - spapr_drc_detach(drc); - } else { - trace_spapr_drc_set_isolation_state_deferring(drc_index); - } + trace_spapr_drc_set_isolation_state_finalizing(drc_index); + spapr_drc_detach(drc); } - drc->configured =3D false; =20 return RTAS_OUT_SUCCESS; } =20 static uint32_t drc_unisolate_physical(sPAPRDRConnector *drc) { + switch (drc->state) { + case SPAPR_DRC_STATE_PHYSICAL_UNISOLATE: + case SPAPR_DRC_STATE_PHYSICAL_CONFIGURED: + return RTAS_OUT_SUCCESS; /* Nothing to do */ + case SPAPR_DRC_STATE_PHYSICAL_POWERON: + break; /* see below */ + default: + g_assert_not_reached(); + } + /* cannot unisolate a non-existent resource, and, or resources * which are in an 'UNUSABLE' allocation state. (PAPR 2.7, * 13.5.3.5) @@ -90,13 +98,25 @@ static uint32_t drc_unisolate_physical(sPAPRDRConnector= *drc) return RTAS_OUT_NO_SUCH_INDICATOR; } =20 - drc->isolation_state =3D SPAPR_DR_ISOLATION_STATE_UNISOLATED; + drc->state =3D SPAPR_DRC_STATE_PHYSICAL_UNISOLATE; =20 return RTAS_OUT_SUCCESS; } =20 static uint32_t drc_isolate_logical(sPAPRDRConnector *drc) { + switch (drc->state) { + case SPAPR_DRC_STATE_LOGICAL_AVAILABLE: + case SPAPR_DRC_STATE_LOGICAL_UNUSABLE: + return RTAS_OUT_SUCCESS; /* Nothing to do */ + case SPAPR_DRC_STATE_LOGICAL_CONFIGURED: + break; /* see below */ + case SPAPR_DRC_STATE_LOGICAL_UNISOLATE: + return RTAS_OUT_PARAM_ERROR; /* not allowed */ + default: + g_assert_not_reached(); + } + /* if the guest is configuring a device attached to this DRC, we * should reset the configuration state at this point since it may * no longer be reliable (guest released device and needs to start @@ -120,7 +140,7 @@ static uint32_t drc_isolate_logical(sPAPRDRConnector *d= rc) return RTAS_OUT_HW_ERROR; } =20 - drc->isolation_state =3D SPAPR_DR_ISOLATION_STATE_ISOLATED; + drc->state =3D SPAPR_DRC_STATE_LOGICAL_AVAILABLE; =20 /* if we're awaiting release, but still in an unconfigured state, * it's likely the guest is still in the process of configuring @@ -132,36 +152,46 @@ static uint32_t drc_isolate_logical(sPAPRDRConnector = *drc) */ if (drc->unplug_requested) { uint32_t drc_index =3D spapr_drc_index(drc); - if (drc->configured) { - trace_spapr_drc_set_isolation_state_finalizing(drc_index); - spapr_drc_detach(drc); - } else { - trace_spapr_drc_set_isolation_state_deferring(drc_index); - } + trace_spapr_drc_set_isolation_state_finalizing(drc_index); + spapr_drc_detach(drc); } - drc->configured =3D false; - return RTAS_OUT_SUCCESS; } =20 static uint32_t drc_unisolate_logical(sPAPRDRConnector *drc) { - /* cannot unisolate a non-existent resource, and, or resources - * which are in an 'UNUSABLE' allocation state. (PAPR 2.7, - * 13.5.3.5) - */ - if (!drc->dev || - drc->allocation_state =3D=3D SPAPR_DR_ALLOCATION_STATE_UNUSABLE) { - return RTAS_OUT_NO_SUCH_INDICATOR; + switch (drc->state) { + case SPAPR_DRC_STATE_LOGICAL_UNISOLATE: + case SPAPR_DRC_STATE_LOGICAL_CONFIGURED: + return RTAS_OUT_SUCCESS; /* Nothing to do */ + case SPAPR_DRC_STATE_LOGICAL_AVAILABLE: + break; /* see below */ + case SPAPR_DRC_STATE_LOGICAL_UNUSABLE: + return RTAS_OUT_NO_SUCH_INDICATOR; /* not allowed */ + default: + g_assert_not_reached(); } =20 - drc->isolation_state =3D SPAPR_DR_ISOLATION_STATE_UNISOLATED; + /* Move to AVAILABLE state should have ensured device was present */ + g_assert(drc->dev); =20 + drc->state =3D SPAPR_DRC_STATE_LOGICAL_UNISOLATE; return RTAS_OUT_SUCCESS; } =20 static uint32_t drc_set_usable(sPAPRDRConnector *drc) { + switch (drc->state) { + case SPAPR_DRC_STATE_LOGICAL_AVAILABLE: + case SPAPR_DRC_STATE_LOGICAL_UNISOLATE: + case SPAPR_DRC_STATE_LOGICAL_CONFIGURED: + return RTAS_OUT_SUCCESS; /* Nothing to do */ + case SPAPR_DRC_STATE_LOGICAL_UNUSABLE: + break; /* see below */ + default: + g_assert_not_reached(); + } + /* if there's no resource/device associated with the DRC, there's * no way for us to put it in an allocation state consistent with * being 'USABLE'. PAPR 2.7, 13.5.3.4 documents that this should @@ -176,14 +206,26 @@ static uint32_t drc_set_usable(sPAPRDRConnector *drc) return RTAS_OUT_NO_SUCH_INDICATOR; } =20 - drc->allocation_state =3D SPAPR_DR_ALLOCATION_STATE_USABLE; + drc->state =3D SPAPR_DRC_STATE_LOGICAL_AVAILABLE; =20 return RTAS_OUT_SUCCESS; } =20 static uint32_t drc_set_unusable(sPAPRDRConnector *drc) { - drc->allocation_state =3D SPAPR_DR_ALLOCATION_STATE_UNUSABLE; + switch (drc->state) { + case SPAPR_DRC_STATE_LOGICAL_UNUSABLE: + return RTAS_OUT_SUCCESS; /* Nothing to do */ + case SPAPR_DRC_STATE_LOGICAL_AVAILABLE: + break; /* see below */ + case SPAPR_DRC_STATE_LOGICAL_UNISOLATE: + case SPAPR_DRC_STATE_LOGICAL_CONFIGURED: + return RTAS_OUT_NO_SUCH_INDICATOR; /* not allowed */ + default: + g_assert_not_reached(); + } + + drc->state =3D SPAPR_DRC_STATE_LOGICAL_UNUSABLE; if (drc->unplug_requested) { uint32_t drc_index =3D spapr_drc_index(drc); trace_spapr_drc_set_allocation_state_finalizing(drc_index); @@ -241,11 +283,16 @@ static sPAPRDREntitySense physical_entity_sense(sPAPR= DRConnector *drc) =20 static sPAPRDREntitySense logical_entity_sense(sPAPRDRConnector *drc) { - if (drc->dev - && (drc->allocation_state !=3D SPAPR_DR_ALLOCATION_STATE_UNUSABLE)= ) { - return SPAPR_DR_ENTITY_SENSE_PRESENT; - } else { + switch (drc->state) { + case SPAPR_DRC_STATE_LOGICAL_UNUSABLE: return SPAPR_DR_ENTITY_SENSE_UNUSABLE; + case SPAPR_DRC_STATE_LOGICAL_AVAILABLE: + case SPAPR_DRC_STATE_LOGICAL_UNISOLATE: + case SPAPR_DRC_STATE_LOGICAL_CONFIGURED: + g_assert(drc->dev); + return SPAPR_DR_ENTITY_SENSE_PRESENT; + default: + g_assert_not_reached(); } } =20 @@ -338,13 +385,12 @@ void spapr_drc_attach(sPAPRDRConnector *drc, DeviceSt= ate *d, void *fdt, { trace_spapr_drc_attach(spapr_drc_index(drc)); =20 - if (drc->isolation_state !=3D SPAPR_DR_ISOLATION_STATE_ISOLATED) { + if (drc->dev) { error_setg(errp, "an attached device is still awaiting release"); return; } - if (spapr_drc_type(drc) =3D=3D SPAPR_DR_CONNECTOR_TYPE_PCI) { - g_assert(drc->allocation_state =3D=3D SPAPR_DR_ALLOCATION_STATE_US= ABLE); - } + g_assert((drc->state =3D=3D SPAPR_DRC_STATE_LOGICAL_UNUSABLE) + || (drc->state =3D=3D SPAPR_DRC_STATE_PHYSICAL_POWERON)); g_assert(fdt); =20 drc->dev =3D d; @@ -373,18 +419,16 @@ static void spapr_drc_release(sPAPRDRConnector *drc) =20 void spapr_drc_detach(sPAPRDRConnector *drc) { + sPAPRDRConnectorClass *drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(drc); + trace_spapr_drc_detach(spapr_drc_index(drc)); =20 - drc->unplug_requested =3D true; + g_assert(drc->dev); =20 - if (drc->isolation_state !=3D SPAPR_DR_ISOLATION_STATE_ISOLATED) { - trace_spapr_drc_awaiting_isolated(spapr_drc_index(drc)); - return; - } + drc->unplug_requested =3D true; =20 - if (spapr_drc_type(drc) !=3D SPAPR_DR_CONNECTOR_TYPE_PCI && - drc->allocation_state !=3D SPAPR_DR_ALLOCATION_STATE_UNUSABLE) { - trace_spapr_drc_awaiting_unusable(spapr_drc_index(drc)); + if (drc->state !=3D drck->empty_state) { + trace_spapr_drc_awaiting_quiesce(spapr_drc_index(drc)); return; } =20 @@ -393,6 +437,8 @@ void spapr_drc_detach(sPAPRDRConnector *drc) =20 void spapr_drc_reset(sPAPRDRConnector *drc) { + sPAPRDRConnectorClass *drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(drc); + trace_spapr_drc_reset(spapr_drc_index(drc)); =20 g_free(drc->ccs); @@ -406,19 +452,10 @@ void spapr_drc_reset(sPAPRDRConnector *drc) } =20 if (drc->dev) { - /* A device present at reset is coldplugged */ - drc->isolation_state =3D SPAPR_DR_ISOLATION_STATE_UNISOLATED; - if (spapr_drc_type(drc) !=3D SPAPR_DR_CONNECTOR_TYPE_PCI) { - drc->allocation_state =3D SPAPR_DR_ALLOCATION_STATE_USABLE; - } - drc->dr_indicator =3D SPAPR_DR_INDICATOR_ACTIVE; + /* A device present at reset is ready to go, same as coldplugged */ + drc->state =3D drck->ready_state; } else { - /* Otherwise device is absent, but might be hotplugged */ - drc->isolation_state =3D SPAPR_DR_ISOLATION_STATE_ISOLATED; - if (spapr_drc_type(drc) !=3D SPAPR_DR_CONNECTOR_TYPE_PCI) { - drc->allocation_state =3D SPAPR_DR_ALLOCATION_STATE_UNUSABLE; - } - drc->dr_indicator =3D SPAPR_DR_INDICATOR_INACTIVE; + drc->state =3D drck->empty_state; } } =20 @@ -431,7 +468,6 @@ static bool spapr_drc_needed(void *opaque) { sPAPRDRConnector *drc =3D (sPAPRDRConnector *)opaque; sPAPRDRConnectorClass *drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(drc); - bool rc =3D false; sPAPRDREntitySense value =3D drck->dr_entity_sense(drc); =20 /* If no dev is plugged in there is no need to migrate the DRC state */ @@ -440,23 +476,10 @@ static bool spapr_drc_needed(void *opaque) } =20 /* - * If there is dev plugged in, we need to migrate the DRC state when - * it is different from cold-plugged state - */ - switch (spapr_drc_type(drc)) { - case SPAPR_DR_CONNECTOR_TYPE_PCI: - case SPAPR_DR_CONNECTOR_TYPE_CPU: - case SPAPR_DR_CONNECTOR_TYPE_LMB: - rc =3D !((drc->isolation_state =3D=3D SPAPR_DR_ISOLATION_STATE_UNI= SOLATED) && - (drc->allocation_state =3D=3D SPAPR_DR_ALLOCATION_STATE_USA= BLE) && - drc->configured); - break; - case SPAPR_DR_CONNECTOR_TYPE_PHB: - case SPAPR_DR_CONNECTOR_TYPE_VIO: - default: - g_assert_not_reached(); - } - return rc; + * We need to migrate the state if it's not equal to the expected + * long-term state, which is the same as the coldplugged initial + * state */ + return (drc->state !=3D drck->ready_state); } =20 static const VMStateDescription vmstate_spapr_drc =3D { @@ -465,10 +488,8 @@ static const VMStateDescription vmstate_spapr_drc =3D { .minimum_version_id =3D 1, .needed =3D spapr_drc_needed, .fields =3D (VMStateField []) { - VMSTATE_UINT32(isolation_state, sPAPRDRConnector), - VMSTATE_UINT32(allocation_state, sPAPRDRConnector), + VMSTATE_UINT32(state, sPAPRDRConnector), VMSTATE_UINT32(dr_indicator, sPAPRDRConnector), - VMSTATE_BOOL(configured, sPAPRDRConnector), VMSTATE_END_OF_LIST() } }; @@ -537,23 +558,20 @@ sPAPRDRConnector *spapr_dr_connector_new(Object *owne= r, const char *type, object_property_set_bool(OBJECT(drc), true, "realized", NULL); g_free(prop_name); =20 - /* PCI slot always start in a USABLE state, and stay there */ - if (spapr_drc_type(drc) =3D=3D SPAPR_DR_CONNECTOR_TYPE_PCI) { - drc->allocation_state =3D SPAPR_DR_ALLOCATION_STATE_USABLE; - } - return drc; } =20 static void spapr_dr_connector_instance_init(Object *obj) { sPAPRDRConnector *drc =3D SPAPR_DR_CONNECTOR(obj); + sPAPRDRConnectorClass *drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(drc); =20 object_property_add_uint32_ptr(obj, "id", &drc->id, NULL); object_property_add(obj, "index", "uint32", prop_get_index, NULL, NULL, NULL, NULL); object_property_add(obj, "fdt", "struct", prop_get_fdt, NULL, NULL, NULL, NULL); + drc->state =3D drck->empty_state; } =20 static void spapr_dr_connector_class_init(ObjectClass *k, void *data) @@ -575,6 +593,8 @@ static void spapr_drc_physical_class_init(ObjectClass *= k, void *data) drck->dr_entity_sense =3D physical_entity_sense; drck->isolate =3D drc_isolate_physical; drck->unisolate =3D drc_unisolate_physical; + drck->ready_state =3D SPAPR_DRC_STATE_PHYSICAL_CONFIGURED; + drck->empty_state =3D SPAPR_DRC_STATE_PHYSICAL_POWERON; } =20 static void spapr_drc_logical_class_init(ObjectClass *k, void *data) @@ -584,6 +604,8 @@ static void spapr_drc_logical_class_init(ObjectClass *k= , void *data) drck->dr_entity_sense =3D logical_entity_sense; drck->isolate =3D drc_isolate_logical; drck->unisolate =3D drc_unisolate_logical; + drck->ready_state =3D SPAPR_DRC_STATE_LOGICAL_CONFIGURED; + drck->empty_state =3D SPAPR_DRC_STATE_LOGICAL_UNUSABLE; } =20 static void spapr_drc_cpu_class_init(ObjectClass *k, void *data) @@ -982,6 +1004,7 @@ static void rtas_ibm_configure_connector(PowerPCCPU *c= pu, uint64_t wa_offset; uint32_t drc_index; sPAPRDRConnector *drc; + sPAPRDRConnectorClass *drck; sPAPRConfigureConnectorState *ccs; sPAPRDRCCResponse resp =3D SPAPR_DR_CC_RESPONSE_CONTINUE; int rc; @@ -1001,12 +1024,17 @@ static void rtas_ibm_configure_connector(PowerPCCPU= *cpu, goto out; } =20 - if (!drc->fdt) { - trace_spapr_rtas_ibm_configure_connector_missing_fdt(drc_index); + if ((drc->state !=3D SPAPR_DRC_STATE_LOGICAL_UNISOLATE) + && (drc->state !=3D SPAPR_DRC_STATE_PHYSICAL_UNISOLATE)) { + /* Need to unisolate the device before configuring */ rc =3D SPAPR_DR_CC_RESPONSE_NOT_CONFIGURABLE; goto out; } =20 + g_assert(drc->fdt); + + drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(drc); + ccs =3D drc->ccs; if (!ccs) { ccs =3D g_new0(sPAPRConfigureConnectorState, 1); @@ -1036,18 +1064,11 @@ static void rtas_ibm_configure_connector(PowerPCCPU= *cpu, case FDT_END_NODE: ccs->fdt_depth--; if (ccs->fdt_depth =3D=3D 0) { - sPAPRDRIsolationState state =3D drc->isolation_state; uint32_t drc_index =3D spapr_drc_index(drc); - /* done sending the device tree, don't need to track - * the state anymore - */ + + /* done sending the device tree, move to configured state = */ trace_spapr_drc_set_configured(drc_index); - if (state =3D=3D SPAPR_DR_ISOLATION_STATE_UNISOLATED) { - drc->configured =3D true; - } else { - /* guest should be not configuring an isolated device = */ - trace_spapr_drc_set_configured_skipping(drc_index); - } + drc->state =3D drck->ready_state; g_free(ccs); drc->ccs =3D NULL; ccs =3D NULL; diff --git a/hw/ppc/trace-events b/hw/ppc/trace-events index 3e8e3cffde..8e79f7eaf6 100644 --- a/hw/ppc/trace-events +++ b/hw/ppc/trace-events @@ -46,8 +46,7 @@ spapr_drc_set_configured(uint32_t index) "drc: 0x%"PRIx32 spapr_drc_set_configured_skipping(uint32_t index) "drc: 0x%"PRIx32", isola= ted device" spapr_drc_attach(uint32_t index) "drc: 0x%"PRIx32 spapr_drc_detach(uint32_t index) "drc: 0x%"PRIx32 -spapr_drc_awaiting_isolated(uint32_t index) "drc: 0x%"PRIx32 -spapr_drc_awaiting_unusable(uint32_t index) "drc: 0x%"PRIx32 +spapr_drc_awaiting_quiesce(uint32_t index) "drc: 0x%"PRIx32 spapr_drc_awaiting_allocation(uint32_t index) "drc: 0x%"PRIx32 spapr_drc_reset(uint32_t index) "drc: 0x%"PRIx32 spapr_drc_realize(uint32_t index) "drc: 0x%"PRIx32 diff --git a/include/hw/ppc/spapr_drc.h b/include/hw/ppc/spapr_drc.h index 5fa502e465..4ceaaf0eff 100644 --- a/include/hw/ppc/spapr_drc.h +++ b/include/hw/ppc/spapr_drc.h @@ -173,6 +173,24 @@ typedef enum { SPAPR_DR_CC_RESPONSE_NOT_CONFIGURABLE =3D -9003, } sPAPRDRCCResponse; =20 +typedef enum { + /* + * Values come from Fig. 12 in LoPAPR section 13.4 + * + * These are exposed in the migration stream, so don't change + * them. + */ + SPAPR_DRC_STATE_INVALID =3D 0, + SPAPR_DRC_STATE_LOGICAL_UNUSABLE =3D 1, + SPAPR_DRC_STATE_LOGICAL_AVAILABLE =3D 2, + SPAPR_DRC_STATE_LOGICAL_UNISOLATE =3D 3, + SPAPR_DRC_STATE_LOGICAL_CONFIGURED =3D 4, + SPAPR_DRC_STATE_PHYSICAL_AVAILABLE =3D 5, + SPAPR_DRC_STATE_PHYSICAL_POWERON =3D 6, + SPAPR_DRC_STATE_PHYSICAL_UNISOLATE =3D 7, + SPAPR_DRC_STATE_PHYSICAL_CONFIGURED =3D 8, +} sPAPRDRCState; + /* rtas-configure-connector state */ typedef struct sPAPRConfigureConnectorState { int fdt_offset; @@ -189,14 +207,11 @@ typedef struct sPAPRDRConnector { /* DR-indicator */ uint32_t dr_indicator; =20 - /* sensor/indicator states */ - uint32_t isolation_state; - uint32_t allocation_state; + uint32_t state; =20 /* configure-connector state */ void *fdt; int fdt_start_offset; - bool configured; sPAPRConfigureConnectorState *ccs; =20 /* device pointer, via link property */ @@ -207,6 +222,8 @@ typedef struct sPAPRDRConnector { typedef struct sPAPRDRConnectorClass { /*< private >*/ DeviceClass parent; + sPAPRDRCState empty_state; + sPAPRDRCState ready_state; =20 /*< public >*/ sPAPRDRConnectorTypeShift typeshift; --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275042505660.9362376011908; Mon, 17 Jul 2017 00:04:02 -0700 (PDT) Received: from localhost ([::1]:48320 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX04W-0000JU-7x for importer@patchew.org; Mon, 17 Jul 2017 03:04:00 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40744) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxP-0002gD-Rh for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:42 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxM-0001d5-JX for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:39 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:49637) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxL-0001a0-S5; Mon, 17 Jul 2017 02:56:36 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGN1nz0z9t3P; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274588; bh=KcHApYgFuqdruyXL0AOtblFcfBfS8OKL12yVLOIn6wU=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=DFoRGmL3eU/tPKSdWSmjf5LWGI5ydKPNH6T2SVbochwXyyN/CY/4b/MtrqzEGD7+e zcCZ8BSkokPBNc0M71sBe5Ard5jH4+IRYIO23b8dj+LHtdcxsB2sQQyBcXenEUSZWk afDzeOJkvX2Usp2hq8PUflBRGYRtK/8c0qji+O58= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:11 +1000 Message-Id: <20170717065621.4688-12-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 11/21] spapr: Remove sPAPRConfigureConnectorState sub-structure X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Most of the time, the state of a DRC object is contained in the single 'state' variable. However, during the transition from UNISOLATE to CONFIGURED state requires multiple calls to the ibm,configure-connector RTAS call to retrieve the device tree for the attached device. We need some extra state to keep track of where we're up to in delivering the device tree information to the guest. Currently that extra state is in a sPAPRConfigureConnectorState substructure which is only allocated when we're in the middle of the configure connector process. That sounds like a good idea, but the extra state is only two integers - on many platforms that will take up the same room as the (maybe NULL) ccs pointer even before malloc() overhead. Plus it's another object whose lifetime we need to manage. In short, it's not worth it. So, fold the sPAPRConfigureConnectorState substructure directly into the DRC object. Previously the structure was allocated lazily when the configure-connector call discovers it's not there. Now, we need to initialize the subfields pre-emptively, as soon as we enter UNISOLATE state. Although it's not strictly necessary (the field values should only ever be consulted when in UNISOLATE state), we try to keep them at -1 when in other states, as a debugging aid. Signed-off-by: David Gibson Reviewed-by: Daniel Barboza Tested-by: Daniel Barboza --- hw/ppc/spapr_drc.c | 56 +++++++++++++++---------------------------= ---- include/hw/ppc/spapr_drc.h | 16 +++++-------- 2 files changed, 24 insertions(+), 48 deletions(-) diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 37d7ae7930..11b9fa534b 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -59,14 +59,6 @@ static uint32_t drc_isolate_physical(sPAPRDRConnector *d= rc) g_assert_not_reached(); } =20 - /* if the guest is configuring a device attached to this DRC, we - * should reset the configuration state at this point since it may - * no longer be reliable (guest released device and needs to start - * over, or unplug occurred so the FDT is no longer valid) - */ - g_free(drc->ccs); - drc->ccs =3D NULL; - drc->state =3D SPAPR_DRC_STATE_PHYSICAL_POWERON; =20 if (drc->unplug_requested) { @@ -99,6 +91,8 @@ static uint32_t drc_unisolate_physical(sPAPRDRConnector *= drc) } =20 drc->state =3D SPAPR_DRC_STATE_PHYSICAL_UNISOLATE; + drc->ccs_offset =3D drc->fdt_start_offset; + drc->ccs_depth =3D 0; =20 return RTAS_OUT_SUCCESS; } @@ -117,14 +111,6 @@ static uint32_t drc_isolate_logical(sPAPRDRConnector *= drc) g_assert_not_reached(); } =20 - /* if the guest is configuring a device attached to this DRC, we - * should reset the configuration state at this point since it may - * no longer be reliable (guest released device and needs to start - * over, or unplug occurred so the FDT is no longer valid) - */ - g_free(drc->ccs); - drc->ccs =3D NULL; - /* * Fail any requests to ISOLATE the LMB DRC if this LMB doesn't * belong to a DIMM device that is marked for removal. @@ -176,6 +162,9 @@ static uint32_t drc_unisolate_logical(sPAPRDRConnector = *drc) g_assert(drc->dev); =20 drc->state =3D SPAPR_DRC_STATE_LOGICAL_UNISOLATE; + drc->ccs_offset =3D drc->fdt_start_offset; + drc->ccs_depth =3D 0; + return RTAS_OUT_SUCCESS; } =20 @@ -441,9 +430,6 @@ void spapr_drc_reset(sPAPRDRConnector *drc) =20 trace_spapr_drc_reset(spapr_drc_index(drc)); =20 - g_free(drc->ccs); - drc->ccs =3D NULL; - /* immediately upon reset we can safely assume DRCs whose devices * are pending removal can be safely removed. */ @@ -457,6 +443,9 @@ void spapr_drc_reset(sPAPRDRConnector *drc) } else { drc->state =3D drck->empty_state; } + + drc->ccs_offset =3D -1; + drc->ccs_depth =3D -1; } =20 static void drc_reset(void *opaque) @@ -1005,7 +994,6 @@ static void rtas_ibm_configure_connector(PowerPCCPU *c= pu, uint32_t drc_index; sPAPRDRConnector *drc; sPAPRDRConnectorClass *drck; - sPAPRConfigureConnectorState *ccs; sPAPRDRCCResponse resp =3D SPAPR_DR_CC_RESPONSE_CONTINUE; int rc; =20 @@ -1035,25 +1023,18 @@ static void rtas_ibm_configure_connector(PowerPCCPU= *cpu, =20 drck =3D SPAPR_DR_CONNECTOR_GET_CLASS(drc); =20 - ccs =3D drc->ccs; - if (!ccs) { - ccs =3D g_new0(sPAPRConfigureConnectorState, 1); - ccs->fdt_offset =3D drc->fdt_start_offset; - drc->ccs =3D ccs; - } - do { uint32_t tag; const char *name; const struct fdt_property *prop; int fdt_offset_next, prop_len; =20 - tag =3D fdt_next_tag(drc->fdt, ccs->fdt_offset, &fdt_offset_next); + tag =3D fdt_next_tag(drc->fdt, drc->ccs_offset, &fdt_offset_next); =20 switch (tag) { case FDT_BEGIN_NODE: - ccs->fdt_depth++; - name =3D fdt_get_name(drc->fdt, ccs->fdt_offset, NULL); + drc->ccs_depth++; + name =3D fdt_get_name(drc->fdt, drc->ccs_offset, NULL); =20 /* provide the name of the next OF node */ wa_offset =3D CC_VAL_DATA_OFFSET; @@ -1062,23 +1043,22 @@ static void rtas_ibm_configure_connector(PowerPCCPU= *cpu, resp =3D SPAPR_DR_CC_RESPONSE_NEXT_CHILD; break; case FDT_END_NODE: - ccs->fdt_depth--; - if (ccs->fdt_depth =3D=3D 0) { + drc->ccs_depth--; + if (drc->ccs_depth =3D=3D 0) { uint32_t drc_index =3D spapr_drc_index(drc); =20 /* done sending the device tree, move to configured state = */ trace_spapr_drc_set_configured(drc_index); drc->state =3D drck->ready_state; - g_free(ccs); - drc->ccs =3D NULL; - ccs =3D NULL; + drc->ccs_offset =3D -1; + drc->ccs_depth =3D -1; resp =3D SPAPR_DR_CC_RESPONSE_SUCCESS; } else { resp =3D SPAPR_DR_CC_RESPONSE_PREV_PARENT; } break; case FDT_PROP: - prop =3D fdt_get_property_by_offset(drc->fdt, ccs->fdt_offset, + prop =3D fdt_get_property_by_offset(drc->fdt, drc->ccs_offset, &prop_len); name =3D fdt_string(drc->fdt, fdt32_to_cpu(prop->nameoff)); =20 @@ -1103,8 +1083,8 @@ static void rtas_ibm_configure_connector(PowerPCCPU *= cpu, /* keep seeking for an actionable tag */ break; } - if (ccs) { - ccs->fdt_offset =3D fdt_offset_next; + if (drc->ccs_offset >=3D 0) { + drc->ccs_offset =3D fdt_offset_next; } } while (resp =3D=3D SPAPR_DR_CC_RESPONSE_CONTINUE); =20 diff --git a/include/hw/ppc/spapr_drc.h b/include/hw/ppc/spapr_drc.h index 4ceaaf0eff..9d4fd41d22 100644 --- a/include/hw/ppc/spapr_drc.h +++ b/include/hw/ppc/spapr_drc.h @@ -191,12 +191,6 @@ typedef enum { SPAPR_DRC_STATE_PHYSICAL_CONFIGURED =3D 8, } sPAPRDRCState; =20 -/* rtas-configure-connector state */ -typedef struct sPAPRConfigureConnectorState { - int fdt_offset; - int fdt_depth; -} sPAPRConfigureConnectorState; - typedef struct sPAPRDRConnector { /*< private >*/ DeviceState parent; @@ -209,14 +203,16 @@ typedef struct sPAPRDRConnector { =20 uint32_t state; =20 - /* configure-connector state */ - void *fdt; - int fdt_start_offset; - sPAPRConfigureConnectorState *ccs; + /* RTAS ibm,configure-connector state */ + /* (only valid in UNISOLATE state) */ + int ccs_offset; + int ccs_depth; =20 /* device pointer, via link property */ DeviceState *dev; bool unplug_requested; + void *fdt; + int fdt_start_offset; } sPAPRDRConnector; =20 typedef struct sPAPRDRConnectorClass { --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275610600395.5701950479157; Mon, 17 Jul 2017 00:13:30 -0700 (PDT) Received: from localhost ([::1]:48373 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX0Dh-0007s7-9j for importer@patchew.org; Mon, 17 Jul 2017 03:13:29 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40676) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxO-0002e0-98 for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:40 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxL-0001c2-U9 for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:38 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:42637) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxL-0001Zh-Gx; Mon, 17 Jul 2017 02:56:35 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM5zyWz9t3M; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=uA00U84KYYJFHVEcnReBdtGKGD8yc6y7r9PinCrnp08=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=Vht3Yg+oKlZljXvAt4IwJG8R9Y7Jmd3RLj11ptghVqJHResklgLuZWobTsdGUo1Qa B8faTyAos0qhcwz7SgKJrTPq5OgtljJ74byi0XYZ7P1Kb3sLjsvhhGCgrUXVMiR83o kBW705r2obG9IPj3lIhXss+5rY7WUauvmSzggLns= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:12 +1000 Message-Id: <20170717065621.4688-13-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 12/21] spapr: Implement DR-indicator for physical DRCs only X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" According to PAPR, the DR-indicator should only be valid for physical DRCs, not logical DRCs. At the moment we implement it for all DRCs, so restrict it to physical ones only. We move the state to the physical DRC subclass, which means adding some QOM boilerplate to handle the newly distinct type. Signed-off-by: David Gibson Reviewed-by: Daniel Barboza Tested-by: Daniel Barboza --- hw/ppc/spapr_drc.c | 67 ++++++++++++++++++++++++++++++++++++++++++= +--- include/hw/ppc/spapr_drc.h | 13 ++++++--- 2 files changed, 72 insertions(+), 8 deletions(-) diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 11b9fa534b..0ffcec6fb2 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -478,7 +478,6 @@ static const VMStateDescription vmstate_spapr_drc =3D { .needed =3D spapr_drc_needed, .fields =3D (VMStateField []) { VMSTATE_UINT32(state, sPAPRDRConnector), - VMSTATE_UINT32(dr_indicator, sPAPRDRConnector), VMSTATE_END_OF_LIST() } }; @@ -575,10 +574,63 @@ static void spapr_dr_connector_class_init(ObjectClass= *k, void *data) dk->user_creatable =3D false; } =20 +static bool drc_physical_needed(void *opaque) +{ + sPAPRDRCPhysical *drcp =3D (sPAPRDRCPhysical *)opaque; + sPAPRDRConnector *drc =3D SPAPR_DR_CONNECTOR(drcp); + + if ((drc->dev && (drcp->dr_indicator =3D=3D SPAPR_DR_INDICATOR_ACTIVE)) + || (!drc->dev && (drcp->dr_indicator =3D=3D SPAPR_DR_INDICATOR_INA= CTIVE))) { + return false; + } + return true; +} + +static const VMStateDescription vmstate_spapr_drc_physical =3D { + .name =3D "spapr_drc/physical", + .version_id =3D 1, + .minimum_version_id =3D 1, + .needed =3D drc_physical_needed, + .fields =3D (VMStateField []) { + VMSTATE_UINT32(dr_indicator, sPAPRDRCPhysical), + VMSTATE_END_OF_LIST() + } +}; + +static void drc_physical_reset(void *opaque) +{ + sPAPRDRConnector *drc =3D SPAPR_DR_CONNECTOR(opaque); + sPAPRDRCPhysical *drcp =3D SPAPR_DRC_PHYSICAL(drc); + + if (drc->dev) { + drcp->dr_indicator =3D SPAPR_DR_INDICATOR_ACTIVE; + } else { + drcp->dr_indicator =3D SPAPR_DR_INDICATOR_INACTIVE; + } +} + +static void realize_physical(DeviceState *d, Error **errp) +{ + sPAPRDRCPhysical *drcp =3D SPAPR_DRC_PHYSICAL(d); + Error *local_err =3D NULL; + + realize(d, &local_err); + if (local_err) { + error_propagate(errp, local_err); + return; + } + + vmstate_register(DEVICE(drcp), spapr_drc_index(SPAPR_DR_CONNECTOR(drcp= )), + &vmstate_spapr_drc_physical, drcp); + qemu_register_reset(drc_physical_reset, drcp); +} + static void spapr_drc_physical_class_init(ObjectClass *k, void *data) { + DeviceClass *dk =3D DEVICE_CLASS(k); sPAPRDRConnectorClass *drck =3D SPAPR_DR_CONNECTOR_CLASS(k); =20 + dk->realize =3D realize_physical; drck->dr_entity_sense =3D physical_entity_sense; drck->isolate =3D drc_isolate_physical; drck->unisolate =3D drc_unisolate_physical; @@ -640,6 +692,7 @@ static const TypeInfo spapr_dr_connector_info =3D { static const TypeInfo spapr_drc_physical_info =3D { .name =3D TYPE_SPAPR_DRC_PHYSICAL, .parent =3D TYPE_SPAPR_DR_CONNECTOR, + .instance_size =3D sizeof(sPAPRDRCPhysical), .class_init =3D spapr_drc_physical_class_init, .abstract =3D true, }; @@ -878,12 +931,18 @@ static uint32_t rtas_set_dr_indicator(uint32_t idx, u= int32_t state) { sPAPRDRConnector *drc =3D spapr_drc_by_index(idx); =20 - if (!drc) { - return RTAS_OUT_PARAM_ERROR; + if (!drc || !object_dynamic_cast(OBJECT(drc), TYPE_SPAPR_DRC_PHYSICAL)= ) { + return RTAS_OUT_NO_SUCH_INDICATOR; + } + if ((state !=3D SPAPR_DR_INDICATOR_INACTIVE) + && (state !=3D SPAPR_DR_INDICATOR_ACTIVE) + && (state !=3D SPAPR_DR_INDICATOR_IDENTIFY) + && (state !=3D SPAPR_DR_INDICATOR_ACTION)) { + return RTAS_OUT_PARAM_ERROR; /* bad state parameter */ } =20 trace_spapr_drc_set_dr_indicator(idx, state); - drc->dr_indicator =3D state; + SPAPR_DRC_PHYSICAL(drc)->dr_indicator =3D state; return RTAS_OUT_SUCCESS; } =20 diff --git a/include/hw/ppc/spapr_drc.h b/include/hw/ppc/spapr_drc.h index 9d4fd41d22..a7958d0a8d 100644 --- a/include/hw/ppc/spapr_drc.h +++ b/include/hw/ppc/spapr_drc.h @@ -33,7 +33,7 @@ #define SPAPR_DRC_PHYSICAL_CLASS(klass) \ OBJECT_CLASS_CHECK(sPAPRDRConnectorClass, klass, \ TYPE_SPAPR_DRC_PHYSICAL) -#define SPAPR_DRC_PHYSICAL(obj) OBJECT_CHECK(sPAPRDRConnector, (obj), \ +#define SPAPR_DRC_PHYSICAL(obj) OBJECT_CHECK(sPAPRDRCPhysical, (obj), \ TYPE_SPAPR_DRC_PHYSICAL) =20 #define TYPE_SPAPR_DRC_LOGICAL "spapr-drc-logical" @@ -198,9 +198,6 @@ typedef struct sPAPRDRConnector { uint32_t id; Object *owner; =20 - /* DR-indicator */ - uint32_t dr_indicator; - uint32_t state; =20 /* RTAS ibm,configure-connector state */ @@ -232,6 +229,14 @@ typedef struct sPAPRDRConnectorClass { void (*release)(DeviceState *dev); } sPAPRDRConnectorClass; =20 +typedef struct sPAPRDRCPhysical { + /*< private >*/ + sPAPRDRConnector parent; + + /* DR-indicator */ + uint32_t dr_indicator; +} sPAPRDRCPhysical; + static inline bool spapr_drc_hotplugged(DeviceState *dev) { return dev->hotplugged && !runstate_check(RUN_STATE_INMIGRATE); --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275421299735.4523927721109; Mon, 17 Jul 2017 00:10:21 -0700 (PDT) Received: from localhost ([::1]:48355 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX0Ad-0005k3-0Z for importer@patchew.org; Mon, 17 Jul 2017 03:10:19 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40648) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxN-0002dE-Ij for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:39 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxM-0001cd-4f for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:37 -0400 Received: from ozlabs.org ([103.22.144.67]:43629) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxL-0001Zu-MD; Mon, 17 Jul 2017 02:56:35 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM6Wmnz9t39; Mon, 17 Jul 2017 16:56:26 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=lPpSP5dFtaFBIN3HuLvJqEvoBy3CsooadwPocxnMD7Q=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=SNfJJ/5jScKyZE/hxYOe4eKtZBl85XwsxnfhgiYNIRXiWFlIrrIe+V263siybzJjG 9BEYII9H7yE2cdntOmTwceDD6QRAp82J5ptaB7Z0g8qwBsctovvhH3Au56FgiM8JcR mSvqqM5x8LCOJ1RB41it2K/83YaIoov/yKZCTFz0= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:13 +1000 Message-Id: <20170717065621.4688-14-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 13/21] spapr: fix potential memory leak in spapr_core_plug() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" From: Greg Kurz Since commit 5c1da81215c7 ("spapr: Remove unnecessary differences between hotplug and coldplug paths"), the CPU DT for the DRC is always allocated. This causes a memory leak for pseries-2.6 and older machine types, that don't support CPU hotplug and don't allocate DRCs for CPUs. Reported-by: Bharata B Rao Signed-off-by: Greg Kurz Signed-off-by: David Gibson --- hw/ppc/spapr.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 16d450f21c..a58dd54392 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -2974,8 +2974,6 @@ static void spapr_core_plug(HotplugHandler *hotplug_d= ev, DeviceState *dev, CPUState *cs =3D CPU(core->threads); sPAPRDRConnector *drc; Error *local_err =3D NULL; - void *fdt =3D NULL; - int fdt_offset =3D 0; int smt =3D kvmppc_smt_threads(); CPUArchId *core_slot; int index; @@ -2991,9 +2989,12 @@ static void spapr_core_plug(HotplugHandler *hotplug_= dev, DeviceState *dev, =20 g_assert(drc || !mc->has_hotpluggable_cpus); =20 - fdt =3D spapr_populate_hotplug_cpu_dt(cs, &fdt_offset, spapr); - if (drc) { + void *fdt; + int fdt_offset; + + fdt =3D spapr_populate_hotplug_cpu_dt(cs, &fdt_offset, spapr); + spapr_drc_attach(drc, dev, fdt, fdt_offset, &local_err); if (local_err) { g_free(fdt); --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275518845375.1563274277737; Mon, 17 Jul 2017 00:11:58 -0700 (PDT) Received: from localhost ([::1]:48363 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX0CA-0006r4-Mj for importer@patchew.org; Mon, 17 Jul 2017 03:11:54 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40663) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxO-0002do-45 for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:39 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxM-0001cU-3D for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:38 -0400 Received: from ozlabs.org ([103.22.144.67]:48743) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxL-0001Zy-Kt; Mon, 17 Jul 2017 02:56:35 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGN36SFz9t33; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274588; bh=VT8MVBlelmPYoXNhAXaUT8/o1Qr6EvhjcyB/1aVd74s=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=eKFgCTY7MCEieloGXgkBU4XLGJYzEKnmoLLz1lxOgceqpRCTVIfLWInMPPHfYOiGF /H/jEUzjBj3V7C0IGZ4kd1a4MYL6NAk49RbXaxEmCE0vhERVrUEUpp8XlwsrcENskp YspotlhKDVyCEPnHvIP8RL73PnR4azufp/R70uCc= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:14 +1000 Message-Id: <20170717065621.4688-15-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 14/21] ppc/pnv: Remove unused XICSState reference X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" From: Alexey Kardashevskiy e6f7e110ee70 "ppc/xics: remove the XICSState classes" got rid of XICSState, this is just an leftover. Signed-off-by: Alexey Kardashevskiy Reviewed-by: C=C3=A9dric Le Goater Signed-off-by: David Gibson --- include/hw/ppc/pnv_psi.h | 2 -- 1 file changed, 2 deletions(-) diff --git a/include/hw/ppc/pnv_psi.h b/include/hw/ppc/pnv_psi.h index 11d83e43f8..f6af5eae1f 100644 --- a/include/hw/ppc/pnv_psi.h +++ b/include/hw/ppc/pnv_psi.h @@ -28,8 +28,6 @@ =20 #define PSIHB_XSCOM_MAX 0x20 =20 -typedef struct XICSState XICSState; - typedef struct PnvPsi { SysBusDevice parent; =20 --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275470265934.3074641749763; Mon, 17 Jul 2017 00:11:10 -0700 (PDT) Received: from localhost ([::1]:48361 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX0BQ-0006MU-Nr for importer@patchew.org; Mon, 17 Jul 2017 03:11:08 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40773) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxQ-0002gh-Ct for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:43 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxM-0001dD-Jw for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:40 -0400 Received: from ozlabs.org ([103.22.144.67]:45175) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxL-0001aI-S3; Mon, 17 Jul 2017 02:56:36 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGN4SYsz9t3Q; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274588; bh=RCPXxjjEzVRaIVowiyXO6GzAm89z+KNswu+VviQw07Q=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=gLu4SItywNsSd2+w0FxZPxRy/snTMtQ6jjOprnrWYIav8dFAAQvqYLOPrkngUNGEN IWzPvFzjJRA9iqM6WAzngpcLVRRT3cCsD14JDG5aX2h6F+Y4HfK95AVonT0tSp83yj qRBsM8RBeYha7Pv0odmwQ/W836NP0rDOkyi88GyQ= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:15 +1000 Message-Id: <20170717065621.4688-16-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 15/21] pseries: Stubs for HPT resizing X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" This introduces stub implementations of the H_RESIZE_HPT_PREPARE and H_RESIZE_HPT_COMMIT hypercalls which we hope to add in a PAPR extension to allow run time resizing of a guest's hash page table. It also adds a new machine property for controlling whether this new facility is available. For now we only allow resizing with TCG, allowing it with KVM will require kernel changes as well. Finally, it adds a new string to the hypertas property in the device tree, advertising to the guest the availability of the HPT resizing hypercalls. This is a tentative suggested value, and would need to be standardized by PAPR before being merged. Signed-off-by: David Gibson Reviewed-by: Suraj Jitindar Singh Reviewed-by: Laurent Vivier --- hw/ppc/spapr.c | 75 ++++++++++++++++++++++++++++++++++++++++++++++= ++++ hw/ppc/spapr_hcall.c | 36 ++++++++++++++++++++++++ hw/ppc/trace-events | 2 ++ include/hw/ppc/spapr.h | 11 ++++++++ target/ppc/kvm.c | 13 +++++++++ target/ppc/kvm_ppc.h | 5 ++++ 6 files changed, 142 insertions(+) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index a58dd54392..232afac3d9 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -874,6 +874,11 @@ static void spapr_dt_rtas(sPAPRMachineState *spapr, vo= id *fdt) if (!kvm_enabled() || kvmppc_spapr_use_multitce()) { add_str(hypertas, "hcall-multi-tce"); } + + if (spapr->resize_hpt !=3D SPAPR_RESIZE_HPT_DISABLED) { + add_str(hypertas, "hcall-hpt-resize"); + } + _FDT(fdt_setprop(fdt, rtas, "ibm,hypertas-functions", hypertas->str, hypertas->len)); g_string_free(hypertas, TRUE); @@ -2148,12 +2153,41 @@ static void ppc_spapr_init(MachineState *machine) hwaddr node0_size =3D spapr_node0_size(); long load_limit, fw_size; char *filename; + Error *resize_hpt_err =3D NULL; =20 msi_nonbroken =3D true; =20 QLIST_INIT(&spapr->phbs); QTAILQ_INIT(&spapr->pending_dimm_unplugs); =20 + /* Check HPT resizing availability */ + kvmppc_check_papr_resize_hpt(&resize_hpt_err); + if (spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_DEFAULT) { + /* + * If the user explicitly requested a mode we should either + * supply it, or fail completely (which we do below). But if + * it's not set explicitly, we reset our mode to something + * that works + */ + if (resize_hpt_err) { + spapr->resize_hpt =3D SPAPR_RESIZE_HPT_DISABLED; + error_free(resize_hpt_err); + resize_hpt_err =3D NULL; + } else { + spapr->resize_hpt =3D smc->resize_hpt_default; + } + } + + assert(spapr->resize_hpt !=3D SPAPR_RESIZE_HPT_DEFAULT); + + if ((spapr->resize_hpt !=3D SPAPR_RESIZE_HPT_DISABLED) && resize_hpt_e= rr) { + /* + * User requested HPT resize, but this host can't supply it. Bail= out + */ + error_report_err(resize_hpt_err); + exit(1); + } + /* Allocate RMA if necessary */ rma_alloc_size =3D kvmppc_alloc_rma(&rma); =20 @@ -2579,6 +2613,40 @@ static void spapr_set_modern_hotplug_events(Object *= obj, bool value, spapr->use_hotplug_event_source =3D value; } =20 +static char *spapr_get_resize_hpt(Object *obj, Error **errp) +{ + sPAPRMachineState *spapr =3D SPAPR_MACHINE(obj); + + switch (spapr->resize_hpt) { + case SPAPR_RESIZE_HPT_DEFAULT: + return g_strdup("default"); + case SPAPR_RESIZE_HPT_DISABLED: + return g_strdup("disabled"); + case SPAPR_RESIZE_HPT_ENABLED: + return g_strdup("enabled"); + case SPAPR_RESIZE_HPT_REQUIRED: + return g_strdup("required"); + } + g_assert_not_reached(); +} + +static void spapr_set_resize_hpt(Object *obj, const char *value, Error **e= rrp) +{ + sPAPRMachineState *spapr =3D SPAPR_MACHINE(obj); + + if (strcmp(value, "default") =3D=3D 0) { + spapr->resize_hpt =3D SPAPR_RESIZE_HPT_DEFAULT; + } else if (strcmp(value, "disabled") =3D=3D 0) { + spapr->resize_hpt =3D SPAPR_RESIZE_HPT_DISABLED; + } else if (strcmp(value, "enabled") =3D=3D 0) { + spapr->resize_hpt =3D SPAPR_RESIZE_HPT_ENABLED; + } else if (strcmp(value, "required") =3D=3D 0) { + spapr->resize_hpt =3D SPAPR_RESIZE_HPT_REQUIRED; + } else { + error_setg(errp, "Bad value for \"resize-hpt\" property"); + } +} + static void spapr_machine_initfn(Object *obj) { sPAPRMachineState *spapr =3D SPAPR_MACHINE(obj); @@ -2603,6 +2671,12 @@ static void spapr_machine_initfn(Object *obj) ppc_compat_add_property(obj, "max-cpu-compat", &spapr->max_compat_pvr, "Maximum permitted CPU compatibility mode", &error_fatal); + + object_property_add_str(obj, "resize-hpt", + spapr_get_resize_hpt, spapr_set_resize_hpt, NU= LL); + object_property_set_description(obj, "resize-hpt", + "Resizing of the Hash Page Table (enab= led, disabled, required)", + NULL); } =20 static void spapr_machine_finalizefn(Object *obj) @@ -3361,6 +3435,7 @@ static void spapr_machine_class_init(ObjectClass *oc,= void *data) smc->dr_lmb_enabled =3D true; smc->tcg_default_cpu =3D "POWER8"; mc->has_hotpluggable_cpus =3D true; + smc->resize_hpt_default =3D SPAPR_RESIZE_HPT_DISABLED; fwc->get_dev_path =3D spapr_get_fw_dev_path; nc->nmi_monitor_handler =3D spapr_nmi; smc->phb_placement =3D spapr_phb_placement; diff --git a/hw/ppc/spapr_hcall.c b/hw/ppc/spapr_hcall.c index 8624ce8d5b..6ea8fa7394 100644 --- a/hw/ppc/spapr_hcall.c +++ b/hw/ppc/spapr_hcall.c @@ -354,6 +354,38 @@ static target_ulong h_read(PowerPCCPU *cpu, sPAPRMachi= neState *spapr, return H_SUCCESS; } =20 +static target_ulong h_resize_hpt_prepare(PowerPCCPU *cpu, + sPAPRMachineState *spapr, + target_ulong opcode, + target_ulong *args) +{ + target_ulong flags =3D args[0]; + target_ulong shift =3D args[1]; + + if (spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_DISABLED) { + return H_AUTHORITY; + } + + trace_spapr_h_resize_hpt_prepare(flags, shift); + return H_HARDWARE; +} + +static target_ulong h_resize_hpt_commit(PowerPCCPU *cpu, + sPAPRMachineState *spapr, + target_ulong opcode, + target_ulong *args) +{ + target_ulong flags =3D args[0]; + target_ulong shift =3D args[1]; + + if (spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_DISABLED) { + return H_AUTHORITY; + } + + trace_spapr_h_resize_hpt_commit(flags, shift); + return H_HARDWARE; +} + static target_ulong h_set_sprg0(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { @@ -1246,6 +1278,10 @@ static void hypercall_register_types(void) /* hcall-bulk */ spapr_register_hypercall(H_BULK_REMOVE, h_bulk_remove); =20 + /* hcall-hpt-resize */ + spapr_register_hypercall(H_RESIZE_HPT_PREPARE, h_resize_hpt_prepare); + spapr_register_hypercall(H_RESIZE_HPT_COMMIT, h_resize_hpt_commit); + /* hcall-splpar */ spapr_register_hypercall(H_REGISTER_VPA, h_register_vpa); spapr_register_hypercall(H_CEDE, h_cede); diff --git a/hw/ppc/trace-events b/hw/ppc/trace-events index 8e79f7eaf6..0f7d9be4ef 100644 --- a/hw/ppc/trace-events +++ b/hw/ppc/trace-events @@ -16,6 +16,8 @@ spapr_cas_continue(unsigned long n) "Copy changes to the = guest: %ld bytes" # hw/ppc/spapr_hcall.c spapr_cas_pvr_try(uint32_t pvr) "%x" spapr_cas_pvr(uint32_t cur_pvr, bool explicit_match, uint32_t new_pvr) "cu= rrent=3D%x, explicit_match=3D%u, new=3D%x" +spapr_h_resize_hpt_prepare(uint64_t flags, uint64_t shift) "flags=3D0x%"PR= Ix64", shift=3D%"PRIu64 +spapr_h_resize_hpt_commit(uint64_t flags, uint64_t shift) "flags=3D0x%"PRI= x64", shift=3D%"PRIu64 =20 # hw/ppc/spapr_iommu.c spapr_iommu_put(uint64_t liobn, uint64_t ioba, uint64_t tce, uint64_t ret)= "liobn=3D%"PRIx64" ioba=3D0x%"PRIx64" tce=3D0x%"PRIx64" ret=3D%"PRId64 diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 2ddec025d2..10ddb90711 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -42,6 +42,13 @@ typedef struct sPAPRMachineClass sPAPRMachineClass; #define SPAPR_MACHINE_CLASS(klass) \ OBJECT_CLASS_CHECK(sPAPRMachineClass, klass, TYPE_SPAPR_MACHINE) =20 +typedef enum { + SPAPR_RESIZE_HPT_DEFAULT =3D 0, + SPAPR_RESIZE_HPT_DISABLED, + SPAPR_RESIZE_HPT_ENABLED, + SPAPR_RESIZE_HPT_REQUIRED, +} sPAPRResizeHPT; + /** * sPAPRMachineClass: */ @@ -58,6 +65,7 @@ struct sPAPRMachineClass { uint64_t *buid, hwaddr *pio,=20 hwaddr *mmio32, hwaddr *mmio64, unsigned n_dma, uint32_t *liobns, Error **errp); + sPAPRResizeHPT resize_hpt_default; }; =20 /** @@ -73,6 +81,7 @@ struct sPAPRMachineState { ICSState *ics; sPAPRRTCState rtc; =20 + sPAPRResizeHPT resize_hpt; void *htab; uint32_t htab_shift; uint64_t patb_entry; /* Process tbl registed in H_REGISTER_PROCESS_TAB= LE */ @@ -367,6 +376,8 @@ struct sPAPRMachineState { #define H_XIRR_X 0x2FC #define H_RANDOM 0x300 #define H_SET_MODE 0x31C +#define H_RESIZE_HPT_PREPARE 0x36C +#define H_RESIZE_HPT_COMMIT 0x370 #define H_CLEAN_SLB 0x374 #define H_INVALIDATE_PID 0x378 #define H_REGISTER_PROC_TBL 0x37C diff --git a/target/ppc/kvm.c b/target/ppc/kvm.c index f7a7ea5858..8bafd1e932 100644 --- a/target/ppc/kvm.c +++ b/target/ppc/kvm.c @@ -22,6 +22,7 @@ #include =20 #include "qemu-common.h" +#include "qapi/error.h" #include "qemu/error-report.h" #include "cpu.h" #include "cpu-models.h" @@ -2709,3 +2710,15 @@ int kvmppc_enable_hwrng(void) =20 return kvmppc_enable_hcall(kvm_state, H_RANDOM); } + +void kvmppc_check_papr_resize_hpt(Error **errp) +{ + if (!kvm_enabled()) { + return; + } + + /* TODO: Check for resize-capable KVM implementations */ + + error_setg(errp, + "Hash page table resizing not available with this KVM versi= on"); +} diff --git a/target/ppc/kvm_ppc.h b/target/ppc/kvm_ppc.h index eab7c8fdb3..9be706c5c9 100644 --- a/target/ppc/kvm_ppc.h +++ b/target/ppc/kvm_ppc.h @@ -63,6 +63,7 @@ bool kvmppc_has_cap_mmu_hash_v3(void); int kvmppc_enable_hwrng(void); int kvmppc_put_books_sregs(PowerPCCPU *cpu); PowerPCCPUClass *kvm_ppc_get_host_cpu_class(void); +void kvmppc_check_papr_resize_hpt(Error **errp); =20 bool kvmppc_is_mem_backend_page_size_ok(const char *obj_path); =20 @@ -297,6 +298,10 @@ static inline PowerPCCPUClass *kvm_ppc_get_host_cpu_cl= ass(void) return NULL; } =20 +static inline void kvmppc_check_papr_resize_hpt(Error **errp) +{ + return; +} #endif =20 #ifndef CONFIG_KVM --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275105401929.1796156741495; Mon, 17 Jul 2017 00:05:05 -0700 (PDT) Received: from localhost ([::1]:48323 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX05W-0001OV-Ip for importer@patchew.org; Mon, 17 Jul 2017 03:05:02 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40763) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxQ-0002gR-46 for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:43 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxL-0001bX-La for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:40 -0400 Received: from ozlabs.org ([103.22.144.67]:52931) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxK-0001Z7-VF; Mon, 17 Jul 2017 02:56:35 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM5WC5z9t3R; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=hdyZmPkOhQ2esSDkqKhBQdam+S4TNM8SSDCJSrEmPss=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=ja3eXSonRpsGM6Ra8012Y7sIyJML/t2Egkg9Lwmxel1IbXBwDvJ0mZWKJ3GJ3TszB G1yWbriTT7cUJOZzbTLjLd5e2Y/o2Kk4cFhLr5zMQgoDD890c2dNbjATFNRKy4YZOq jCf8GErY6R0syxc9IDJ3F9NFdJeu0ZOm+Bcp6mp8= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:16 +1000 Message-Id: <20170717065621.4688-17-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 16/21] pseries: Implement HPT resizing X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" This patch implements hypercalls allowing a PAPR guest to resize its own hash page table. This will eventually allow for more flexible memory hotplug. The implementation is partially asynchronous, handled in a special thread running the hpt_prepare_thread() function. The state of a pending resize is stored in SPAPR_MACHINE->pending_hpt. The H_RESIZE_HPT_PREPARE hypercall will kick off creation of a new HPT, or, if one is already in progress, monitor it for completion. If there is an existing HPT resize in progress that doesn't match the size specified in the call, it will cancel it, replacing it with a new one matching the given size. The H_RESIZE_HPT_COMMIT completes transition to a resized HPT, and can only be called successfully once H_RESIZE_HPT_PREPARE has successfully completed initialization of a new HPT. The guest must ensure that there are no concurrent accesses to the existing HPT while this is called (this effectively means stop_machine() for Linux guests). For now H_RESIZE_HPT_COMMIT goes through the whole old HPT, rehashing each HPTE into the new HPT. This can have quite high latency, but it seems to be of the order of typical migration downtime latencies for HPTs of size up to ~2GiB (which would be used in a 256GiB guest). In future we probably want to move more of the rehashing to the "prepare" phase, by having H_ENTER and other hcalls update both current and pending HPTs. That's a project for another day, but should be possible without any changes to the guest interface. Signed-off-by: David Gibson --- hw/ppc/spapr.c | 4 +- hw/ppc/spapr_hcall.c | 314 ++++++++++++++++++++++++++++++++++++++++++++= +++- include/hw/ppc/spapr.h | 6 + target/ppc/mmu-hash64.h | 4 + 4 files changed, 322 insertions(+), 6 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 232afac3d9..c0bc935c59 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -98,8 +98,6 @@ =20 #define PHANDLE_XICP 0x00001111 =20 -#define HTAB_SIZE(spapr) (1ULL << ((spapr)->htab_shift)) - static ICSState *spapr_ics_create(sPAPRMachineState *spapr, const char *type_ics, int nr_irqs, Error **errp) @@ -1269,7 +1267,7 @@ static void spapr_store_hpte(PPCVirtualHypervisor *vh= yp, hwaddr ptex, } } =20 -static int spapr_hpt_shift_for_ramsize(uint64_t ramsize) +int spapr_hpt_shift_for_ramsize(uint64_t ramsize) { int shift; =20 diff --git a/hw/ppc/spapr_hcall.c b/hw/ppc/spapr_hcall.c index 6ea8fa7394..f69ce4f60c 100644 --- a/hw/ppc/spapr_hcall.c +++ b/hw/ppc/spapr_hcall.c @@ -3,6 +3,7 @@ #include "sysemu/hw_accel.h" #include "sysemu/sysemu.h" #include "qemu/log.h" +#include "qemu/error-report.h" #include "cpu.h" #include "exec/exec-all.h" #include "helper_regs.h" @@ -354,20 +355,291 @@ static target_ulong h_read(PowerPCCPU *cpu, sPAPRMac= hineState *spapr, return H_SUCCESS; } =20 +struct sPAPRPendingHPT { + /* These fields are read-only after initialization */ + int shift; + QemuThread thread; + + /* These fields are protected by the BQL */ + bool complete; + + /* These fields are private to the preparation thread if + * !complete, otherwise protected by the BQL */ + int ret; + void *hpt; +}; + +static void free_pending_hpt(sPAPRPendingHPT *pending) +{ + if (pending->hpt) { + qemu_vfree(pending->hpt); + } + + g_free(pending); +} + +static void *hpt_prepare_thread(void *opaque) +{ + sPAPRPendingHPT *pending =3D opaque; + size_t size =3D 1ULL << pending->shift; + + pending->hpt =3D qemu_memalign(size, size); + if (pending->hpt) { + memset(pending->hpt, 0, size); + pending->ret =3D H_SUCCESS; + } else { + pending->ret =3D H_NO_MEM; + } + + qemu_mutex_lock_iothread(); + + if (SPAPR_MACHINE(qdev_get_machine())->pending_hpt =3D=3D pending) { + /* Ready to go */ + pending->complete =3D true; + } else { + /* We've been cancelled, clean ourselves up */ + free_pending_hpt(pending); + } + + qemu_mutex_unlock_iothread(); + return NULL; +} + +/* Must be called with BQL held */ +static void cancel_hpt_prepare(sPAPRMachineState *spapr) +{ + sPAPRPendingHPT *pending =3D spapr->pending_hpt; + + /* Let the thread know it's cancelled */ + spapr->pending_hpt =3D NULL; + + if (!pending) { + /* Nothing to do */ + return; + } + + if (!pending->complete) { + /* thread will clean itself up */ + return; + } + + free_pending_hpt(pending); +} + static target_ulong h_resize_hpt_prepare(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { target_ulong flags =3D args[0]; - target_ulong shift =3D args[1]; + int shift =3D args[1]; + sPAPRPendingHPT *pending =3D spapr->pending_hpt; + uint64_t current_ram_size =3D MACHINE(spapr)->ram_size; =20 if (spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_DISABLED) { return H_AUTHORITY; } =20 + if (!spapr->htab_shift) { + /* Radix guest, no HPT */ + return H_NOT_AVAILABLE; + } + trace_spapr_h_resize_hpt_prepare(flags, shift); - return H_HARDWARE; + + if (flags !=3D 0) { + return H_PARAMETER; + } + + if (shift && ((shift < 18) || (shift > 46))) { + return H_PARAMETER; + } + + current_ram_size =3D pc_existing_dimms_capacity(&error_fatal); + + /* We only allow the guest to allocate an HPT one order above what + * we'd normally give them (to stop a small guest claiming a huge + * chunk of resources in the HPT */ + if (shift > (spapr_hpt_shift_for_ramsize(current_ram_size) + 1)) { + return H_RESOURCE; + } + + if (pending) { + /* something already in progress */ + if (pending->shift =3D=3D shift) { + /* and it's suitable */ + if (pending->complete) { + return pending->ret; + } else { + return H_LONG_BUSY_ORDER_100_MSEC; + } + } + + /* not suitable, cancel and replace */ + cancel_hpt_prepare(spapr); + } + + if (!shift) { + /* nothing to do */ + return H_SUCCESS; + } + + /* start new prepare */ + + pending =3D g_new0(sPAPRPendingHPT, 1); + pending->shift =3D shift; + pending->ret =3D H_HARDWARE; + + qemu_thread_create(&pending->thread, "sPAPR HPT prepare", + hpt_prepare_thread, pending, QEMU_THREAD_DETACHED); + + spapr->pending_hpt =3D pending; + + /* In theory we could estimate the time more accurately based on + * the new size, but there's not much point */ + return H_LONG_BUSY_ORDER_100_MSEC; +} + +static uint64_t new_hpte_load0(void *htab, uint64_t pteg, int slot) +{ + uint8_t *addr =3D htab; + + addr +=3D pteg * HASH_PTEG_SIZE_64; + addr +=3D slot * HASH_PTE_SIZE_64; + return ldq_p(addr); +} + +static void new_hpte_store(void *htab, uint64_t pteg, int slot, + uint64_t pte0, uint64_t pte1) +{ + uint8_t *addr =3D htab; + + addr +=3D pteg * HASH_PTEG_SIZE_64; + addr +=3D slot * HASH_PTE_SIZE_64; + + stq_p(addr, pte0); + stq_p(addr + HASH_PTE_SIZE_64 / 2, pte1); +} + +static int rehash_hpte(PowerPCCPU *cpu, + const ppc_hash_pte64_t *hptes, + void *old_hpt, uint64_t oldsize, + void *new_hpt, uint64_t newsize, + uint64_t pteg, int slot) +{ + uint64_t old_hash_mask =3D (oldsize >> 7) - 1; + uint64_t new_hash_mask =3D (newsize >> 7) - 1; + target_ulong pte0 =3D ppc_hash64_hpte0(cpu, hptes, slot); + target_ulong pte1; + uint64_t avpn; + unsigned base_pg_shift; + uint64_t hash, new_pteg, replace_pte0; + + if (!(pte0 & HPTE64_V_VALID) || !(pte0 & HPTE64_V_BOLTED)) { + return H_SUCCESS; + } + + pte1 =3D ppc_hash64_hpte1(cpu, hptes, slot); + + base_pg_shift =3D ppc_hash64_hpte_page_shift_noslb(cpu, pte0, pte1); + assert(base_pg_shift); /* H_ENTER shouldn't allow a bad encoding */ + avpn =3D HPTE64_V_AVPN_VAL(pte0) & ~(((1ULL << base_pg_shift) - 1) >> = 23); + + if (pte0 & HPTE64_V_SECONDARY) { + pteg =3D ~pteg; + } + + if ((pte0 & HPTE64_V_SSIZE) =3D=3D HPTE64_V_SSIZE_256M) { + uint64_t offset, vsid; + + /* We only have 28 - 23 bits of offset in avpn */ + offset =3D (avpn & 0x1f) << 23; + vsid =3D avpn >> 5; + /* We can find more bits from the pteg value */ + if (base_pg_shift < 23) { + offset |=3D ((vsid ^ pteg) & old_hash_mask) << base_pg_shift; + } + + hash =3D vsid ^ (offset >> base_pg_shift); + } else if ((pte0 & HPTE64_V_SSIZE) =3D=3D HPTE64_V_SSIZE_1T) { + uint64_t offset, vsid; + + /* We only have 40 - 23 bits of seg_off in avpn */ + offset =3D (avpn & 0x1ffff) << 23; + vsid =3D avpn >> 17; + if (base_pg_shift < 23) { + offset |=3D ((vsid ^ (vsid << 25) ^ pteg) & old_hash_mask) + << base_pg_shift; + } + + hash =3D vsid ^ (vsid << 25) ^ (offset >> base_pg_shift); + } else { + error_report("rehash_pte: Bad segment size in HPTE"); + return H_HARDWARE; + } + + new_pteg =3D hash & new_hash_mask; + if (pte0 & HPTE64_V_SECONDARY) { + assert(~pteg =3D=3D (hash & old_hash_mask)); + new_pteg =3D ~new_pteg; + } else { + assert(pteg =3D=3D (hash & old_hash_mask)); + } + assert((oldsize !=3D newsize) || (pteg =3D=3D new_pteg)); + replace_pte0 =3D new_hpte_load0(new_hpt, new_pteg, slot); + /* + * Strictly speaking, we don't need all these tests, since we only + * ever rehash bolted HPTEs. We might in future handle non-bolted + * HPTEs, though so make the logic correct for those cases as + * well. + */ + if (replace_pte0 & HPTE64_V_VALID) { + assert(newsize < oldsize); + if (replace_pte0 & HPTE64_V_BOLTED) { + if (pte0 & HPTE64_V_BOLTED) { + /* Bolted collision, nothing we can do */ + return H_PTEG_FULL; + } else { + /* Discard this hpte */ + return H_SUCCESS; + } + } + } + + new_hpte_store(new_hpt, new_pteg, slot, pte0, pte1); + return H_SUCCESS; +} + +static int rehash_hpt(PowerPCCPU *cpu, + void *old_hpt, uint64_t oldsize, + void *new_hpt, uint64_t newsize) +{ + uint64_t n_ptegs =3D oldsize >> 7; + uint64_t pteg; + int slot; + int rc; + + for (pteg =3D 0; pteg < n_ptegs; pteg++) { + hwaddr ptex =3D pteg * HPTES_PER_GROUP; + const ppc_hash_pte64_t *hptes + =3D ppc_hash64_map_hptes(cpu, ptex, HPTES_PER_GROUP); + + if (!hptes) { + return H_HARDWARE; + } + + for (slot =3D 0; slot < HPTES_PER_GROUP; slot++) { + rc =3D rehash_hpte(cpu, hptes, old_hpt, oldsize, new_hpt, news= ize, + pteg, slot); + if (rc !=3D H_SUCCESS) { + ppc_hash64_unmap_hptes(cpu, hptes, ptex, HPTES_PER_GROUP); + return rc; + } + } + ppc_hash64_unmap_hptes(cpu, hptes, ptex, HPTES_PER_GROUP); + } + + return H_SUCCESS; } =20 static target_ulong h_resize_hpt_commit(PowerPCCPU *cpu, @@ -377,13 +649,49 @@ static target_ulong h_resize_hpt_commit(PowerPCCPU *c= pu, { target_ulong flags =3D args[0]; target_ulong shift =3D args[1]; + sPAPRPendingHPT *pending =3D spapr->pending_hpt; + int rc; + size_t newsize; =20 if (spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_DISABLED) { return H_AUTHORITY; } =20 trace_spapr_h_resize_hpt_commit(flags, shift); - return H_HARDWARE; + + if (flags !=3D 0) { + return H_PARAMETER; + } + + if (!pending || (pending->shift !=3D shift)) { + /* no matching prepare */ + return H_CLOSED; + } + + if (!pending->complete) { + /* prepare has not completed */ + return H_BUSY; + } + + /* Shouldn't have got past PREPARE without an HPT */ + g_assert(spapr->htab_shift); + + newsize =3D 1ULL << pending->shift; + rc =3D rehash_hpt(cpu, spapr->htab, HTAB_SIZE(spapr), + pending->hpt, newsize); + if (rc =3D=3D H_SUCCESS) { + qemu_vfree(spapr->htab); + spapr->htab =3D pending->hpt; + spapr->htab_shift =3D pending->shift; + + pending->hpt =3D NULL; /* so it's not free()d */ + } + + /* Clean up */ + spapr->pending_hpt =3D NULL; + free_pending_hpt(pending); + + return rc; } =20 static target_ulong h_set_sprg0(PowerPCCPU *cpu, sPAPRMachineState *spapr, diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 10ddb90711..3dd62d81f6 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -13,6 +13,7 @@ struct sPAPRPHBState; struct sPAPRNVRAM; typedef struct sPAPREventLogEntry sPAPREventLogEntry; typedef struct sPAPREventSource sPAPREventSource; +typedef struct sPAPRPendingHPT sPAPRPendingHPT; =20 #define HPTE64_V_HPTE_DIRTY 0x0000000000000040ULL #define SPAPR_ENTRY_POINT 0x100 @@ -85,6 +86,8 @@ struct sPAPRMachineState { void *htab; uint32_t htab_shift; uint64_t patb_entry; /* Process tbl registed in H_REGISTER_PROCESS_TAB= LE */ + sPAPRPendingHPT *pending_hpt; /* in-progress resize */ + hwaddr rma_size; int vrma_adjust; ssize_t rtas_size; @@ -656,6 +659,7 @@ void spapr_hotplug_req_add_by_count_indexed(sPAPRDRConn= ectorType drc_type, void spapr_hotplug_req_remove_by_count_indexed(sPAPRDRConnectorType drc_ty= pe, uint32_t count, uint32_t in= dex); void spapr_cpu_parse_features(sPAPRMachineState *spapr); +int spapr_hpt_shift_for_ramsize(uint64_t ramsize); =20 /* CPU and LMB DRC release callbacks. */ void spapr_core_release(DeviceState *dev); @@ -696,4 +700,6 @@ int spapr_rng_populate_dt(void *fdt); =20 void spapr_do_system_reset_on_cpu(CPUState *cs, run_on_cpu_data arg); =20 +#define HTAB_SIZE(spapr) (1ULL << ((spapr)->htab_shift)) + #endif /* HW_SPAPR_H */ diff --git a/target/ppc/mmu-hash64.h b/target/ppc/mmu-hash64.h index 54f1e37655..d297b97d37 100644 --- a/target/ppc/mmu-hash64.h +++ b/target/ppc/mmu-hash64.h @@ -63,11 +63,15 @@ void ppc_hash64_update_rmls(CPUPPCState *env); #define HASH_PTE_SIZE_64 16 #define HASH_PTEG_SIZE_64 (HASH_PTE_SIZE_64 * HPTES_PER_GROUP) =20 +#define HPTE64_V_SSIZE SLB_VSID_B +#define HPTE64_V_SSIZE_256M SLB_VSID_B_256M +#define HPTE64_V_SSIZE_1T SLB_VSID_B_1T #define HPTE64_V_SSIZE_SHIFT 62 #define HPTE64_V_AVPN_SHIFT 7 #define HPTE64_V_AVPN 0x3fffffffffffff80ULL #define HPTE64_V_AVPN_VAL(x) (((x) & HPTE64_V_AVPN) >> HPTE64_V_AVPN_SH= IFT) #define HPTE64_V_COMPARE(x, y) (!(((x) ^ (y)) & 0xffffffffffffff83ULL)) +#define HPTE64_V_BOLTED 0x0000000000000010ULL #define HPTE64_V_LARGE 0x0000000000000004ULL #define HPTE64_V_SECONDARY 0x0000000000000002ULL #define HPTE64_V_VALID 0x0000000000000001ULL --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500274861903104.0235056365351; Mon, 17 Jul 2017 00:01:01 -0700 (PDT) Received: from localhost ([::1]:48305 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX01c-0006NA-HD for importer@patchew.org; Mon, 17 Jul 2017 03:01:00 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40655) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxN-0002dK-MU for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:38 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxM-0001cJ-1B for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:37 -0400 Received: from ozlabs.org ([103.22.144.67]:47699) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxL-0001Zw-Jb; Mon, 17 Jul 2017 02:56:35 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGN0b5sz9t3B; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274588; bh=mjax8EPFk+ojltzCawC3H/jqKNS0kP6edfu/fvdUcU8=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=Bo3+HFPOt3K5a1tIM6itjfAcUkkDjjKMSrF934XQ8AQ6aUInGb+rarKMGkZhXMKMW WmZNVPz8769Okv/3F3b47VKQ6a3R4dLNe0/i4PftM099d0wkBzKAvcpsNczAQsOQco URtKPCgzvcq+Z+bxcRWr7Lp3hC9oKIE2ysFJ5sX0= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:17 +1000 Message-Id: <20170717065621.4688-18-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 17/21] pseries: Enable HPT resizing for 2.10 X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" We've now implemented a PAPR extensions which allows PAPR guests (i.e. "pseries" machine type) to resize their hash page table during runtime. However, that extension is only enabled if explicitly chosen on the command line. This patch enables it by default for spapr-2.10, but leaves it disabled (by default) for older machine types. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier --- hw/ppc/spapr.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index c0bc935c59..3a925ef18a 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -3433,7 +3433,7 @@ static void spapr_machine_class_init(ObjectClass *oc,= void *data) smc->dr_lmb_enabled =3D true; smc->tcg_default_cpu =3D "POWER8"; mc->has_hotpluggable_cpus =3D true; - smc->resize_hpt_default =3D SPAPR_RESIZE_HPT_DISABLED; + smc->resize_hpt_default =3D SPAPR_RESIZE_HPT_ENABLED; fwc->get_dev_path =3D spapr_get_fw_dev_path; nc->nmi_monitor_handler =3D spapr_nmi; smc->phb_placement =3D spapr_phb_placement; @@ -3540,6 +3540,7 @@ static void spapr_machine_2_9_class_options(MachineCl= ass *mc) SET_MACHINE_COMPAT(mc, SPAPR_COMPAT_2_9); mc->numa_auto_assign_ram =3D numa_legacy_auto_assign_ram; smc->pre_2_10_has_unused_icps =3D true; + smc->resize_hpt_default =3D SPAPR_RESIZE_HPT_DISABLED; } =20 DEFINE_SPAPR_MACHINE(2_9, "2.9", false); --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275360381275.4382120618327; Mon, 17 Jul 2017 00:09:20 -0700 (PDT) Received: from localhost ([::1]:48350 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX09f-00055w-5h for importer@patchew.org; Mon, 17 Jul 2017 03:09:19 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40747) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxP-0002gG-Sf for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:42 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxM-0001cp-9P for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:39 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:46993) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxL-0001a5-RV; Mon, 17 Jul 2017 02:56:36 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGN3wkwz9t3D; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274588; bh=62ClrjRiq+is+mRLmTq6M49Sema0VZw5Jh2uzjj8Pd0=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=oqCnwxBbRgNbiWP4N5Ytx0DM2LeJyO/SoMuhtOXbrVDODzN+wHuer+t/jf4TR11lf eOsMtkLxdRbWILkNlUkxnJGJvZvgYiciDhqS+HOqVjtYqBqgTXIiiNikASLAJmeSV1 zQmLdrjYZwYFO7uQRugaFrLxxZHIg7Xm8aSGECjc= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:18 +1000 Message-Id: <20170717065621.4688-19-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 18/21] pseries: Use smaller default hash page tables when guest can resize X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" We've now implemented a PAPR extension allowing PAPR guest to resize their hash page table (HPT) during runtime. This patch makes use of that facility to allocate smaller HPTs by default. Specifically when a guest is aware of the HPT resize facility, qemu sizes the HPT to the initial memory size, rather than the maximum memory size on the assumption that the guest will resize its HPT if necessary for hot plugged memory. When the initial memory size is much smaller than the maximum memory size (a common configuration with e.g. oVirt / RHEV) then this can save significant memory on the HPT. If the guest does *not* advertise HPT resize awareness when it makes the ibm,client-architecture-support call, qemu resizes the HPT for maxmimum memory size (unless it's been configured not to allow such guests at all). For now we make that reallocation assuming the guest has not yet used the HPT at all. That's true in practice, but not, strictly, an architectural or PAPR requirement. If we need to in future we can fix this by having the client-architecture-support call reboot the guest with the revised HPT size (the client-architecture-support call is explicitly permitted to trigger a reboot in this way). Signed-off-by: David Gibson Reviewed-by: Suraj Jitindar Singh --- hw/ppc/spapr.c | 23 ++++++++++++++++++----- hw/ppc/spapr_hcall.c | 29 +++++++++++++++++++++++++++++ include/hw/ppc/spapr.h | 2 ++ include/hw/ppc/spapr_ovec.h | 1 + 4 files changed, 50 insertions(+), 5 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 3a925ef18a..68f936c4f8 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -1288,8 +1288,8 @@ void spapr_free_hpt(sPAPRMachineState *spapr) close_htab_fd(spapr); } =20 -static void spapr_reallocate_hpt(sPAPRMachineState *spapr, int shift, - Error **errp) +void spapr_reallocate_hpt(sPAPRMachineState *spapr, int shift, + Error **errp) { long rc; =20 @@ -1337,9 +1337,17 @@ static void spapr_reallocate_hpt(sPAPRMachineState *= spapr, int shift, =20 void spapr_setup_hpt_and_vrma(sPAPRMachineState *spapr) { - spapr_reallocate_hpt(spapr, - spapr_hpt_shift_for_ramsize(MACHINE(spapr)->maxram_si= ze), - &error_fatal); + int hpt_shift; + + if ((spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_DISABLED) + || (spapr->cas_reboot + && !spapr_ovec_test(spapr->ov5_cas, OV5_HPT_RESIZE))) { + hpt_shift =3D spapr_hpt_shift_for_ramsize(MACHINE(spapr)->maxram_s= ize); + } else { + hpt_shift =3D spapr_hpt_shift_for_ramsize(MACHINE(spapr)->ram_size= ); + } + spapr_reallocate_hpt(spapr, hpt_shift, &error_fatal); + if (spapr->vrma_adjust) { spapr->rma_size =3D kvmppc_rma_size(spapr_node0_size(), spapr->htab_shift); @@ -2254,6 +2262,11 @@ static void ppc_spapr_init(MachineState *machine) spapr_ovec_set(spapr->ov5, OV5_HP_EVT); } =20 + /* advertise support for HPT resizing */ + if (spapr->resize_hpt !=3D SPAPR_RESIZE_HPT_DISABLED) { + spapr_ovec_set(spapr->ov5, OV5_HPT_RESIZE); + } + /* init CPUs */ if (machine->cpu_model =3D=3D NULL) { machine->cpu_model =3D kvm_enabled() ? "host" : smc->tcg_default_c= pu; diff --git a/hw/ppc/spapr_hcall.c b/hw/ppc/spapr_hcall.c index f69ce4f60c..436f5e2b22 100644 --- a/hw/ppc/spapr_hcall.c +++ b/hw/ppc/spapr_hcall.c @@ -1473,6 +1473,35 @@ static target_ulong h_client_architecture_support(Po= werPCCPU *cpu, guest_radix =3D spapr_ovec_test(ov5_guest, OV5_MMU_RADIX_300); spapr_ovec_clear(ov5_guest, OV5_MMU_RADIX_300); =20 + /* + * HPT resizing is a bit of a special case, because when enabled + * we assume an HPT guest will support it until it says it + * doesn't, instead of assuming it won't support it until it says + * it does. Strictly speaking that approach could break for + * guests which don't make a CAS call, but those are so old we + * don't care about them. Without that assumption we'd have to + * make at least a temporary allocation of an HPT sized for max + * memory, which could be impossibly difficult under KVM HV if + * maxram is large. + */ + if (!guest_radix && !spapr_ovec_test(ov5_guest, OV5_HPT_RESIZE)) { + int maxshift =3D spapr_hpt_shift_for_ramsize(MACHINE(spapr)->maxra= m_size); + + if (spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_REQUIRED) { + error_report( + "h_client_architecture_support: Guest doesn't support HPT = resizing, but resize-hpt=3Drequired"); + exit(1); + } + + if (spapr->htab_shift < maxshift) { + /* Guest doesn't know about HPT resizing, so we + * pre-emptively resize for the maximum permitted RAM. At + * the point this is called, nothing should have been + * entered into the existing HPT */ + spapr_reallocate_hpt(spapr, maxshift, &error_fatal); + } + } + /* NOTE: there are actually a number of ov5 bits where input from the * guest is always zero, and the platform/QEMU enables them independen= tly * of guest input. To model these properly we'd want some sort of mask, diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 3dd62d81f6..2a303a705c 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -660,6 +660,8 @@ void spapr_hotplug_req_remove_by_count_indexed(sPAPRDRC= onnectorType drc_type, uint32_t count, uint32_t in= dex); void spapr_cpu_parse_features(sPAPRMachineState *spapr); int spapr_hpt_shift_for_ramsize(uint64_t ramsize); +void spapr_reallocate_hpt(sPAPRMachineState *spapr, int shift, + Error **errp); =20 /* CPU and LMB DRC release callbacks. */ void spapr_core_release(DeviceState *dev); diff --git a/include/hw/ppc/spapr_ovec.h b/include/hw/ppc/spapr_ovec.h index 0b464e22e7..9edfa5ff75 100644 --- a/include/hw/ppc/spapr_ovec.h +++ b/include/hw/ppc/spapr_ovec.h @@ -50,6 +50,7 @@ typedef struct sPAPROptionVector sPAPROptionVector; #define OV5_DRCONF_MEMORY OV_BIT(2, 2) #define OV5_FORM1_AFFINITY OV_BIT(5, 0) #define OV5_HP_EVT OV_BIT(6, 5) +#define OV5_HPT_RESIZE OV_BIT(6, 7) #define OV5_XIVE_EXPLOIT OV_BIT(23, 7) =20 /* ISA 3.00 MMU features: */ --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500274931688299.0405283670226; Mon, 17 Jul 2017 00:02:11 -0700 (PDT) Received: from localhost ([::1]:48308 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX01v-0006e3-5F for importer@patchew.org; Mon, 17 Jul 2017 03:01:19 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40563) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxL-0002ao-Al for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:38 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxJ-0001ZT-C8 for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:35 -0400 Received: from ozlabs.org ([103.22.144.67]:45317) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxI-0001XN-Nl; Mon, 17 Jul 2017 02:56:33 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM4kXjz9t3V; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=ZCVAF4l/NsAVoWhTGmxZS6VZM5yXGZlD3xhyyL5eIcU=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=nsHqgXR3o9HcJ6fqcY8NXqs82U2HxnQyjOFO3TBypGrb4NAvup9NTnvfItuOXwY1i 7SqfVB31dHM67FQGYe/dkaix93N0Y1kBE30Fc/I4ffCfUsvdOx89+WpkYp7rdLmO9F lHQ3UJt20TXw77e9C+o3PtU54td5BbJPw9+C0B1c= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:19 +1000 Message-Id: <20170717065621.4688-20-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 19/21] pseries: Allow HPT resizing with KVM X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" So far, qemu implements the PAPR Hash Page Table (HPT) resizing extension with TCG. The same implementation will work with KVM PR, but we don't currently allow that. For KVM HV we can only implement resizing with the assistance of the host kernel, which needs a new capability and ioctl()s. This patch adds support for testing the new KVM capability and implementing the resize in terms of KVM facilities when necessary. If we're running on a kernel which doesn't have the new capability flag at all, we fall back to testing for PR vs. HV KVM using the same hack that we already use in a number of places for older kernels. Signed-off-by: David Gibson --- hw/ppc/spapr_hcall.c | 66 ++++++++++++++++++++++++++++++++++++++++++++++++= +++ target/ppc/kvm.c | 67 ++++++++++++++++++++++++++++++++++++++++++++++++= ++-- target/ppc/kvm_ppc.h | 21 ++++++++++++++++ 3 files changed, 152 insertions(+), 2 deletions(-) diff --git a/hw/ppc/spapr_hcall.c b/hw/ppc/spapr_hcall.c index 436f5e2b22..72ea5a8247 100644 --- a/hw/ppc/spapr_hcall.c +++ b/hw/ppc/spapr_hcall.c @@ -426,6 +426,44 @@ static void cancel_hpt_prepare(sPAPRMachineState *spap= r) free_pending_hpt(pending); } =20 +/* Convert a return code from the KVM ioctl()s implementing resize HPT + * into a PAPR hypercall return code */ +static target_ulong resize_hpt_convert_rc(int ret) +{ + if (ret >=3D 100000) { + return H_LONG_BUSY_ORDER_100_SEC; + } else if (ret >=3D 10000) { + return H_LONG_BUSY_ORDER_10_SEC; + } else if (ret >=3D 1000) { + return H_LONG_BUSY_ORDER_1_SEC; + } else if (ret >=3D 100) { + return H_LONG_BUSY_ORDER_100_MSEC; + } else if (ret >=3D 10) { + return H_LONG_BUSY_ORDER_10_MSEC; + } else if (ret > 0) { + return H_LONG_BUSY_ORDER_1_MSEC; + } + + switch (ret) { + case 0: + return H_SUCCESS; + case -EPERM: + return H_AUTHORITY; + case -EINVAL: + return H_PARAMETER; + case -ENXIO: + return H_CLOSED; + case -ENOSPC: + return H_PTEG_FULL; + case -EBUSY: + return H_BUSY; + case -ENOMEM: + return H_NO_MEM; + default: + return H_HARDWARE; + } +} + static target_ulong h_resize_hpt_prepare(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, @@ -435,6 +473,7 @@ static target_ulong h_resize_hpt_prepare(PowerPCCPU *cp= u, int shift =3D args[1]; sPAPRPendingHPT *pending =3D spapr->pending_hpt; uint64_t current_ram_size =3D MACHINE(spapr)->ram_size; + int rc; =20 if (spapr->resize_hpt =3D=3D SPAPR_RESIZE_HPT_DISABLED) { return H_AUTHORITY; @@ -464,6 +503,11 @@ static target_ulong h_resize_hpt_prepare(PowerPCCPU *c= pu, return H_RESOURCE; } =20 + rc =3D kvmppc_resize_hpt_prepare(cpu, flags, shift); + if (rc !=3D -ENOSYS) { + return resize_hpt_convert_rc(rc); + } + if (pending) { /* something already in progress */ if (pending->shift =3D=3D shift) { @@ -659,6 +703,11 @@ static target_ulong h_resize_hpt_commit(PowerPCCPU *cp= u, =20 trace_spapr_h_resize_hpt_commit(flags, shift); =20 + rc =3D kvmppc_resize_hpt_commit(cpu, flags, shift); + if (rc !=3D -ENOSYS) { + return resize_hpt_convert_rc(rc); + } + if (flags !=3D 0) { return H_PARAMETER; } @@ -684,6 +733,13 @@ static target_ulong h_resize_hpt_commit(PowerPCCPU *cp= u, spapr->htab =3D pending->hpt; spapr->htab_shift =3D pending->shift; =20 + if (kvm_enabled()) { + /* For KVM PR, update the HPT pointer */ + target_ulong sdr1 =3D (target_ulong)(uintptr_t)spapr->htab + | (spapr->htab_shift - 18); + kvmppc_update_sdr1(sdr1); + } + pending->hpt =3D NULL; /* so it's not free()d */ } =20 @@ -1494,11 +1550,21 @@ static target_ulong h_client_architecture_support(P= owerPCCPU *cpu, } =20 if (spapr->htab_shift < maxshift) { + CPUState *cs; + /* Guest doesn't know about HPT resizing, so we * pre-emptively resize for the maximum permitted RAM. At * the point this is called, nothing should have been * entered into the existing HPT */ spapr_reallocate_hpt(spapr, maxshift, &error_fatal); + CPU_FOREACH(cs) { + if (kvm_enabled()) { + /* For KVM PR, update the HPT pointer */ + target_ulong sdr1 =3D (target_ulong)(uintptr_t)spapr->= htab + | (spapr->htab_shift - 18); + kvmppc_update_sdr1(sdr1); + } + } } } =20 diff --git a/target/ppc/kvm.c b/target/ppc/kvm.c index 8bafd1e932..85713795de 100644 --- a/target/ppc/kvm.c +++ b/target/ppc/kvm.c @@ -89,6 +89,7 @@ static int cap_fixup_hcalls; static int cap_htm; /* Hardware transactional memory support */ static int cap_mmu_radix; static int cap_mmu_hash_v3; +static int cap_resize_hpt; =20 static uint32_t debug_inst_opcode; =20 @@ -145,6 +146,7 @@ int kvm_arch_init(MachineState *ms, KVMState *s) cap_htm =3D kvm_vm_check_extension(s, KVM_CAP_PPC_HTM); cap_mmu_radix =3D kvm_vm_check_extension(s, KVM_CAP_PPC_MMU_RADIX); cap_mmu_hash_v3 =3D kvm_vm_check_extension(s, KVM_CAP_PPC_MMU_HASH_V3); + cap_resize_hpt =3D kvm_vm_check_extension(s, KVM_CAP_SPAPR_RESIZE_HPT); =20 if (!cap_interrupt_level) { fprintf(stderr, "KVM: Couldn't find level irq capability. Expect t= he " @@ -2714,11 +2716,72 @@ int kvmppc_enable_hwrng(void) void kvmppc_check_papr_resize_hpt(Error **errp) { if (!kvm_enabled()) { - return; + return; /* No KVM, we're good */ + } + + if (cap_resize_hpt) { + return; /* Kernel has explicit support, we're good */ } =20 - /* TODO: Check for resize-capable KVM implementations */ + /* Otherwise fallback on looking for PR KVM */ + if (kvmppc_is_pr(kvm_state)) { + return; + } =20 error_setg(errp, "Hash page table resizing not available with this KVM versi= on"); } + +int kvmppc_resize_hpt_prepare(PowerPCCPU *cpu, target_ulong flags, int shi= ft) +{ + CPUState *cs =3D CPU(cpu); + struct kvm_ppc_resize_hpt rhpt =3D { + .flags =3D flags, + .shift =3D shift, + }; + + if (!cap_resize_hpt) { + return -ENOSYS; + } + + return kvm_vm_ioctl(cs->kvm_state, KVM_PPC_RESIZE_HPT_PREPARE, &rhpt); +} + +int kvmppc_resize_hpt_commit(PowerPCCPU *cpu, target_ulong flags, int shif= t) +{ + CPUState *cs =3D CPU(cpu); + struct kvm_ppc_resize_hpt rhpt =3D { + .flags =3D flags, + .shift =3D shift, + }; + + if (!cap_resize_hpt) { + return -ENOSYS; + } + + return kvm_vm_ioctl(cs->kvm_state, KVM_PPC_RESIZE_HPT_COMMIT, &rhpt); +} + +static void kvmppc_pivot_hpt_cpu(CPUState *cs, run_on_cpu_data arg) +{ + target_ulong sdr1 =3D arg.target_ptr; + PowerPCCPU *cpu =3D POWERPC_CPU(cs); + CPUPPCState *env =3D &cpu->env; + + /* This is just for the benefit of PR KVM */ + cpu_synchronize_state(cs); + env->spr[SPR_SDR1] =3D sdr1; + if (kvmppc_put_books_sregs(cpu) < 0) { + error_report("Unable to update SDR1 in KVM"); + exit(1); + } +} + +void kvmppc_update_sdr1(target_ulong sdr1) +{ + CPUState *cs; + + CPU_FOREACH(cs) { + run_on_cpu(cs, kvmppc_pivot_hpt_cpu, RUN_ON_CPU_TARGET_PTR(sdr1)); + } +} diff --git a/target/ppc/kvm_ppc.h b/target/ppc/kvm_ppc.h index 9be706c5c9..6bc6fb3e2d 100644 --- a/target/ppc/kvm_ppc.h +++ b/target/ppc/kvm_ppc.h @@ -64,6 +64,9 @@ int kvmppc_enable_hwrng(void); int kvmppc_put_books_sregs(PowerPCCPU *cpu); PowerPCCPUClass *kvm_ppc_get_host_cpu_class(void); void kvmppc_check_papr_resize_hpt(Error **errp); +int kvmppc_resize_hpt_prepare(PowerPCCPU *cpu, target_ulong flags, int shi= ft); +int kvmppc_resize_hpt_commit(PowerPCCPU *cpu, target_ulong flags, int shif= t); +void kvmppc_update_sdr1(target_ulong sdr1); =20 bool kvmppc_is_mem_backend_page_size_ok(const char *obj_path); =20 @@ -302,6 +305,24 @@ static inline void kvmppc_check_papr_resize_hpt(Error = **errp) { return; } + +static inline int kvmppc_resize_hpt_prepare(PowerPCCPU *cpu, + target_ulong flags, int shift) +{ + return -ENOSYS; +} + +static inline int kvmppc_resize_hpt_commit(PowerPCCPU *cpu, + target_ulong flags, int shift) +{ + return -ENOSYS; +} + +static inline void kvmppc_update_sdr1(target_ulong sdr1) +{ + abort(); +} + #endif =20 #ifndef CONFIG_KVM --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500274713569897.5215871929108; Sun, 16 Jul 2017 23:58:33 -0700 (PDT) Received: from localhost ([::1]:48292 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzzC-0003tc-5Y for importer@patchew.org; Mon, 17 Jul 2017 02:58:30 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40552) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxK-0002aZ-WB for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:36 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxJ-0001Zb-DS for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:35 -0400 Received: from ozlabs.org ([2401:3900:2:1::2]:56237) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxJ-0001XL-1x; Mon, 17 Jul 2017 02:56:33 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGM2rNRz9t32; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274587; bh=nTlPBg9RA+BG7enIcZX+f3PqASqn+rP6m4aim66VvRE=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=VcfJyC2BL1IyGWzUjzXccVK889jMJT0Evdb2G6SbERifZ6Ny9yRH0Qe87FO/xheK0 wBNRjPk1T/L9zf8I1A/wEoH4MSPH9uvujBtCJEj20tnVA38q9VkTNtqY7fyRUL8O4L m60FZ5SdOuecqoSREjnWcjm06//KypHEJLDSGEcc= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:20 +1000 Message-Id: <20170717065621.4688-21-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2401:3900:2:1::2 Subject: [Qemu-devel] [PULL 20/21] spapr: fix memory leak in spapr_core_pre_plug() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" From: Greg Kurz In case of error, we must ensure the dynamically allocated base_core_type is freed, like it is done everywhere else in this function. This is a regression introduced in QEMU 2.9 by commit 8149e2992f78. Signed-off-by: Greg Kurz Signed-off-by: David Gibson --- hw/ppc/spapr.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 68f936c4f8..970093e6b5 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -3150,9 +3150,9 @@ static void spapr_core_pre_plug(HotplugHandler *hotpl= ug_dev, DeviceState *dev, * total vcpus not a multiple of threads-per-core. */ if (mc->has_hotpluggable_cpus && (cc->nr_threads !=3D smp_threads)) { - error_setg(errp, "invalid nr-threads %d, must be %d", + error_setg(&local_err, "invalid nr-threads %d, must be %d", cc->nr_threads, smp_threads); - return; + goto out; } =20 core_slot =3D spapr_find_cpu_slot(MACHINE(hotplug_dev), cc->core_id, &= index); --=20 2.13.3 From nobody Sat May 4 05:14:46 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1500275713865661.210181107536; Mon, 17 Jul 2017 00:15:13 -0700 (PDT) Received: from localhost ([::1]:48381 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dX0FL-0000sE-Lj for importer@patchew.org; Mon, 17 Jul 2017 03:15:11 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40798) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dWzxR-0002hQ-2n for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:43 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dWzxP-0001gB-DL for qemu-devel@nongnu.org; Mon, 17 Jul 2017 02:56:41 -0400 Received: from ozlabs.org ([103.22.144.67]:59547) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dWzxN-0001cf-T1; Mon, 17 Jul 2017 02:56:39 -0400 Received: by ozlabs.org (Postfix, from userid 1007) id 3x9vGN56cYz9t3J; Mon, 17 Jul 2017 16:56:27 +1000 (AEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gibson.dropbear.id.au; s=201602; t=1500274588; bh=FKvs/5AN6//Oxsvnnl2ONwb1860BQqWnljWUOn6rVUQ=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=R+a8pOab0huRe8s7xjYJgeUVdLp8kcjt1BzG2LvLWpzlNXcP58T/qzXM7qCYZPkMe Sv0YqZJiK7vtCqrl+ncIyCCw2SoFyAJFeyg1W/YdJw13YitCTq2QN83UUgBTKmM1MS eJSOcu4vld+YSHH8+DOKUihweOHEmTUhi3I3Lc+A= From: David Gibson To: peter.maydell@linaro.org Date: Mon, 17 Jul 2017 16:56:21 +1000 Message-Id: <20170717065621.4688-22-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.13.3 In-Reply-To: <20170717065621.4688-1-david@gibson.dropbear.id.au> References: <20170717065621.4688-1-david@gibson.dropbear.id.au> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 103.22.144.67 Subject: [Qemu-devel] [PULL 21/21] target/ppc: fix CPU hotplug when radix is enabled (TCG) X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-devel@nongnu.org, aik@ozlabs.ru, mdroth@linux.vnet.ibm.com, groug@kaod.org, qemu-ppc@nongnu.org, =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= , sjitindarsingh@gmail.com, David Gibson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" From: C=C3=A9dric Le Goater But when a guest initializes radix mode, it issues a H_REGISTER_PROC_TBL to update the LPCR of all CPUs. Hot-plugged CPUs inherit from the same setting under KVM but not under TCG. So, Let's check for radix and update the default LPCR to keep new CPUs in sync. Signed-off-by: C=C3=A9dric Le Goater Signed-off-by: David Gibson --- target/ppc/translate_init.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/target/ppc/translate_init.c b/target/ppc/translate_init.c index ae25fafab9..b325c2cce6 100644 --- a/target/ppc/translate_init.c +++ b/target/ppc/translate_init.c @@ -9011,8 +9011,16 @@ void cpu_ppc_set_papr(PowerPCCPU *cpu, PPCVirtualHyp= ervisor *vhyp) /* By default we choose legacy mode and switch to new hash or radix * when a register process table hcall is made. So disable process * tables and guest translation shootdown by default + * + * Hot-plugged CPUs inherit from the guest radix setting under + * KVM but not under TCG. Update the default LPCR to keep new + * CPUs in sync when radix is enabled. */ - lpcr->default_value &=3D ~(LPCR_UPRT | LPCR_GTSE); + if (ppc64_radix_guest(cpu)) { + lpcr->default_value |=3D LPCR_UPRT | LPCR_GTSE; + } else { + lpcr->default_value &=3D ~(LPCR_UPRT | LPCR_GTSE); + } lpcr->default_value |=3D LPCR_PDEE | LPCR_HDEE | LPCR_EEE | LPCR_D= EE | LPCR_OEE; break; --=20 2.13.3