From 4fa36f1392e0ca411c345e5f4c37c91182b750a0 Mon Sep 17 00:00:00 2001 From: Osier Yang Date: Tue, 29 Nov 2011 15:34:53 +0800 Subject: [PATCH] block_resize: Implement qemu monitor functions Implements functions for both HMP and QMP mode. For HMP mode, qemu uses "M" as the units by default, so the passed "sized" is divided by 1024. For QMP mode, qemu uses "Bytes" as the units by default, the passed "sized" is multiplied by 1024. All of the monitor functions return -1 on failure, 0 on success, or -2 if not supported. --- src/qemu/qemu_monitor.c | 15 +++++++++++++++ src/qemu/qemu_monitor.h | 5 +++-- src/qemu/qemu_monitor_json.c | 32 ++++++++++++++++++++++++++++++++ src/qemu/qemu_monitor_json.h | 4 +++- src/qemu/qemu_monitor_text.c | 33 +++++++++++++++++++++++++++++++++ src/qemu/qemu_monitor_text.h | 4 +++- 6 files changed, 89 insertions(+), 4 deletions(-) diff --git a/src/qemu/qemu_monitor.c b/src/qemu/qemu_monitor.c index 73e5ea9867..6423bf785d 100644 --- a/src/qemu/qemu_monitor.c +++ b/src/qemu/qemu_monitor.c @@ -1307,6 +1307,21 @@ int qemuMonitorGetBlockExtent(qemuMonitorPtr mon, return ret; } +int qemuMonitorBlockResize(qemuMonitorPtr mon, + const char *device, + unsigned long long size) +{ + int ret; + VIR_DEBUG("mon=%p, fd=%d, devname=%p size=%llu", + mon, mon->fd, device, size); + + if (mon->json) + ret = qemuMonitorJSONBlockResize(mon, device, size); + else + ret = qemuMonitorTextBlockResize(mon, device, size); + + return ret; +} int qemuMonitorSetVNCPassword(qemuMonitorPtr mon, const char *password) diff --git a/src/qemu/qemu_monitor.h b/src/qemu/qemu_monitor.h index 883e0aaf1e..41b8da2cff 100644 --- a/src/qemu/qemu_monitor.h +++ b/src/qemu/qemu_monitor.h @@ -255,8 +255,9 @@ int qemuMonitorGetBlockStatsParamsNumber(qemuMonitorPtr mon, int qemuMonitorGetBlockExtent(qemuMonitorPtr mon, const char *dev_name, unsigned long long *extent); - - +int qemuMonitorBlockResize(qemuMonitorPtr mon, + const char *devname, + unsigned long long size); int qemuMonitorSetVNCPassword(qemuMonitorPtr mon, const char *password); int qemuMonitorSetPassword(qemuMonitorPtr mon, diff --git a/src/qemu/qemu_monitor_json.c b/src/qemu/qemu_monitor_json.c index 56a62dbf41..2ea5e48ce4 100644 --- a/src/qemu/qemu_monitor_json.c +++ b/src/qemu/qemu_monitor_json.c @@ -1775,6 +1775,38 @@ cleanup: return ret; } +/* Return 0 on success, -1 on failure, or -2 if not supported. */ +int qemuMonitorJSONBlockResize(qemuMonitorPtr mon, + const char *device, + unsigned long long size) +{ + int ret; + virJSONValuePtr cmd; + virJSONValuePtr reply = NULL; + + cmd = qemuMonitorJSONMakeCommand("block_resize", + "s:device", device, + "U:size", size * 1024, + NULL); + if (!cmd) + return -1; + + ret = qemuMonitorJSONCommand(mon, cmd, &reply); + + if (ret == 0) { + if (qemuMonitorJSONHasError(reply, "CommandNotFound")) { + ret = -2; + goto cleanup; + } + + ret = qemuMonitorJSONCheckError(cmd, reply); + } + +cleanup: + virJSONValueFree(cmd); + virJSONValueFree(reply); + return ret; +} int qemuMonitorJSONSetVNCPassword(qemuMonitorPtr mon, const char *password) diff --git a/src/qemu/qemu_monitor_json.h b/src/qemu/qemu_monitor_json.h index f10d7d20ce..d31b32bc41 100644 --- a/src/qemu/qemu_monitor_json.h +++ b/src/qemu/qemu_monitor_json.h @@ -81,7 +81,9 @@ int qemuMonitorJSONGetBlockStatsParamsNumber(qemuMonitorPtr mon, int qemuMonitorJSONGetBlockExtent(qemuMonitorPtr mon, const char *dev_name, unsigned long long *extent); - +int qemuMonitorJSONBlockResize(qemuMonitorPtr mon, + const char *devce, + unsigned long long size); int qemuMonitorJSONSetVNCPassword(qemuMonitorPtr mon, const char *password); diff --git a/src/qemu/qemu_monitor_text.c b/src/qemu/qemu_monitor_text.c index 5de4d24be8..728bea84b2 100644 --- a/src/qemu/qemu_monitor_text.c +++ b/src/qemu/qemu_monitor_text.c @@ -1075,6 +1075,39 @@ int qemuMonitorTextGetBlockExtent(qemuMonitorPtr mon ATTRIBUTE_UNUSED, return -1; } +/* Return 0 on success, -1 on failure, or -2 if not supported. */ +int qemuMonitorTextBlockResize(qemuMonitorPtr mon, + const char *device, + unsigned long long size) +{ + char *cmd = NULL; + char *reply = NULL; + int ret = -1; + + if (virAsprintf(&cmd, "block_resize %s %llu", + device, VIR_DIV_UP(size, 1024)) < 0) { + virReportOOMError(); + goto cleanup; + } + + if (qemuMonitorHMPCommand(mon, cmd, &reply) < 0) { + qemuReportError(VIR_ERR_OPERATION_FAILED, + "%s", _("failed to resize block")); + goto cleanup; + } + + if (strstr(reply, "unknown command:")) { + ret = -2; + goto cleanup; + } + + ret = 0; + +cleanup: + VIR_FREE(cmd); + VIR_FREE(reply); + return ret; +} static int qemuMonitorSendVNCPassphrase(qemuMonitorPtr mon ATTRIBUTE_UNUSED, diff --git a/src/qemu/qemu_monitor_text.h b/src/qemu/qemu_monitor_text.h index f32fce0235..cece21cefc 100644 --- a/src/qemu/qemu_monitor_text.h +++ b/src/qemu/qemu_monitor_text.h @@ -78,7 +78,9 @@ int qemuMonitorTextGetBlockStatsParamsNumber(qemuMonitorPtr mon, int qemuMonitorTextGetBlockExtent(qemuMonitorPtr mon, const char *dev_name, unsigned long long *extent); - +int qemuMonitorTextBlockResize(qemuMonitorPtr mon, + const char *device, + unsigned long long size); int qemuMonitorTextSetVNCPassword(qemuMonitorPtr mon, const char *password); int qemuMonitorTextSetPassword(qemuMonitorPtr mon,