# HG changeset patch
# User Olaf Hering <olaf@xxxxxxxxx>
# Date 1316099907 -7200
# Node ID c9a9779fd9581666c3276f95020ad12e8ceff930
# Parent 7fb21fac6d7d0a20a7af9aa2caa6fb4145ee3e23
xenpaging: libxl support
Add support to libxl for starting xenpaging, I send it out for review.
It mimics what the code to start qemu-dm does.
The patch adds four new config options:
xenpaging=<int> , the number of pages to page-out
xenpaging_dir=<string>, the working directory where the pagefile is stored
xenpaging_debug=<int>, enable or disable debug output
xenpaging_policy_mru_size=<int>, tweak the number of most-recently-used pages
There are still a few pieces missing like 'xl list -l'.
Signed-off-by: Olaf Hering <olaf@xxxxxxxxx>
diff -r 7fb21fac6d7d -r c9a9779fd958 tools/libxl/libxl.h
--- a/tools/libxl/libxl.h
+++ b/tools/libxl/libxl.h
@@ -229,6 +229,7 @@ typedef struct {
libxl_domain_create_info c_info;
libxl_domain_build_info b_info;
libxl_device_model_info dm_info;
+ libxl_xenpaging_info xp_info;
int num_disks, num_vifs, num_pcidevs, num_vfbs, num_vkbs;
diff -r 7fb21fac6d7d -r c9a9779fd958 tools/libxl/libxl.idl
--- a/tools/libxl/libxl.idl
+++ b/tools/libxl/libxl.idl
@@ -190,6 +190,17 @@ by libxl_domain_build/restore. If either
then the user is responsible for calling
libxl_file_reference_unmap.""")
+libxl_xenpaging_info = Struct("xenpaging_info",[
+ ("xenpaging", integer, False, "number of pages"),
+ ("xenpaging_workdir", string, False, "directory to store guest
page file"),
+ ("xenpaging_debug", bool, False, "enable debug output in
pager"),
+ ("xenpaging_policy_mru_size", integer, False, "number of paged-in pages
to keep in memory"),
+ ],
+ comment=
+"""xenpaging information.
+
+Something review is missing""")
+
libxl_device_model_info = Struct("device_model_info",[
("domid", libxl_domid),
("uuid", libxl_uuid, False, "this is use only with stubdom,
and must be different from the domain uuid"),
diff -r 7fb21fac6d7d -r c9a9779fd958 tools/libxl/libxl_create.c
--- a/tools/libxl/libxl_create.c
+++ b/tools/libxl/libxl_create.c
@@ -429,6 +429,109 @@ retry_transaction:
return rc;
}
+static void xp_xenstore_record_pid(void *for_spawn, pid_t innerchild)
+{
+ libxl__device_model_starting *starting = for_spawn;
+ struct xs_handle *xsh;
+ char *path = NULL, *pid = NULL;
+ int len;
+
+ if (asprintf(&path, "%s/%s", starting->dom_path,
"xenpaging/xenpaging-pid") < 0)
+ goto out;
+
+ len = asprintf(&pid, "%d", innerchild);
+ if (len < 0)
+ goto out;
+
+ /* we mustn't use the parent's handle in the child */
+ xsh = xs_daemon_open();
+
+ xs_write(xsh, XBT_NULL, path, pid, len);
+
+ xs_daemon_close(xsh);
+out:
+ free(path);
+ free(pid);
+}
+
+static int libxl__create_xenpaging(libxl__gc *gc, char *dom_name, uint32_t
domid, libxl_xenpaging_info *xp_info)
+{
+ libxl__xenpaging_starting buf_starting;
+ int rc;
+ char *logfile;
+ int logfile_w, null;
+ char **args;
+ char *xp;
+ flexarray_t *xp_args;
+ libxl_ctx *ctx = libxl__gc_owner(gc);
+
+ /* Check if paging is enabled */
+ if (!xp_info->xenpaging)
+ return 0;
+
+ /* Check if xenpaging is present */
+ xp = libxl__abs_path(gc, "xenpaging", libxl_libexec_path());
+ if (access(xp, X_OK) < 0) {
+ LIBXL__LOG_ERRNO(ctx, LIBXL__LOG_ERROR, "%s is not executable", xp);
+ rc = ERROR_FAIL;
+ goto out;
+ }
+
+ /* Initialise settings for child */
+ buf_starting.domid = domid;
+ buf_starting.dom_path = libxl__xs_get_dompath(gc, domid);
+ if (!buf_starting.dom_path) {
+ rc = ERROR_FAIL;
+ goto out;
+ }
+
+ /* Set working directory if not specified in config file */
+ if (!xp_info->xenpaging_workdir)
+ xp_info->xenpaging_workdir = "/var/lib/xen/xenpaging";
+
+ /* Assemble arguments for xenpaging */
+ xp_args = flexarray_make(16, 1);
+ if (!xp_args)
+ {
+ rc = ERROR_NOMEM;
+ goto out;
+ }
+ flexarray_vappend(xp_args, xp, libxl__sprintf(gc, "%u", domid),
libxl__sprintf(gc, "%d", xp_info->xenpaging), NULL);
+ flexarray_append(xp_args, NULL);
+ args = (char **) flexarray_contents(xp_args);
+
+ /* Initialise logfile */
+ libxl_create_logfile(ctx, libxl__sprintf(gc, "xenpaging-%s-%u", dom_name,
domid), &logfile);
+ logfile_w = open(logfile, O_WRONLY|O_CREAT, 0644);
+ free(logfile);
+ null = open("/dev/null", O_RDONLY);
+
+ /* Spawn the child */
+ rc = libxl__spawn_spawn(gc, NULL, "xenpaging", xp_xenstore_record_pid,
&buf_starting);
+ if (rc < 0)
+ goto out_close;
+ if (!rc) { /* inner child */
+ setsid();
+ /* Enable debug output in the child */
+ if (xp_info->xenpaging_debug)
+ setenv("XENPAGING_DEBUG", "1", 1);
+ /* Adjust most-recently-used value in the child */
+ if (xp_info->xenpaging_policy_mru_size)
+ setenv("XENPAGING_POLICY_MRU_SIZE", libxl__sprintf(gc, "%d",
xp_info->xenpaging_policy_mru_size), 1);
+ /* Change working directory */
+ if (chdir(xp_info->xenpaging_workdir))
+ LIBXL__LOG_ERRNO(ctx, LIBXL__LOG_ERROR, "%s",
xp_info->xenpaging_workdir);
+ /* Finally run xenpaging */
+ libxl__exec(null, logfile_w, logfile_w, xp, args);
+ }
+out_close:
+ close(null);
+ close(logfile_w);
+ free(args);
+out:
+ return rc;
+}
+
static int do_domain_create(libxl__gc *gc, libxl_domain_config *d_config,
libxl_console_ready cb, void *priv,
uint32_t *domid_out, int restore_fd)
@@ -436,6 +539,7 @@ static int do_domain_create(libxl__gc *g
libxl_ctx *ctx = libxl__gc_owner(gc);
libxl__device_model_starting *dm_starting = 0;
libxl_device_model_info *dm_info = &d_config->dm_info;
+ libxl_xenpaging_info *xp_info = &d_config->xp_info;
libxl__domain_build_state state;
uint32_t domid;
int i, ret;
@@ -524,6 +628,12 @@ static int do_domain_create(libxl__gc *g
"failed to create device model: %d", ret);
goto error_out;
}
+ ret = libxl__create_xenpaging(gc, dm_info->dom_name, domid, xp_info);
+ if (ret < 0) {
+ LIBXL__LOG(ctx, LIBXL__LOG_ERROR,
+ "failed to create xenpaging: %d", ret);
+ goto error_out;
+ }
break;
}
case LIBXL_DOMAIN_TYPE_PV:
diff -r 7fb21fac6d7d -r c9a9779fd958 tools/libxl/libxl_internal.h
--- a/tools/libxl/libxl_internal.h
+++ b/tools/libxl/libxl_internal.h
@@ -251,6 +251,11 @@ typedef struct {
libxl__spawn_starting *for_spawn;
} libxl__device_model_starting;
+typedef struct {
+ char *dom_path; /* from libxl_malloc, only for xp_xenstore_record_pid */
+ int domid;
+} libxl__xenpaging_starting;
+
/* from xl_create */
_hidden int libxl__domain_make(libxl__gc *gc, libxl_domain_create_info *info,
uint32_t *domid);
_hidden int libxl__domain_build(libxl__gc *gc,
diff -r 7fb21fac6d7d -r c9a9779fd958 tools/libxl/xl_cmdimpl.c
--- a/tools/libxl/xl_cmdimpl.c
+++ b/tools/libxl/xl_cmdimpl.c
@@ -290,6 +290,7 @@ static void dolog(const char *file, int
static void printf_info(int domid,
libxl_domain_config *d_config,
+ libxl_xenpaging_info *xp_info,
libxl_device_model_info *dm_info)
{
int i;
@@ -519,6 +520,7 @@ static void parse_config_data(const char
const char *configfile_data,
int configfile_len,
libxl_domain_config *d_config,
+ libxl_xenpaging_info *xp_info,
libxl_device_model_info *dm_info)
{
const char *buf;
@@ -695,6 +697,15 @@ static void parse_config_data(const char
b_info->u.hvm.timer_mode = l;
if (!xlu_cfg_get_long (config, "nestedhvm", &l))
b_info->u.hvm.nested_hvm = l;
+
+ if (!xlu_cfg_get_long (config, "xenpaging", &l))
+ xp_info->xenpaging = l;
+ if (!xlu_cfg_get_long (config, "xenpaging_debug", &l))
+ xp_info->xenpaging_debug = l;
+ if (!xlu_cfg_get_long (config, "xenpaging_policy_mru_size", &l))
+ xp_info->xenpaging_policy_mru_size = l;
+ xlu_cfg_replace_string (config, "xenpaging_workdir",
&xp_info->xenpaging_workdir);
+
break;
case LIBXL_DOMAIN_TYPE_PV:
{
@@ -1465,7 +1476,7 @@ static int create_domain(struct domain_c
if (!dom_info->quiet)
printf("Parsing config file %s\n", config_file);
- parse_config_data(config_file, config_data, config_len, &d_config,
&d_config.dm_info);
+ parse_config_data(config_file, config_data, config_len, &d_config,
&d_config.xp_info, &d_config.dm_info);
if (migrate_fd >= 0) {
if (d_config.c_info.name) {
@@ -1486,7 +1497,7 @@ static int create_domain(struct domain_c
}
if (debug || dom_info->dryrun)
- printf_info(-1, &d_config, &d_config.dm_info);
+ printf_info(-1, &d_config, &d_config.xp_info, &d_config.dm_info);
ret = 0;
if (dom_info->dryrun)
@@ -2211,6 +2222,7 @@ static void list_domains_details(const l
uint8_t *data;
int i, len, rc;
libxl_device_model_info dm_info;
+ libxl_xenpaging_info xp_info;
for (i = 0; i < nb_domain; i++) {
/* no detailed info available on dom0 */
@@ -2221,8 +2233,8 @@ static void list_domains_details(const l
continue;
CHK_ERRNO(asprintf(&config_file, "<domid %d data>", info[i].domid));
memset(&d_config, 0x00, sizeof(d_config));
- parse_config_data(config_file, (char *)data, len, &d_config, &dm_info);
- printf_info(info[i].domid, &d_config, &dm_info);
+ parse_config_data(config_file, (char *)data, len, &d_config, &xp_info,
&dm_info);
+ printf_info(info[i].domid, &d_config, &xp_info, &dm_info);
libxl_domain_config_destroy(&d_config);
free(data);
free(config_file);
_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel
|