]> git.proxmox.com Git - qemu.git/commitdiff
qmp: add query-block-jobs
authorStefan Hajnoczi <stefanha@linux.vnet.ibm.com>
Wed, 18 Jan 2012 14:40:49 +0000 (14:40 +0000)
committerKevin Wolf <kwolf@redhat.com>
Thu, 26 Jan 2012 13:49:18 +0000 (14:49 +0100)
Add query-block-jobs, which shows the progress of ongoing block device
operations.

Signed-off-by: Stefan Hajnoczi <stefanha@linux.vnet.ibm.com>
Acked-by: Luiz Capitulino <lcapitulino@redhat.com>
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
blockdev.c
hmp.c
hmp.h
monitor.c
qapi-schema.json
qmp-commands.hx

index d3d6718056d8df06a6d7f5233b6756c4e9f2367c..d026cd4fda7f1673075edf15866a579c9e238eac 100644 (file)
@@ -1006,3 +1006,36 @@ void qmp_block_job_cancel(const char *device, Error **errp)
     trace_qmp_block_job_cancel(job);
     block_job_cancel(job);
 }
+
+static void do_qmp_query_block_jobs_one(void *opaque, BlockDriverState *bs)
+{
+    BlockJobInfoList **prev = opaque;
+    BlockJob *job = bs->job;
+
+    if (job) {
+        BlockJobInfoList *elem;
+        BlockJobInfo *info = g_new(BlockJobInfo, 1);
+        *info = (BlockJobInfo){
+            .type   = g_strdup(job->job_type->job_type),
+            .device = g_strdup(bdrv_get_device_name(bs)),
+            .len    = job->len,
+            .offset = job->offset,
+            .speed  = job->speed,
+        };
+
+        elem = g_new0(BlockJobInfoList, 1);
+        elem->value = info;
+
+        (*prev)->next = elem;
+        *prev = elem;
+    }
+}
+
+BlockJobInfoList *qmp_query_block_jobs(Error **errp)
+{
+    /* Dummy is a fake list element for holding the head pointer */
+    BlockJobInfoList dummy = {};
+    BlockJobInfoList *prev = &dummy;
+    bdrv_iterate(do_qmp_query_block_jobs_one, &prev);
+    return dummy.next;
+}
diff --git a/hmp.c b/hmp.c
index 867c338788a1f407119c49e5316e269df8756489..8ff8c9434e10cbfa73c877f90c214b3b5a53c674 100644 (file)
--- a/hmp.c
+++ b/hmp.c
@@ -509,6 +509,42 @@ void hmp_info_pci(Monitor *mon)
     qapi_free_PciInfoList(info_list);
 }
 
+void hmp_info_block_jobs(Monitor *mon)
+{
+    BlockJobInfoList *list;
+    Error *err = NULL;
+
+    list = qmp_query_block_jobs(&err);
+    assert(!err);
+
+    if (!list) {
+        monitor_printf(mon, "No active jobs\n");
+        return;
+    }
+
+    while (list) {
+        if (strcmp(list->value->type, "stream") == 0) {
+            monitor_printf(mon, "Streaming device %s: Completed %" PRId64
+                           " of %" PRId64 " bytes, speed limit %" PRId64
+                           " bytes/s\n",
+                           list->value->device,
+                           list->value->offset,
+                           list->value->len,
+                           list->value->speed);
+        } else {
+            monitor_printf(mon, "Type %s, device %s: Completed %" PRId64
+                           " of %" PRId64 " bytes, speed limit %" PRId64
+                           " bytes/s\n",
+                           list->value->type,
+                           list->value->device,
+                           list->value->offset,
+                           list->value->len,
+                           list->value->speed);
+        }
+        list = list->next;
+    }
+}
+
 void hmp_quit(Monitor *mon, const QDict *qdict)
 {
     monitor_suspend(mon);
diff --git a/hmp.h b/hmp.h
index eb4ca82853935d011c65368e9e270b0b0836f754..18eecbdcb9c148c8fc31cd6b2497e66df1e8c24c 100644 (file)
--- a/hmp.h
+++ b/hmp.h
@@ -32,6 +32,7 @@ void hmp_info_vnc(Monitor *mon);
 void hmp_info_spice(Monitor *mon);
 void hmp_info_balloon(Monitor *mon);
 void hmp_info_pci(Monitor *mon);
+void hmp_info_block_jobs(Monitor *mon);
 void hmp_quit(Monitor *mon, const QDict *qdict);
 void hmp_stop(Monitor *mon, const QDict *qdict);
 void hmp_system_reset(Monitor *mon, const QDict *qdict);
index 9424c31edcc552d2b0b785958e4ae84a6282e4e8..aadbdcbf3322b7eea728368a20e48107c1ace9d5 100644 (file)
--- a/monitor.c
+++ b/monitor.c
@@ -2317,6 +2317,13 @@ static mon_cmd_t info_cmds[] = {
         .help       = "show block device statistics",
         .mhandler.info = hmp_info_blockstats,
     },
+    {
+        .name       = "block-jobs",
+        .args_type  = "",
+        .params     = "",
+        .help       = "show progress of ongoing block device operations",
+        .mhandler.info = hmp_info_block_jobs,
+    },
     {
         .name       = "registers",
         .args_type  = "",
index 02c4e22571666da6b45ae5624b4e8164f479ed60..3f72c2cfd4d939f87b042b6e0884812e1895f88b 100644 (file)
 ##
 { 'command': 'query-pci', 'returns': ['PciInfo'] }
 
+##
+# @BlockJobInfo:
+#
+# Information about a long-running block device operation.
+#
+# @type: the job type ('stream' for image streaming)
+#
+# @device: the block device name
+#
+# @len: the maximum progress value
+#
+# @offset: the current progress value
+#
+# @speed: the rate limit, bytes per second
+#
+# Since: 1.1
+##
+{ 'type': 'BlockJobInfo',
+  'data': {'type': 'str', 'device': 'str', 'len': 'int',
+           'offset': 'int', 'speed': 'int'} }
+
+##
+# @query-block-jobs:
+#
+# Return information about long-running block device operations.
+#
+# Returns: a list of @BlockJobInfo for each active block job
+#
+# Since: 1.1
+##
+{ 'command': 'query-block-jobs', 'returns': ['BlockJobInfo'] }
+
 ##
 # @quit:
 #
index 0795c5d48da4965eb3cc496f7923bc4a2964ef8e..bd6b6410ad9ce9651b05a0733b255846a89617ff 100644 (file)
@@ -2013,6 +2013,12 @@ EQMP
         .mhandler.cmd_new = qmp_marshal_input_query_balloon,
     },
 
+    {
+        .name       = "query-block-jobs",
+        .args_type  = "",
+        .mhandler.cmd_new = qmp_marshal_input_query_block_jobs,
+    },
+
     {
         .name       = "qom-list",
         .args_type  = "path:s",