On 7/29/2026 9:31 AM, Peter Krempa wrote:
On Wed, Jul 22, 2026 at 13:52:13 -0500, Jaehoon Kim wrote:
Add virsh support for configuring and reporting iothread poll-weight.

Document poll-weight in the virsh manpage and extend iothreadset so
that poll-weight can be configured from the command line. Also add
poll-weight support to the test driver and extend virshtest accordingly.

Signed-off-by: Jaehoon Kim <[email protected]>
---
  docs/manpages/virsh.rst           | 18 ++++++++++++------
  src/test/test_driver.c            | 12 ++++++++++++
  tests/virshtestdata/iothreads.in  |  2 ++
  tests/virshtestdata/iothreads.out | 18 ++++++++++++++++++
  tools/virsh-domain.c              | 18 ++++++++++++++++++
  5 files changed, 62 insertions(+), 6 deletions(-)

diff --git a/docs/manpages/virsh.rst b/docs/manpages/virsh.rst
index a10d29e0ea..24052d0cdb 100644
--- a/docs/manpages/virsh.rst
+++ b/docs/manpages/virsh.rst
@@ -2905,6 +2905,8 @@ not available for statistical purposes.
    growth is managed by the hypervisor.
  * ``iothread.<id>.poll-shrink`` - polling time shrink value. A value of
    (zero) indicates shrink is managed by hypervisor.
+* ``iothread.<id>.poll-weight`` - polling weight shift value. A value of 0
+  (zero) indicates the hypervisor's default weight is used.
This hunk belongs to the patch that adds the stats gathering code since
it starts being emitted at that point.

This patch is adding the code to modify the setting.

I'll move to the stats patch in v2.


*--memory* returns: @@ -3498,8 +3500,8 @@ iothreadset
  ::
iothreadset domain iothread_id [[--poll-max-ns ns] [--poll-grow factor]
-      [--poll-shrink divisor] [--thread-pool-min value]
-      [--thread-pool-max value]]
+      [--poll-shrink divisor] [--poll-weight factor]
+      [--thread-pool-min value] [--thread-pool-max value]]
        [[--config] [--live] | [--current]]
Modifies an existing iothread of the domain using the specified
@@ -3511,10 +3513,14 @@ reach the maximum polling time. If a 0 (zero) is 
provided, then the
  default factor will be used. The *--poll-shrink* is the quotient
  by which the current polling time will be reduced in order to get
  below the maximum polling interval. If a 0 (zero) is provided, then
-the default quotient will be used. The polling values are purely dynamic
-for a running guest. Saving, destroying, stopping, etc. the guest will
-result in the polling values returning to hypervisor defaults at the
-next start, restore, etc.
+the default quotient will be used. The *--poll-weight* sets the weight
+shift value for adaptive polling, determining how much the most recent
+event interval affects the next polling duration calculation. Larger
+values reduce the weight of recent events. Valid range is [0, 63].
+If omitted or set to 0, the hypervisor selects a default.
This is not accurate. If the --poll-weight parameter is not supplied
this virsh command will not put the VIR_DOMAIN_IOTHREAD_POLL_WEIGHT
parameter to the list of stuff to change.

At that point the backend code will not modify this value rather than
set it to the default.

Correct. If --poll-weight is omitted, the value is not changed. I'll fix
the documentation in v2.

+The polling values are purely dynamic for a running guest. Saving,
+destroying, stopping, etc. the guest will result in the polling values
+returning to hypervisor defaults at the next start, restore, etc.
The *--thread-pool-min* and *--thread-pool-max* options then set lower and
  upper bound, respectively of number of threads in worker pool of given
diff --git a/src/test/test_driver.c b/src/test/test_driver.c
index 536e291861..8546c3e251 100644
--- a/src/test/test_driver.c
+++ b/src/test/test_driver.c
@@ -189,6 +189,7 @@ struct _testIOThreadInfo {
      unsigned long long poll_max_ns;
      unsigned int poll_grow;
      unsigned int poll_shrink;
+    unsigned int poll_weight;
  };
static void
@@ -749,6 +750,7 @@ testDomainGenerateIOThreadInfos(virDomainObj *obj)
          iothread.poll_max_ns = 32768;
          iothread.poll_grow = 0;
          iothread.poll_shrink = 0;
+        iothread.poll_weight = 0;
          g_array_append_val(priv->iothreads, iothread);
      }
  }
@@ -9681,6 +9683,7 @@ testDomainAddIOThread(virDomainPtr dom,
      iothread.poll_max_ns = 32768;
      iothread.poll_grow = 0;
      iothread.poll_shrink = 0;
+    iothread.poll_weight = 0;
g_array_append_val(priv->iothreads, iothread); @@ -9795,6 +9798,8 @@ testDomainIOThreadParseParams(virTypedParameterPtr params,
                                 VIR_TYPED_PARAM_UINT,
                                 VIR_DOMAIN_IOTHREAD_POLL_SHRINK,
                                 VIR_TYPED_PARAM_UINT,
+                               VIR_DOMAIN_IOTHREAD_POLL_WEIGHT,
+                               VIR_TYPED_PARAM_UINT,
                                 NULL) < 0)
          return -1;
@@ -9813,6 +9818,11 @@ testDomainIOThreadParseParams(virTypedParameterPtr params,
                                &iothread->poll_shrink) < 0)
          return -1;
+ if (virTypedParamsGetUInt(params, nparams,
+                              VIR_DOMAIN_IOTHREAD_POLL_WEIGHT,
+                              &iothread->poll_weight) < 0)
+        return -1;
+
      return 0;
  }
@@ -9899,6 +9909,8 @@ testDomainGetStatsIOThread(virDomainObj *dom,
                                   "iothread.%u.poll-grow", 
iothread.iothread_id);
          virTypedParamListAddUInt(params, iothread.poll_shrink,
                                   "iothread.%u.poll-shrink", 
iothread.iothread_id);
+        virTypedParamListAddUInt(params, iothread.poll_weight,
+                                 "iothread.%u.poll-weight", 
iothread.iothread_id);
      }
return 0;
Please separate the testr driver changes into a separate patch.

I will move the test driver changes into a separate patch in v2.


diff --git a/tests/virshtestdata/iothreads.in b/tests/virshtestdata/iothreads.in
index 25ebcb5cda..b5aed83bba 100644
--- a/tests/virshtestdata/iothreads.in
+++ b/tests/virshtestdata/iothreads.in
@@ -7,6 +7,8 @@ iothreadinfo --domain fc4
  domstats --domain fc4
  iothreadset --domain fc4 --id 6 --poll-max-ns 100 --poll-shrink 10 
--poll-grow 10
  domstats --domain fc4
+iothreadset --domain fc4 --id 6 --poll-weight 3
+domstats --domain fc4
iothreadadd --domain fc5 --id 2
  iothreadinfo --domain fc5
diff --git a/tests/virshtestdata/iothreads.out 
b/tests/virshtestdata/iothreads.out
index 1e38733bcf..a51593d765 100644
--- a/tests/virshtestdata/iothreads.out
+++ b/tests/virshtestdata/iothreads.out
@@ -23,9 +23,11 @@ Domain: 'fc4'
    iothread.4.poll-max-ns=32768
    iothread.4.poll-grow=0
    iothread.4.poll-shrink=0
+  iothread.4.poll-weight=0
    iothread.6.poll-max-ns=32768
    iothread.6.poll-grow=0
    iothread.6.poll-shrink=0
+  iothread.6.poll-weight=0
Domain: 'fc4'
@@ -35,9 +37,25 @@ Domain: 'fc4'
    iothread.4.poll-max-ns=32768
    iothread.4.poll-grow=0
    iothread.4.poll-shrink=0
+  iothread.4.poll-weight=0
    iothread.6.poll-max-ns=100
    iothread.6.poll-grow=10
    iothread.6.poll-shrink=10
+  iothread.6.poll-weight=0
+
+
+Domain: 'fc4'
+  state.state=1
+  state.reason=0
+  iothread.count=2
+  iothread.4.poll-max-ns=32768
+  iothread.4.poll-grow=0
+  iothread.4.poll-shrink=0
+  iothread.4.poll-weight=0
+  iothread.6.poll-max-ns=100
+  iothread.6.poll-grow=10
+  iothread.6.poll-shrink=10
+  iothread.6.poll-weight=3
IOThread ID CPU Affinity
IIUC the fetching of the value will change this output right when the
test driver code is changed, so those bits will need to be moved there.

The last one where the weight is set will need to happen after that
patch but also possibly in a separate commit.

Understood, I will move the poll-weight=0 output changes caused by the
test driver stats emission to the test driver patch. The poll-weight=3
output after the iothreadset call will be moved to a patch after that.


diff --git a/tools/virsh-domain.c b/tools/virsh-domain.c
index aa4f2a7a48..2e4923283b 100644
--- a/tools/virsh-domain.c
+++ b/tools/virsh-domain.c
@@ -8270,6 +8270,11 @@ static const vshCmdOptDef opts_iothreadset[] = {
       .unwanted_positional = true,
       .help = N_("set the value for reduction of the IOThread polling time")
      },
+    {.name = "poll-weight",
+     .type = VSH_OT_INT,
+     .unwanted_positional = true,
+     .help = N_("set the adaptive polling weight factor")
+    },
      {.name = "thread-pool-min",
       .type = VSH_OT_INT,
       .unwanted_positional = true,
@@ -8299,6 +8304,7 @@ cmdIOThreadSet(vshControl *ctl, const vshCmd *cmd)
      virTypedParameterPtr par;
      size_t npar = 0;
      unsigned long long poll_val;
+    unsigned int poll_weight;
      int thread_val;
      int rc;
@@ -8335,6 +8341,18 @@ cmdIOThreadSet(vshControl *ctl, const vshCmd *cmd)
      if (rc > 0)
          virTypedParamListAddUnsigned(params, poll_val, 
VIR_DOMAIN_IOTHREAD_POLL_SHRINK);
+ if ((rc = vshCommandOptUInt(ctl, cmd, "poll-weight", &poll_weight)) < 0)
+        return false;
+    if (rc > 0) {
+        if (poll_weight > 63) {
+            vshError(ctl, _("poll-weight value %1$u is out of range [0, 63]"),
+                     poll_weight);
+            return false;
+        }
+
+        virTypedParamListAddUInt(params, poll_weight, 
VIR_DOMAIN_IOTHREAD_POLL_WEIGHT);
+    }
+
      if ((rc = vshCommandOptInt(ctl, cmd, "thread-pool-min", &thread_val)) < 0)
          return false;
      if (rc > 0)
--
2.54.0


Reply via email to