diff options
author | Ian Campbell <ian.campbell@citrix.com> | 2011-10-18 13:36:42 +0100 |
---|---|---|
committer | Ian Campbell <ian.campbell@citrix.com> | 2011-10-18 13:36:42 +0100 |
commit | 9c85a46e0a38c01988b86d52e9369cab74f4906c (patch) | |
tree | da86d50c028f52b19d2534621dd446adf0a6a7b7 /tools/libxl/libxl_device.c | |
parent | aec4680fb168930d8e3ceb31e7ecb34f36571aa7 (diff) | |
download | xen-9c85a46e0a38c01988b86d52e9369cab74f4906c.tar.gz xen-9c85a46e0a38c01988b86d52e9369cab74f4906c.tar.bz2 xen-9c85a46e0a38c01988b86d52e9369cab74f4906c.zip |
libxl: merge libxl__device_del into libxl__device_remove
Note that the "wait" parameter added to libxl_device_remove is different to the
wait paramter previously used by similar functions. In the past not-wait meant
forced whereas now in means wait for a graceful shutdown, as opposed to setting
off a graceful shutdown but not waiting.
Signed-off-by: Ian Campbell <ian.campbell@citrix.com>
Acked-by: Ian Jackson <ian.jackson.citrix.com>
Committed-by: Ian Jackson <ian.jackson.citrix.com>
Diffstat (limited to 'tools/libxl/libxl_device.c')
-rw-r--r-- | tools/libxl/libxl_device.c | 115 |
1 files changed, 57 insertions, 58 deletions
diff --git a/tools/libxl/libxl_device.c b/tools/libxl/libxl_device.c index d4206293cb..16ee508f7e 100644 --- a/tools/libxl/libxl_device.c +++ b/tools/libxl/libxl_device.c @@ -367,7 +367,39 @@ int libxl__device_disk_dev_number(const char *virtpath, int *pdisk, return -1; } -int libxl__device_remove(libxl__gc *gc, libxl__device *dev) +static int wait_for_dev_destroy(libxl__gc *gc, struct timeval *tv) +{ + libxl_ctx *ctx = libxl__gc_owner(gc); + int nfds, rc; + unsigned int n; + fd_set rfds; + char **l1 = NULL; + + rc = 1; + nfds = xs_fileno(ctx->xsh) + 1; + FD_ZERO(&rfds); + FD_SET(xs_fileno(ctx->xsh), &rfds); + if (select(nfds, &rfds, NULL, NULL, tv) > 0) { + l1 = xs_read_watch(ctx->xsh, &n); + if (l1 != NULL) { + char *state = libxl__xs_read(gc, XBT_NULL, l1[XS_WATCH_PATH]); + if (!state || atoi(state) == 6) { + xs_unwatch(ctx->xsh, l1[0], l1[1]); + xs_rm(ctx->xsh, XBT_NULL, l1[XS_WATCH_TOKEN]); + LIBXL__LOG(ctx, LIBXL__LOG_DEBUG, "Destroyed device backend at %s", l1[XS_WATCH_TOKEN]); + rc = 0; + } + free(l1); + } + } + return rc; +} + +/* + * Returns 0 (device already destroyed) or 1 (caller must + * wait_for_dev_destroy) on success, ERROR_* on fail. + */ +int libxl__device_remove(libxl__gc *gc, libxl__device *dev, int wait) { libxl_ctx *ctx = libxl__gc_owner(gc); xs_transaction_t t; @@ -392,14 +424,24 @@ retry_transaction: if (errno == EAGAIN) goto retry_transaction; else { - rc = -1; + rc = ERROR_FAIL; goto out; } } xs_watch(ctx->xsh, state_path, be_path); libxl__device_destroy_tapdisk(gc, be_path); - rc = 1; + + if (wait) { + struct timeval tv; + tv.tv_sec = LIBXL_DESTROY_TIMEOUT; + tv.tv_usec = 0; + (void)wait_for_dev_destroy(gc, &tv); + xs_rm(ctx->xsh, XBT_NULL, libxl__device_frontend_path(gc, dev)); + } else { + rc = 1; /* Caller must wait_for_dev_destroy */ + } + out: return rc; } @@ -418,34 +460,6 @@ int libxl__device_destroy(libxl__gc *gc, libxl__device *dev) return 0; } -static int wait_for_dev_destroy(libxl__gc *gc, struct timeval *tv) -{ - libxl_ctx *ctx = libxl__gc_owner(gc); - int nfds, rc; - unsigned int n; - fd_set rfds; - char **l1 = NULL; - - rc = 1; - nfds = xs_fileno(ctx->xsh) + 1; - FD_ZERO(&rfds); - FD_SET(xs_fileno(ctx->xsh), &rfds); - if (select(nfds, &rfds, NULL, NULL, tv) > 0) { - l1 = xs_read_watch(ctx->xsh, &n); - if (l1 != NULL) { - char *state = libxl__xs_read(gc, XBT_NULL, l1[XS_WATCH_PATH]); - if (!state || atoi(state) == 6) { - xs_unwatch(ctx->xsh, l1[0], l1[1]); - xs_rm(ctx->xsh, XBT_NULL, l1[XS_WATCH_TOKEN]); - LIBXL__LOG(ctx, LIBXL__LOG_DEBUG, "Destroyed device backend at %s", l1[XS_WATCH_TOKEN]); - rc = 0; - } - free(l1); - } - } - return rc; -} - int libxl__devices_destroy(libxl__gc *gc, uint32_t domid, int force) { libxl_ctx *ctx = libxl__gc_owner(gc); @@ -485,8 +499,12 @@ int libxl__devices_destroy(libxl__gc *gc, uint32_t domid, int force) if (force) { libxl__device_destroy(gc, &dev); } else { - if (libxl__device_remove(gc, &dev) > 0) - n_watches++; + int rc = libxl__device_remove(gc, &dev, 0); + if (rc < 0) + LIBXL__LOG(ctx, LIBXL__LOG_ERROR, + "cannot remove device %s\n", path); + else + n_watches += rc; } } } @@ -504,8 +522,12 @@ int libxl__devices_destroy(libxl__gc *gc, uint32_t domid, int force) if (force) { libxl__device_destroy(gc, &dev); } else { - if (libxl__device_remove(gc, &dev) > 0) - n_watches++; + int rc = libxl__device_remove(gc, &dev, 0); + if (rc < 0) + LIBXL__LOG(ctx, LIBXL__LOG_ERROR, + "cannot remove device %s\n", path); + else + n_watches += rc; } } @@ -530,29 +552,6 @@ out: return 0; } -int libxl__device_del(libxl__gc *gc, libxl__device *dev) -{ - libxl_ctx *ctx = libxl__gc_owner(gc); - struct timeval tv; - int rc; - - rc = libxl__device_remove(gc, dev); - if (rc == -1) { - rc = ERROR_FAIL; - goto out; - } - - tv.tv_sec = LIBXL_DESTROY_TIMEOUT; - tv.tv_usec = 0; - (void)wait_for_dev_destroy(gc, &tv); - - xs_rm(ctx->xsh, XBT_NULL, libxl__device_frontend_path(gc, dev)); - rc = 0; - -out: - return rc; -} - int libxl__wait_for_device_model(libxl__gc *gc, uint32_t domid, char *state, libxl__spawn_starting *spawning, |