From: Marc-André Lureau <marcandre.lureau@redhat.com>
Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Juan Quintela <quintela@redhat.com>
---
migration/savevm.c | 43 +++++++++++++++++++++++++++++++++++++++++++
1 file changed, 43 insertions(+)
diff --git a/migration/savevm.c b/migration/savevm.c
index bc98c2ea6f..2ae65b8088 100644
--- a/migration/savevm.c
+++ b/migration/savevm.c
@@ -217,6 +217,7 @@ typedef struct SaveStateEntry {
void *opaque;
CompatEntry *compat;
int is_ram;
+ bool visited;
} SaveStateEntry;
typedef struct SaveState {
@@ -1787,6 +1788,36 @@ int qemu_save_device_state(QEMUFile *f)
return qemu_file_get_error(f);
}
+static void savevm_reset_visited(void)
+{
+ SaveStateEntry *se;
+
+ QTAILQ_FOREACH(se, &savevm_state.handlers, entry) {
+ se->visited = false;
+ }
+}
+
+static bool loadvm_check_visited(Error **errp)
+{
+ SaveStateEntry *se;
+
+ QTAILQ_FOREACH(se, &savevm_state.handlers, entry) {
+ if (se->ops && se->ops->is_active && !se->ops->is_active(se->opaque)) {
+ continue;
+ }
+ if (se->vmsd && !vmstate_section_needed(se->vmsd, se->opaque)) {
+ continue;
+ }
+ if (!se->visited) {
+ error_setg(errp, "Missing entry '%s' while loading VM", se->idstr);
+ return false;
+ }
+ }
+
+ return true;
+}
+
+
static SaveStateEntry *find_se(const char *idstr, uint32_t instance_id)
{
SaveStateEntry *se;
@@ -2592,6 +2623,11 @@ qemu_loadvm_section_start_full(QEMUFile *f, MigrationIncomingState *mis,
idstr, instance_id);
return -EINVAL;
}
+ if (se->visited) {
+ error_report("error while loading state for instance 0x%"PRIx32" of"
+ " device '%s'", instance_id, idstr);
+ return -EINVAL;
+ }
/* Validate version */
if (version_id > se->version_id) {
@@ -2629,6 +2665,8 @@ qemu_loadvm_section_start_full(QEMUFile *f, MigrationIncomingState *mis,
return -EINVAL;
}
+ se->visited = true;
+
return 0;
}
@@ -2950,7 +2988,12 @@ int qemu_loadvm_state(QEMUFile *f)
cpu_synchronize_all_pre_loadvm();
+ savevm_reset_visited();
ret = qemu_loadvm_state_main(f, mis);
+ if (!loadvm_check_visited(&local_err)) {
+ error_report_err(local_err);
+ return -EINVAL;
+ }
qemu_event_set(&mis->main_thread_load_event);
trace_qemu_loadvm_state_post_main(ret);
--
2.41.0