[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[xen master] libxc/PM: Ensure pxstat buffers are correctly sized



commit de6a05a8a0d5090f1cdb9b5449b034afcbe7a208
Author:     Ross Lagerwall <ross.lagerwall@xxxxxxxxxx>
AuthorDate: Wed Jun 11 11:06:45 2025 +0200
Commit:     Jan Beulich <jbeulich@xxxxxxxx>
CommitDate: Wed Jun 11 11:06:45 2025 +0200

    libxc/PM: Ensure pxstat buffers are correctly sized
    
    xc_pm_get_pxstat() requires the caller to allocate the pt and trans_pt
    buffers but then calls xc_pm_get_max_px() to determine how big they are
    (and hence how much Xen will copy into them). This is susceptible to
    races if xc_pm_get_max_px() changes so avoid the problem by requiring
    the caller to also pass in the size of the buffers.
    
    Suggested-by: Jan Beulich <jbeulich@xxxxxxxx>
    Signed-off-by: Ross Lagerwall <ross.lagerwall@xxxxxxxxxx>
    Reviewed-by: Anthony PERARD <anthony.perard@xxxxxxxxxx>
---
 tools/libs/ctrl/xc_pm.c | 22 ++++++++++------------
 tools/misc/xenpm.c      |  1 +
 2 files changed, 11 insertions(+), 12 deletions(-)

diff --git a/tools/libs/ctrl/xc_pm.c b/tools/libs/ctrl/xc_pm.c
index ff7b5ada05..1f2430cac2 100644
--- a/tools/libs/ctrl/xc_pm.c
+++ b/tools/libs/ctrl/xc_pm.c
@@ -45,36 +45,34 @@ int xc_pm_get_max_px(xc_interface *xch, int cpuid, int 
*max_px)
 int xc_pm_get_pxstat(xc_interface *xch, int cpuid, struct xc_px_stat *pxpt)
 {
     struct xen_sysctl sysctl = {};
-    /* Sizes unknown until xc_pm_get_max_px */
-    DECLARE_NAMED_HYPERCALL_BOUNCE(trans, pxpt->trans_pt, 0, 
XC_HYPERCALL_BUFFER_BOUNCE_BOTH);
-    DECLARE_NAMED_HYPERCALL_BOUNCE(pt, pxpt->pt, 0, 
XC_HYPERCALL_BUFFER_BOUNCE_BOTH);
+    DECLARE_NAMED_HYPERCALL_BOUNCE(trans, pxpt->trans_pt,
+                                   pxpt->total * pxpt->total * 
sizeof(uint64_t),
+                                   XC_HYPERCALL_BUFFER_BOUNCE_BOTH);
+    DECLARE_NAMED_HYPERCALL_BOUNCE(pt, pxpt->pt,
+                                   pxpt->total * sizeof(struct xc_px_val),
+                                   XC_HYPERCALL_BUFFER_BOUNCE_BOTH);
 
-    int max_px, ret;
+    int ret;
 
     if ( !pxpt->trans_pt || !pxpt->pt )
     {
         errno = EINVAL;
         return -1;
     }
-    if ( (ret = xc_pm_get_max_px(xch, cpuid, &max_px)) != 0)
-        return ret;
-
-    HYPERCALL_BOUNCE_SET_SIZE(trans, max_px * max_px * sizeof(uint64_t));
-    HYPERCALL_BOUNCE_SET_SIZE(pt, max_px * sizeof(struct xc_px_val));
 
     if ( xc_hypercall_bounce_pre(xch, trans) )
-        return ret;
+        return -1;
 
     if ( xc_hypercall_bounce_pre(xch, pt) )
     {
         xc_hypercall_bounce_post(xch, trans);
-        return ret;
+        return -1;
     }
 
     sysctl.cmd = XEN_SYSCTL_get_pmstat;
     sysctl.u.get_pmstat.type = PMSTAT_get_pxstat;
     sysctl.u.get_pmstat.cpuid = cpuid;
-    sysctl.u.get_pmstat.u.getpx.total = max_px;
+    sysctl.u.get_pmstat.u.getpx.total = pxpt->total;
     set_xen_guest_handle(sysctl.u.get_pmstat.u.getpx.trans_pt, trans);
     set_xen_guest_handle(sysctl.u.get_pmstat.u.getpx.pt, pt);
 
diff --git a/tools/misc/xenpm.c b/tools/misc/xenpm.c
index db658ebadd..de319329e6 100644
--- a/tools/misc/xenpm.c
+++ b/tools/misc/xenpm.c
@@ -319,6 +319,7 @@ static int get_pxstat_by_cpuid(xc_interface *xc_handle, int 
cpuid, struct xc_px_
     if ( !pxstat)
         return -EINVAL;
 
+    pxstat->total = max_px_num;
     pxstat->trans_pt = malloc(max_px_num * max_px_num *
                               sizeof(uint64_t));
     if ( !pxstat->trans_pt )
--
generated by git-patchbot for /home/xen/git/xen.git#master



 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.