[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [PATCH v2 4/5] 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> --- * New in v2. tools/libs/ctrl/xc_pm.c | 20 +++++++++----------- tools/misc/xenpm.c | 1 + 2 files changed, 10 insertions(+), 11 deletions(-) diff --git a/tools/libs/ctrl/xc_pm.c b/tools/libs/ctrl/xc_pm.c index ff7b5ada053f..cffbd1b8a955 100644 --- a/tools/libs/ctrl/xc_pm.c +++ b/tools/libs/ctrl/xc_pm.c @@ -46,35 +46,33 @@ 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, + XC_HYPERCALL_BUFFER_BOUNCE_BOTH); + DECLARE_NAMED_HYPERCALL_BOUNCE(pt, pxpt->pt, pxpt->total, + 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 db658ebaddd5..de319329e6b0 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 ) -- 2.49.0
|
![]() |
Lists.xenproject.org is hosted with RackSpace, monitoring our |