[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-devel] [PATCH] XENMEM_memory_map and DOMCTL_set_memmap_limit implementation
Keir, Here follows the hopefully end revision. If you think it needs more rework, just please warn me ASAP. -- Glauber de Oliveira Costa Red Hat Inc. "Free as in Freedom" # HG changeset patch # User gcosta@xxxxxxxxxx # Date 1164812939 18000 # Node ID 0d6e4c983718a41b651bb8504ff5949a623b4e09 # Parent 71ea8d34e818c7aed76e77edcf7a23a7e6e9e71e Implement memory_map hypercall + set_memmap_limit domctl and friends This patch implements two new interfaces: XENMEM_memory_map hypercall, currently defined, but not implemented. It provides a way to inform guests about how should their physical memory mapping look like. DOMCTL_set_memmap_limit domctl and proper tools, which allows us to inform the hypervisor about the maximum size guest's physical mapping can grow to. Signed-off-by: Glauber de Oliveira Costa <gcosta@xxxxxxxxxx> diff -r 71ea8d34e818 -r 0d6e4c983718 tools/libxc/xc_domain.c --- a/tools/libxc/xc_domain.c Wed Nov 29 08:36:41 2006 -0500 +++ b/tools/libxc/xc_domain.c Wed Nov 29 10:08:59 2006 -0500 @@ -313,6 +313,17 @@ int xc_domain_setmaxmem(int xc_handle, domctl.cmd = XEN_DOMCTL_max_mem; domctl.domain = (domid_t)domid; domctl.u.max_mem.max_memkb = max_memkb; + return do_domctl(xc_handle, &domctl); +} + +int xc_domain_set_memmap_limit(int xc_handle, + uint32_t domid, + unsigned int map_limitkb) +{ + DECLARE_DOMCTL; + domctl.cmd = XEN_DOMCTL_memmap_limit; + domctl.domain = (domid_t)domid; + domctl.u.memmap_limit.map_limitkb = map_limitkb; return do_domctl(xc_handle, &domctl); } diff -r 71ea8d34e818 -r 0d6e4c983718 tools/libxc/xenctrl.h --- a/tools/libxc/xenctrl.h Wed Nov 29 08:36:41 2006 -0500 +++ b/tools/libxc/xenctrl.h Wed Nov 29 10:08:59 2006 -0500 @@ -415,6 +415,10 @@ int xc_domain_setmaxmem(int xc_handle, uint32_t domid, unsigned int max_memkb); +int xc_domain_set_memmap_limit(int xc_handle, + uint32_t domid, + unsigned int map_limitkb); + int xc_domain_set_time_offset(int xc_handle, uint32_t domid, int32_t time_offset_seconds); diff -r 71ea8d34e818 -r 0d6e4c983718 tools/python/xen/lowlevel/xc/xc.c --- a/tools/python/xen/lowlevel/xc/xc.c Wed Nov 29 08:36:41 2006 -0500 +++ b/tools/python/xen/lowlevel/xc/xc.c Wed Nov 29 10:08:59 2006 -0500 @@ -741,6 +741,21 @@ static PyObject *pyxc_domain_setmaxmem(X return zero; } +static PyObject *pyxc_domain_set_memmap_limit(XcObject *self, PyObject *args) +{ + uint32_t dom; + unsigned int maplimit_kb; + + if (!PyArg_ParseTuple(args, "ii", &dom, &maplimit_kb)) + return NULL; + + if (xc_domain_set_memmap_limit(self->xc_handle, dom, maplimit_kb) != 0) + return PyErr_SetFromErrno(xc_error); + + Py_INCREF(zero); + return zero; +} + static PyObject *pyxc_domain_memory_increase_reservation(XcObject *self, PyObject *args, PyObject *kwds) @@ -1122,6 +1137,14 @@ static PyMethodDef pyxc_methods[] = { "Set a domain's memory limit\n" " dom [int]: Identifier of domain.\n" " maxmem_kb [int]: .\n" + "Returns: [int] 0 on success; -1 on error.\n" }, + + { "domain_set_memmap_limit", + (PyCFunction)pyxc_domain_set_memmap_limit, + METH_VARARGS, "\n" + "Set a domain's physical memory mappping limit\n" + " dom [int]: Identifier of domain.\n" + " map_limitkb [int]: .\n" "Returns: [int] 0 on success; -1 on error.\n" }, { "domain_memory_increase_reservation", diff -r 71ea8d34e818 -r 0d6e4c983718 tools/python/xen/xend/XendDomainInfo.py --- a/tools/python/xen/xend/XendDomainInfo.py Wed Nov 29 08:36:41 2006 -0500 +++ b/tools/python/xen/xend/XendDomainInfo.py Wed Nov 29 10:08:59 2006 -0500 @@ -1297,6 +1297,10 @@ class XendDomainInfo: # set memory limit xc.domain_setmaxmem(self.domid, maxmem) + + # set physical mapping limit + # add an 8MB slack to balance backend allocations. + xc.domain_set_memmap_limit(self.domid, maxmem + (8 << 20)) # Make sure there's enough RAM available for the domain balloon.free(memory + shadow) diff -r 71ea8d34e818 -r 0d6e4c983718 xen/arch/x86/mm.c --- a/xen/arch/x86/mm.c Wed Nov 29 08:36:41 2006 -0500 +++ b/xen/arch/x86/mm.c Wed Nov 29 10:08:59 2006 -0500 @@ -2976,7 +2976,40 @@ long arch_memory_op(int op, XEN_GUEST_HA case XENMEM_memory_map: { - return -ENOSYS; + struct xen_memory_map memmap; + struct domain *d; + XEN_GUEST_HANDLE(e820entry_t) buffer; + struct e820entry map; + + + d = current->domain; + + if ( copy_from_guest(&memmap, arg, 1) ) + return -EFAULT; + + buffer = guest_handle_cast(memmap.buffer, e820entry_t); + if ( unlikely(guest_handle_is_null(buffer)) ) + return -EFAULT; + + memmap.nr_entries = 1; + + if ( d->memmap_limit ) + map.size = d->memmap_limit; + else + /* Don know how to implement the mapping. Act as if it were not + * implemented */ + return -ENOSYS; + + map.addr = 0ULL; + map.type = E820_RAM; + + if ( copy_to_guest(arg, &memmap, 1) ) + return -EFAULT; + + if ( copy_to_guest(buffer, &map, 1) < 0 ) + return -EFAULT; + + return 0; } case XENMEM_machine_memory_map: diff -r 71ea8d34e818 -r 0d6e4c983718 xen/common/domctl.c --- a/xen/common/domctl.c Wed Nov 29 08:36:41 2006 -0500 +++ b/xen/common/domctl.c Wed Nov 29 10:08:59 2006 -0500 @@ -552,6 +552,29 @@ long do_domctl(XEN_GUEST_HANDLE(xen_domc } break; + case XEN_DOMCTL_memmap_limit: + { + struct domain *d; + unsigned long new_limit; + + ret = -ESRCH; + d = find_domain_by_id(op->domain); + if ( d == NULL ) + break; + + ret = -EINVAL; + new_limit = op->u.memmap_limit.map_limitkb << 10; + + /* No point in neither calling it more than once, nor + * setting physical map limit to zero */ + if ( (d->memmap_limit == 0) && (new_limit != 0) ) + { + d->memmap_limit = new_limit; + ret = 0; + } + + put_domain(d); + } case XEN_DOMCTL_setdomainhandle: { struct domain *d; diff -r 71ea8d34e818 -r 0d6e4c983718 xen/include/public/domctl.h --- a/xen/include/public/domctl.h Wed Nov 29 08:36:41 2006 -0500 +++ b/xen/include/public/domctl.h Wed Nov 29 10:08:59 2006 -0500 @@ -385,6 +385,14 @@ typedef struct xen_domctl_settimeoffset typedef struct xen_domctl_settimeoffset xen_domctl_settimeoffset_t; DEFINE_XEN_GUEST_HANDLE(xen_domctl_settimeoffset_t); +#define XEN_DOMCTL_memmap_limit 26 +struct xen_domctl_memmap_limit { + /* IN variables. */ + uint64_t map_limitkb; +}; +typedef struct xen_domctl_memory_map_limit xen_domctl_map_limit_t; +DEFINE_XEN_GUEST_HANDLE(xen_domctl_map_limit_t); + struct xen_domctl { uint32_t cmd; uint32_t interface_version; /* XEN_DOMCTL_INTERFACE_VERSION */ @@ -410,9 +418,11 @@ struct xen_domctl { struct xen_domctl_hypercall_init hypercall_init; struct xen_domctl_arch_setup arch_setup; struct xen_domctl_settimeoffset settimeoffset; - uint8_t pad[128]; + struct xen_domctl_memmap_limit memmap_limit; + uint8_t pad[120]; } u; }; + typedef struct xen_domctl xen_domctl_t; DEFINE_XEN_GUEST_HANDLE(xen_domctl_t); diff -r 71ea8d34e818 -r 0d6e4c983718 xen/include/xen/sched.h --- a/xen/include/xen/sched.h Wed Nov 29 08:36:41 2006 -0500 +++ b/xen/include/xen/sched.h Wed Nov 29 10:08:59 2006 -0500 @@ -112,6 +112,7 @@ struct domain struct list_head xenpage_list; /* linked list, of size xenheap_pages */ unsigned int tot_pages; /* number of pages currently possesed */ unsigned int max_pages; /* maximum value for tot_pages */ + unsigned int memmap_limit; /* the higher our memory map can go */ unsigned int xenheap_pages; /* # pages allocated from Xen heap */ /* Scheduling. */ _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |