[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 1/4] savevm: refactor qemu_loadvm_state().
From: |
Yoshiaki Tamura |
Subject: |
[Qemu-devel] [PATCH 1/4] savevm: refactor qemu_loadvm_state(). |
Date: |
Thu, 3 Jun 2010 16:22:24 +0900 |
Split qemu_loadvm_state(), and introduce
qemu_loadvm_state_{begin,iterate,complete,async}.
qemu_loadvm_state_async() is a function to handle a single incoming
section.
Signed-off-by: Yoshiaki Tamura <address@hidden>
---
savevm.c | 206 +++++++++++++++++++++++++++++++++++++++++++-------------------
sysemu.h | 2 +
2 files changed, 146 insertions(+), 62 deletions(-)
diff --git a/savevm.c b/savevm.c
index dc20390..aa4f98c 100644
--- a/savevm.c
+++ b/savevm.c
@@ -1005,6 +1005,8 @@ typedef struct SaveStateEntry {
static QTAILQ_HEAD(savevm_handlers, SaveStateEntry) savevm_handlers =
QTAILQ_HEAD_INITIALIZER(savevm_handlers);
+static QLIST_HEAD(, LoadStateEntry) loadvm_handlers =
+ QLIST_HEAD_INITIALIZER(loadvm_handlers);
static int global_section_id;
static int calculate_new_instance_id(const char *idstr)
@@ -1460,14 +1462,9 @@ typedef struct LoadStateEntry {
int version_id;
} LoadStateEntry;
-int qemu_loadvm_state(QEMUFile *f)
+int qemu_loadvm_state_begin(QEMUFile *f)
{
- QLIST_HEAD(, LoadStateEntry) loadvm_handlers =
- QLIST_HEAD_INITIALIZER(loadvm_handlers);
- LoadStateEntry *le, *new_le;
- uint8_t section_type;
unsigned int v;
- int ret;
v = qemu_get_be32(f);
if (v != QEMU_VM_FILE_MAGIC)
@@ -1481,73 +1478,157 @@ int qemu_loadvm_state(QEMUFile *f)
if (v != QEMU_VM_FILE_VERSION)
return -ENOTSUP;
- while ((section_type = qemu_get_byte(f)) != QEMU_VM_EOF) {
- uint32_t instance_id, version_id, section_id;
- SaveStateEntry *se;
- char idstr[257];
- int len;
+ return 0;
+}
- switch (section_type) {
- case QEMU_VM_SECTION_START:
- case QEMU_VM_SECTION_FULL:
- /* Read section start */
- section_id = qemu_get_be32(f);
- len = qemu_get_byte(f);
- qemu_get_buffer(f, (uint8_t *)idstr, len);
- idstr[len] = 0;
- instance_id = qemu_get_be32(f);
- version_id = qemu_get_be32(f);
-
- /* Find savevm section */
- se = find_se(idstr, instance_id);
- if (se == NULL) {
- fprintf(stderr, "Unknown savevm section or instance '%s'
%d\n", idstr, instance_id);
- ret = -EINVAL;
- goto out;
- }
+static int qemu_loadvm_state_iterate(QEMUFile *f)
+{
+ LoadStateEntry *le;
+ uint32_t section_id;
+ int ret;
- /* Validate version */
- if (version_id > se->version_id) {
- fprintf(stderr, "savevm: unsupported version %d for '%s'
v%d\n",
- version_id, idstr, se->version_id);
- ret = -EINVAL;
- goto out;
- }
+ section_id = qemu_get_be32(f);
+
+ QLIST_FOREACH(le, &loadvm_handlers, entry) {
+ if (le->section_id == section_id) {
+ break;
+ }
+ }
+ if (le == NULL) {
+ fprintf(stderr, "Unknown savevm section %d\n", section_id);
+ return -EINVAL;
+ }
+
+ ret = vmstate_load(f, le->se, le->version_id);
+ if (ret < 0) {
+ fprintf(stderr, "qemu: warning: error while loading state section id
%d\n",
+ section_id);
+ return ret;
+ }
+
+ return 0;
+}
+
+static int qemu_loadvm_state_complete(QEMUFile *f)
+{
+ LoadStateEntry *le;
+ uint32_t instance_id, version_id, section_id;
+ SaveStateEntry *se;
+ char idstr[257];
+ int ret = -1, len;
+
+ /* Read section start */
+ section_id = qemu_get_be32(f);
+ len = qemu_get_byte(f);
+ qemu_get_buffer(f, (uint8_t *)idstr, len);
+ idstr[len] = 0;
+ instance_id = qemu_get_be32(f);
+ version_id = qemu_get_be32(f);
+
+ /* Find savevm section */
+ se = find_se(idstr, instance_id);
+ if (se == NULL) {
+ fprintf(stderr, "Unknown savevm section or instance '%s' %d\n", idstr,
instance_id);
+ return -EINVAL;
+ }
+
+ /* Validate version */
+ if (version_id > se->version_id) {
+ fprintf(stderr, "savevm: unsupported version %d for '%s' v%d\n",
+ version_id, idstr, se->version_id);
+ return -EINVAL;
+ }
+
+ /* Add entry */
+ le = qemu_mallocz(sizeof(*le));
+
+ le->se = se;
+ le->section_id = section_id;
+ le->version_id = version_id;
+ QLIST_INSERT_HEAD(&loadvm_handlers, le, entry);
+
+ ret = vmstate_load(f, le->se, le->version_id);
+ if (ret < 0) {
+ fprintf(stderr, "qemu: warning: error while loading state for instance
0x%x of device '%s'\n",
+ instance_id, idstr);
+ return ret;
+ }
+
+ return 0;
+}
- /* Add entry */
- le = qemu_mallocz(sizeof(*le));
+int qemu_loadvm_state_async(QEMUFile *f)
+{
+ LoadStateEntry *le, *new_le;
+ int ret;
+ uint8_t section_type;
- le->se = se;
- le->section_id = section_id;
- le->version_id = version_id;
- QLIST_INSERT_HEAD(&loadvm_handlers, le, entry);
+ section_type = qemu_get_byte(f);
+ switch (section_type) {
+ case QEMU_VM_SECTION_START:
+ case QEMU_VM_SECTION_FULL:
+ ret = qemu_loadvm_state_complete(f);
+ if (ret < 0) {
+ goto out_free;
+ }
+ break;
+ case QEMU_VM_SECTION_PART:
+ case QEMU_VM_SECTION_END:
+ ret = qemu_loadvm_state_iterate(f);
+ if (ret < 0) {
+ goto out_free;
+ }
+ break;
+ case QEMU_VM_EOF:
+ cpu_synchronize_all_post_init();
+ break;
+ default:
+ fprintf(stderr, "Unknown savevm section type %d\n", section_type);
+ ret = -EINVAL;
+ goto out_free;
+ }
+
+ ret = section_type;
+ if (ret != QEMU_VM_EOF) {
+ goto out;
+ }
- ret = vmstate_load(f, le->se, le->version_id);
+out_free:
+ QLIST_FOREACH_SAFE(le, &loadvm_handlers, entry, new_le) {
+ QLIST_REMOVE(le, entry);
+ qemu_free(le);
+ }
+out:
+ if (qemu_file_has_error(f)) {
+ ret = -EIO;
+ }
+
+ return ret;
+}
+
+int qemu_loadvm_state(QEMUFile *f)
+{
+ LoadStateEntry *le, *new_le;
+ int ret;
+ uint8_t section_type;
+
+ ret = qemu_loadvm_state_begin(f);
+ if (ret < 0)
+ goto out;
+
+ while ((section_type = qemu_get_byte(f)) != QEMU_VM_EOF) {
+ switch (section_type) {
+ case QEMU_VM_SECTION_START:
+ case QEMU_VM_SECTION_FULL:
+ ret = qemu_loadvm_state_complete(f);
if (ret < 0) {
- fprintf(stderr, "qemu: warning: error while loading state for
instance 0x%x of device '%s'\n",
- instance_id, idstr);
goto out;
}
break;
case QEMU_VM_SECTION_PART:
case QEMU_VM_SECTION_END:
- section_id = qemu_get_be32(f);
-
- QLIST_FOREACH(le, &loadvm_handlers, entry) {
- if (le->section_id == section_id) {
- break;
- }
- }
- if (le == NULL) {
- fprintf(stderr, "Unknown savevm section %d\n", section_id);
- ret = -EINVAL;
- goto out;
- }
-
- ret = vmstate_load(f, le->se, le->version_id);
+ ret = qemu_loadvm_state_iterate(f);
if (ret < 0) {
- fprintf(stderr, "qemu: warning: error while loading state
section id %d\n",
- section_id);
goto out;
}
break;
@@ -1568,8 +1649,9 @@ out:
qemu_free(le);
}
- if (qemu_file_has_error(f))
+ if (qemu_file_has_error(f)) {
ret = -EIO;
+ }
return ret;
}
diff --git a/sysemu.h b/sysemu.h
index 879446a..c576840 100644
--- a/sysemu.h
+++ b/sysemu.h
@@ -69,6 +69,8 @@ int qemu_savevm_state_begin(Monitor *mon, QEMUFile *f, int
blk_enable,
int qemu_savevm_state_iterate(Monitor *mon, QEMUFile *f);
int qemu_savevm_state_complete(Monitor *mon, QEMUFile *f);
void qemu_savevm_state_cancel(Monitor *mon, QEMUFile *f);
+int qemu_loadvm_state_begin(QEMUFile *f);
+int qemu_loadvm_state_async(QEMUFile *f);
int qemu_loadvm_state(QEMUFile *f);
#ifdef _WIN32
--
1.7.0.31.g1df487
[Qemu-devel] [PATCH 3/4] arch_init: calculate transferred bytes at ram_load()., Yoshiaki Tamura, 2010/06/03
[Qemu-devel] [PATCH 2/4] migration-tcp: add support for asynchronous incoming migration., Yoshiaki Tamura, 2010/06/03