From nobody Tue May 13 12:25:19 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) client-ip=209.132.183.28; envelope-from=libvir-list-bounces@redhat.com; helo=mx1.redhat.com; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass(p=none dis=none) header.from=redhat.com Return-Path: Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by mx.zohomail.com with SMTPS id 1539963795466923.468638501237; Fri, 19 Oct 2018 08:43:15 -0700 (PDT) Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.phx2.redhat.com [10.5.11.13]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 82B2B30001E1; Fri, 19 Oct 2018 15:43:13 +0000 (UTC) Received: from colo-mx.corp.redhat.com (colo-mx01.intmail.prod.int.phx2.redhat.com [10.5.11.20]) by smtp.corp.redhat.com (Postfix) with ESMTPS id 398FA694BF; Fri, 19 Oct 2018 15:43:13 +0000 (UTC) Received: from lists01.pubmisc.prod.ext.phx2.redhat.com (lists01.pubmisc.prod.ext.phx2.redhat.com [10.5.19.33]) by colo-mx.corp.redhat.com (Postfix) with ESMTP id D1FAC180B5B7; Fri, 19 Oct 2018 15:43:12 +0000 (UTC) Received: from smtp.corp.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by lists01.pubmisc.prod.ext.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id w9JFDbXT007263 for ; Fri, 19 Oct 2018 11:13:37 -0400 Received: by smtp.corp.redhat.com (Postfix) id 96C8A6AE94; Fri, 19 Oct 2018 15:13:37 +0000 (UTC) Received: from unknown54ee7586bd10.attlocal.net.com (ovpn-116-156.phx2.redhat.com [10.3.116.156]) by smtp.corp.redhat.com (Postfix) with ESMTP id 506EA6AE90 for ; Fri, 19 Oct 2018 15:13:37 +0000 (UTC) From: John Ferlan To: libvir-list@redhat.com Date: Fri, 19 Oct 2018 11:13:24 -0400 Message-Id: <20181019151326.16793-11-jferlan@redhat.com> In-Reply-To: <20181019151326.16793-1-jferlan@redhat.com> References: <20181019151326.16793-1-jferlan@redhat.com> X-Scanned-By: MIMEDefang 2.79 on 10.5.11.12 X-loop: libvir-list@redhat.com Subject: [libvirt] [PATCH v2 10/12] qemu: Introduce qemuDomainSetIOThreadParams X-BeenThere: libvir-list@redhat.com X-Mailman-Version: 2.1.12 Precedence: junk List-Id: Development discussions about the libvirt library & tools List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Sender: libvir-list-bounces@redhat.com Errors-To: libvir-list-bounces@redhat.com X-Scanned-By: MIMEDefang 2.79 on 10.5.11.13 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.49]); Fri, 19 Oct 2018 15:43:14 +0000 (UTC) X-ZohoMail: RDMRC_0 RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" https://bugzilla.redhat.com/show_bug.cgi?id=3D1545732 Implement the QEMU driver mechanism in order to set the polling parameters for an IOThread within the bounds specified by the QEMU qapi parameter passing. Based heavily on patches originally posted by Pavel Hrdina , but modified to only handle alterations for a running guest. For the most part the API names changed, the typed parameters removed the poll enabled value, and the capabilities check was moved to just before the live attempt to set. Since changes are only supported for a running guest, no guest XML alterations were kept. Signed-off-by: John Ferlan --- src/qemu/qemu_driver.c | 201 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 201 insertions(+) diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index 4ddca2f765..135d44550a 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -5902,6 +5902,35 @@ qemuDomainHotplugAddIOThread(virQEMUDriverPtr driver, goto cleanup; } =20 + +static int +qemuDomainHotplugModIOThread(virQEMUDriverPtr driver, + virDomainObjPtr vm, + qemuMonitorIOThreadInfo iothread) +{ + qemuDomainObjPrivatePtr priv =3D vm->privateData; + int rc; + + if (!virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_IOTHREAD_POLLING)) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("IOThreads polling is not supported for this QEMU= ")); + return -1; + } + + qemuDomainObjEnterMonitor(driver, vm); + + rc =3D qemuMonitorSetIOThread(priv->mon, &iothread); + + if (qemuDomainObjExitMonitor(driver, vm) < 0) + return -1; + + if (rc < 0) + return -1; + + return 0; +} + + static int qemuDomainHotplugDelIOThread(virQEMUDriverPtr driver, virDomainObjPtr vm, @@ -6018,9 +6047,106 @@ qemuDomainDelIOThreadCheck(virDomainDefPtr def, return 0; } =20 + +/** + * @params: Pointer to params list + * @nparams: Number of params to be parsed + * @iothread: Buffer to store the values + * + * The following is a description of each value parsed: + * + * - "poll-max-ns" for each IOThread is the maximum time in nanoseconds + * to allow each polling interval to occur. A polling interval is a + * period of time allowed for a thread to process data before it returns + * the CPU quantum back to the host. A value set too small will not all= ow + * the IOThread to run long enough on a CPU to process data. A value set + * too high will consume too much CPU time per IOThread failing to allow + * other threads running on the CPU to get time. A value of 0 (zero) wi= ll + * disable the polling. + * + * - "poll-grow" - factor to grow the current polling time when deemed + * necessary. If a 0 (zero) value is provided, QEMU currently doubles + * its polling interval unless the current value is greater than the + * poll-max-ns. + * + * - "poll-shrink" - divisor to reduced the current polling time when deem= ed + * necessary. If a 0 (zero) value is provided, QEMU resets the polling + * interval to 0 (zero) allowing the poll-grow to manipulate the time. + * + * QEMU keeps track of the polling time elapsed and may grow or shrink the + * its polling interval based upon its heuristic algorithm. It is possible + * that calculations determine that it has found a "sweet spot" and no + * ajustments are made. The polling time value is not available. + * + * Returns 0 on success, -1 on failure with error set. + */ +static int +qemuDomainIOThreadParseParams(virTypedParameterPtr params, + int nparams, + qemuMonitorIOThreadInfoPtr iothread) +{ + int rc; + + if (virTypedParamsValidate(params, nparams, + VIR_DOMAIN_IOTHREAD_POLL_MAX_NS, + VIR_TYPED_PARAM_ULLONG, + VIR_DOMAIN_IOTHREAD_POLL_GROW, + VIR_TYPED_PARAM_UINT, + VIR_DOMAIN_IOTHREAD_POLL_SHRINK, + VIR_TYPED_PARAM_UINT, + NULL) < 0) + return -1; + + if ((rc =3D virTypedParamsGetULLong(params, nparams, + VIR_DOMAIN_IOTHREAD_POLL_MAX_NS, + &iothread->poll_max_ns)) < 0) + return -1; + if (rc =3D=3D 1) + iothread->set_poll_max_ns =3D true; + + if ((rc =3D virTypedParamsGetUInt(params, nparams, + VIR_DOMAIN_IOTHREAD_POLL_GROW, + &iothread->poll_grow)) < 0) + return -1; + if (rc =3D=3D 1) + iothread->set_poll_grow =3D true; + + if ((rc =3D virTypedParamsGetUInt(params, nparams, + VIR_DOMAIN_IOTHREAD_POLL_SHRINK, + &iothread->poll_shrink)) < 0) + return -1; + if (rc =3D=3D 1) + iothread->set_poll_shrink =3D true; + + if (iothread->set_poll_max_ns && iothread->poll_max_ns > INT_MAX) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("poll-max-ns (%llu) must be less than or equal to= %d"), + iothread->poll_max_ns, INT_MAX); + return -1; + } + + if (iothread->set_poll_grow && iothread->poll_grow > INT_MAX) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("poll-grow (%u) must be less than or equal to %d"= ), + iothread->poll_grow, INT_MAX); + return -1; + } + + if (iothread->set_poll_shrink && iothread->poll_shrink > INT_MAX) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("poll-shrink (%u) must be less than or equal to %= d"), + iothread->poll_shrink, INT_MAX); + return -1; + } + + return 0; +} + + typedef enum { VIR_DOMAIN_IOTHREAD_ACTION_ADD, VIR_DOMAIN_IOTHREAD_ACTION_DEL, + VIR_DOMAIN_IOTHREAD_ACTION_MOD, } virDomainIOThreadAction; =20 static int @@ -6071,6 +6197,20 @@ qemuDomainChgIOThread(virQEMUDriverPtr driver, goto endjob; =20 break; + + case VIR_DOMAIN_IOTHREAD_ACTION_MOD: + if (!(virDomainIOThreadIDFind(def, iothread.iothread_id))) { + virReportError(VIR_ERR_INVALID_ARG, + _("cannot find IOThread '%u' in iothreadids= "), + iothread.iothread_id); + goto endjob; + } + + if (qemuDomainHotplugModIOThread(driver, vm, iothread) < 0) + goto endjob; + + break; + } =20 if (virDomainSaveStatus(driver->xmlopt, cfg->stateDir, vm, driver-= >caps) < 0) @@ -6094,6 +6234,14 @@ qemuDomainChgIOThread(virQEMUDriverPtr driver, =20 virDomainIOThreadIDDel(persistentDef, iothread.iothread_id); =20 + break; + + case VIR_DOMAIN_IOTHREAD_ACTION_MOD: + virReportError(VIR_ERR_OPERATION_UNSUPPORTED, "%s", + _("configuring persistent polling values is " + "not supported")); + goto endjob; + break; } =20 @@ -6181,6 +6329,58 @@ qemuDomainDelIOThread(virDomainPtr dom, return ret; } =20 + +/** + * @dom: Domain to set IOThread params + * @iothread_id: IOThread 'id' that will be modified + * @params: List of parameters to change + * @nparams: Number of parameters in the list + * @flags: Flags for the set (only supports live alteration) + * + * Alter the specified @iothread_id with the values provided. + * + * Returs 0 on success, -1 on failure + */ +static int +qemuDomainSetIOThreadParams(virDomainPtr dom, + unsigned int iothread_id, + virTypedParameterPtr params, + int nparams, + unsigned int flags) +{ + virQEMUDriverPtr driver =3D dom->conn->privateData; + virDomainObjPtr vm =3D NULL; + qemuMonitorIOThreadInfo iothread =3D {0}; + int ret =3D -1; + + virCheckFlags(VIR_DOMAIN_AFFECT_LIVE, -1); + + if (iothread_id =3D=3D 0) { + virReportError(VIR_ERR_INVALID_ARG, "%s", + _("invalid value of 0 for iothread_id")); + goto cleanup; + } + + iothread.iothread_id =3D iothread_id; + + if (!(vm =3D qemuDomObjFromDomain(dom))) + goto cleanup; + + if (virDomainSetIOThreadParamsEnsureACL(dom->conn, vm->def, flags) < 0) + goto cleanup; + + if (qemuDomainIOThreadParseParams(params, nparams, &iothread) < 0) + goto cleanup; + + ret =3D qemuDomainChgIOThread(driver, vm, iothread, + VIR_DOMAIN_IOTHREAD_ACTION_MOD, flags); + + cleanup: + virDomainObjEndAPI(&vm); + return ret; +} + + static int qemuDomainGetSecurityLabel(virDomainPtr dom, virSecurityLabelPt= r seclabel) { virQEMUDriverPtr driver =3D dom->conn->privateData; @@ -21964,6 +22164,7 @@ static virHypervisorDriver qemuHypervisorDriver =3D= { .domainPinIOThread =3D qemuDomainPinIOThread, /* 1.2.14 */ .domainAddIOThread =3D qemuDomainAddIOThread, /* 1.2.15 */ .domainDelIOThread =3D qemuDomainDelIOThread, /* 1.2.15 */ + .domainSetIOThreadParams =3D qemuDomainSetIOThreadParams, /* 4.9.0 */ .domainGetSecurityLabel =3D qemuDomainGetSecurityLabel, /* 0.6.1 */ .domainGetSecurityLabelList =3D qemuDomainGetSecurityLabelList, /* 0.1= 0.0 */ .nodeGetSecurityModel =3D qemuNodeGetSecurityModel, /* 0.6.1 */ --=20 2.17.2 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list