mirror of
https://github.com/xen-project/xen.git
synced 2026-10-28 02:01:24 +01:00
tools: Make some callers of xc_domain_getinfo() use xc_domain_getinfolist()
xc_domain_getinfo() is slow and prone to races because N hypercalls are needed to find information about N domains. xc_domain_getinfolist() finds the same information in a single hypercall as long as a big enough buffer is provided. Plus, xc_domain_getinfo() is disappearing on a future patch so migrate the callers interested in more than 1 domain to the the *list() version. Signed-off-by: Alejandro Vallejo <alejandro.vallejo@cloud.com> Acked-by: Marek Marczykowski-Górecki <marmarek@invisiblethingslab.com> Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
This commit is contained in:
1 parent
8e974df445
commit
4af349a404
3 files changed
+30
-17
No files matched your search
@@ -468,6 +468,19 @@ typedef struct xc_dominfo {
|
|||||||
|
|
||||||
typedef xen_domctl_getdomaininfo_t xc_domaininfo_t;
|
typedef xen_domctl_getdomaininfo_t xc_domaininfo_t;
|
||||||
|
|
||||||
|
static inline unsigned int dominfo_shutdown_reason(const xc_domaininfo_t *info)
|
||||||
|
{
|
||||||
|
return (info->flags >> XEN_DOMINF_shutdownshift) & XEN_DOMINF_shutdownmask;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline bool dominfo_shutdown_with(const xc_domaininfo_t *info,
|
||||||
|
unsigned int expected_reason)
|
||||||
|
{
|
||||||
|
/* The reason doesn't make sense unless the domain is actually shutdown */
|
||||||
|
return (info->flags & XEN_DOMINF_shutdown) &&
|
||||||
|
(dominfo_shutdown_reason(info) == expected_reason);
|
||||||
|
}
|
||||||
|
|
||||||
typedef union
|
typedef union
|
||||||
{
|
{
|
||||||
#if defined(__i386__) || defined(__x86_64__)
|
#if defined(__i386__) || defined(__x86_64__)
|
||||||
|
|||||||
@@ -342,7 +342,7 @@ static PyObject *pyxc_domain_getinfo(XcObject *self,
|
|||||||
uint32_t first_dom = 0;
|
uint32_t first_dom = 0;
|
||||||
int max_doms = 1024, nr_doms, i;
|
int max_doms = 1024, nr_doms, i;
|
||||||
size_t j;
|
size_t j;
|
||||||
xc_dominfo_t *info;
|
xc_domaininfo_t *info;
|
||||||
|
|
||||||
static char *kwd_list[] = { "first_dom", "max_doms", NULL };
|
static char *kwd_list[] = { "first_dom", "max_doms", NULL };
|
||||||
|
|
||||||
@@ -350,11 +350,11 @@ static PyObject *pyxc_domain_getinfo(XcObject *self,
|
|||||||
&first_dom, &max_doms) )
|
&first_dom, &max_doms) )
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
info = calloc(max_doms, sizeof(xc_dominfo_t));
|
info = calloc(max_doms, sizeof(*info));
|
||||||
if (info == NULL)
|
if (info == NULL)
|
||||||
return PyErr_NoMemory();
|
return PyErr_NoMemory();
|
||||||
|
|
||||||
nr_doms = xc_domain_getinfo(self->xc_handle, first_dom, max_doms, info);
|
nr_doms = xc_domain_getinfolist(self->xc_handle, first_dom, max_doms, info);
|
||||||
|
|
||||||
if (nr_doms < 0)
|
if (nr_doms < 0)
|
||||||
{
|
{
|
||||||
@@ -368,21 +368,21 @@ static PyObject *pyxc_domain_getinfo(XcObject *self,
|
|||||||
info_dict = Py_BuildValue(
|
info_dict = Py_BuildValue(
|
||||||
"{s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i"
|
"{s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i"
|
||||||
",s:L,s:L,s:L,s:i,s:i,s:i}",
|
",s:L,s:L,s:L,s:i,s:i,s:i}",
|
||||||
"domid", (int)info[i].domid,
|
"domid", (int)info[i].domain,
|
||||||
"online_vcpus", info[i].nr_online_vcpus,
|
"online_vcpus", info[i].nr_online_vcpus,
|
||||||
"max_vcpu_id", info[i].max_vcpu_id,
|
"max_vcpu_id", info[i].max_vcpu_id,
|
||||||
"hvm", info[i].hvm,
|
"hvm", !!(info[i].flags & XEN_DOMINF_hvm_guest),
|
||||||
"dying", info[i].dying,
|
"dying", !!(info[i].flags & XEN_DOMINF_dying),
|
||||||
"crashed", info[i].crashed,
|
"crashed", dominfo_shutdown_with(&info[i], SHUTDOWN_crash),
|
||||||
"shutdown", info[i].shutdown,
|
"shutdown", !!(info[i].flags & XEN_DOMINF_shutdown),
|
||||||
"paused", info[i].paused,
|
"paused", !!(info[i].flags & XEN_DOMINF_paused),
|
||||||
"blocked", info[i].blocked,
|
"blocked", !!(info[i].flags & XEN_DOMINF_blocked),
|
||||||
"running", info[i].running,
|
"running", !!(info[i].flags & XEN_DOMINF_running),
|
||||||
"mem_kb", (long long)info[i].nr_pages*(XC_PAGE_SIZE/1024),
|
"mem_kb", (long long)info[i].tot_pages * (XC_PAGE_SIZE / 1024),
|
||||||
"cpu_time", (long long)info[i].cpu_time,
|
"cpu_time", (long long)info[i].cpu_time,
|
||||||
"maxmem_kb", (long long)info[i].max_memkb,
|
"maxmem_kb", (long long)(info[i].max_pages << (XC_PAGE_SHIFT - 10)),
|
||||||
"ssidref", (int)info[i].ssidref,
|
"ssidref", (int)info[i].ssidref,
|
||||||
"shutdown_reason", info[i].shutdown_reason,
|
"shutdown_reason", dominfo_shutdown_reason(&info[i]),
|
||||||
"cpupool", (int)info[i].cpupool);
|
"cpupool", (int)info[i].cpupool);
|
||||||
pyhandle = PyList_New(sizeof(xen_domain_handle_t));
|
pyhandle = PyList_New(sizeof(xen_domain_handle_t));
|
||||||
if ( (pyhandle == NULL) || (info_dict == NULL) )
|
if ( (pyhandle == NULL) || (info_dict == NULL) )
|
||||||
|
|||||||
@@ -775,7 +775,7 @@ static void global_init_domain(int domid, int idx)
|
|||||||
static int indexof(int domid)
|
static int indexof(int domid)
|
||||||
{
|
{
|
||||||
int idx;
|
int idx;
|
||||||
xc_dominfo_t dominfo[NDOMAINS];
|
xc_domaininfo_t dominfo[NDOMAINS];
|
||||||
xc_interface *xc_handle;
|
xc_interface *xc_handle;
|
||||||
int ndomains;
|
int ndomains;
|
||||||
|
|
||||||
@@ -797,7 +797,7 @@ static int indexof(int domid)
|
|||||||
|
|
||||||
// call domaininfo hypercall to try and garbage collect unused entries
|
// call domaininfo hypercall to try and garbage collect unused entries
|
||||||
xc_handle = xc_interface_open(0,0,0);
|
xc_handle = xc_interface_open(0,0,0);
|
||||||
ndomains = xc_domain_getinfo(xc_handle, 0, NDOMAINS, dominfo);
|
ndomains = xc_domain_getinfolist(xc_handle, 0, NDOMAINS, dominfo);
|
||||||
xc_interface_close(xc_handle);
|
xc_interface_close(xc_handle);
|
||||||
|
|
||||||
// for each domain in our data, look for it in the system dominfo structure
|
// for each domain in our data, look for it in the system dominfo structure
|
||||||
@@ -808,7 +808,7 @@ static int indexof(int domid)
|
|||||||
int jdx;
|
int jdx;
|
||||||
|
|
||||||
for (jdx=0; jdx<ndomains; jdx++) {
|
for (jdx=0; jdx<ndomains; jdx++) {
|
||||||
if (dominfo[jdx].domid == domid)
|
if (dominfo[jdx].domain == domid)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if (jdx == ndomains) // we didn't find domid in the dominfo struct
|
if (jdx == ndomains) // we didn't find domid in the dominfo struct
|
||||||
|
|||||||