提交 dba433c0 编写于 作者: P Paolo Bonzini 提交者: Juan Quintela

migration: simplify error handling

Always use qemu_file_get_error to detect errors, since that is how
QEMUFile itself drops I/O after an error occurs.  There is no need
to propagate and check return values all the time.

Also remove the "complete" member, since we know that it is set (via
migrate_fd_cleanup) only when the state changes.
Reviewed-by: NOrit Wasserman <owasserm@redhat.com>
Reviewed-by: NJuan Quintela <quintela@redhat.com>
Signed-off-by: NPaolo Bonzini <pbonzini@redhat.com>
Signed-off-by: NJuan Quintela <quintela@redhat.com>
上级 63dfbd7e
...@@ -54,7 +54,6 @@ struct MigrationState ...@@ -54,7 +54,6 @@ struct MigrationState
int64_t dirty_bytes_rate; int64_t dirty_bytes_rate;
bool enabled_capabilities[MIGRATION_CAPABILITY_MAX]; bool enabled_capabilities[MIGRATION_CAPABILITY_MAX];
int64_t xbzrle_cache_size; int64_t xbzrle_cache_size;
bool complete;
}; };
void process_incoming_migration(QEMUFile *f); void process_incoming_migration(QEMUFile *f);
......
...@@ -525,6 +525,10 @@ static void buffered_flush(MigrationState *s) ...@@ -525,6 +525,10 @@ static void buffered_flush(MigrationState *s)
DPRINTF("flushing %zu byte(s) of data\n", s->buffer_size); DPRINTF("flushing %zu byte(s) of data\n", s->buffer_size);
if (qemu_file_get_error(s->file)) {
s->buffer_size = 0;
return;
}
qemu_fflush(s->file); qemu_fflush(s->file);
while (s->bytes_xfer < s->xfer_limit && offset < s->buffer_size) { while (s->bytes_xfer < s->xfer_limit && offset < s->buffer_size) {
...@@ -592,7 +596,6 @@ static int buffered_close(void *opaque) ...@@ -592,7 +596,6 @@ static int buffered_close(void *opaque)
while (!qemu_file_get_error(s->file) && s->buffer_size) { while (!qemu_file_get_error(s->file) && s->buffer_size) {
buffered_flush(s); buffered_flush(s);
} }
s->complete = true;
return migrate_fd_close(s); return migrate_fd_close(s);
} }
...@@ -656,37 +659,21 @@ static void *buffered_file_thread(void *opaque) ...@@ -656,37 +659,21 @@ static void *buffered_file_thread(void *opaque)
int64_t sleep_time = 0; int64_t sleep_time = 0;
int64_t max_size = 0; int64_t max_size = 0;
bool last_round = false; bool last_round = false;
int ret;
qemu_mutex_lock_iothread(); qemu_mutex_lock_iothread();
DPRINTF("beginning savevm\n"); DPRINTF("beginning savevm\n");
ret = qemu_savevm_state_begin(s->file, &s->params); qemu_savevm_state_begin(s->file, &s->params);
qemu_mutex_unlock_iothread();
while (ret >= 0) { while (s->state == MIG_STATE_ACTIVE) {
int64_t current_time; int64_t current_time;
uint64_t pending_size; uint64_t pending_size;
qemu_mutex_lock_iothread();
if (s->state != MIG_STATE_ACTIVE) {
DPRINTF("put_ready returning because of non-active state\n");
qemu_mutex_unlock_iothread();
break;
}
if (s->complete) {
qemu_mutex_unlock_iothread();
break;
}
if (s->bytes_xfer < s->xfer_limit) { if (s->bytes_xfer < s->xfer_limit) {
DPRINTF("iterate\n"); DPRINTF("iterate\n");
pending_size = qemu_savevm_state_pending(s->file, max_size); pending_size = qemu_savevm_state_pending(s->file, max_size);
DPRINTF("pending size %lu max %lu\n", pending_size, max_size); DPRINTF("pending size %lu max %lu\n", pending_size, max_size);
if (pending_size && pending_size >= max_size) { if (pending_size && pending_size >= max_size) {
ret = qemu_savevm_state_iterate(s->file); qemu_savevm_state_iterate(s->file);
if (ret < 0) {
qemu_mutex_unlock_iothread();
break;
}
} else { } else {
int old_vm_running = runstate_is_running(); int old_vm_running = runstate_is_running();
int64_t start_time, end_time; int64_t start_time, end_time;
...@@ -695,13 +682,8 @@ static void *buffered_file_thread(void *opaque) ...@@ -695,13 +682,8 @@ static void *buffered_file_thread(void *opaque)
start_time = qemu_get_clock_ms(rt_clock); start_time = qemu_get_clock_ms(rt_clock);
qemu_system_wakeup_request(QEMU_WAKEUP_REASON_OTHER); qemu_system_wakeup_request(QEMU_WAKEUP_REASON_OTHER);
vm_stop_force_state(RUN_STATE_FINISH_MIGRATE); vm_stop_force_state(RUN_STATE_FINISH_MIGRATE);
ret = qemu_savevm_state_complete(s->file); qemu_savevm_state_complete(s->file);
if (ret < 0) { migrate_fd_completed(s);
qemu_mutex_unlock_iothread();
break;
} else {
migrate_fd_completed(s);
}
end_time = qemu_get_clock_ms(rt_clock); end_time = qemu_get_clock_ms(rt_clock);
s->total_time = end_time - s->total_time; s->total_time = end_time - s->total_time;
s->downtime = end_time - start_time; s->downtime = end_time - start_time;
...@@ -740,12 +722,13 @@ static void *buffered_file_thread(void *opaque) ...@@ -740,12 +722,13 @@ static void *buffered_file_thread(void *opaque)
sleep_time += qemu_get_clock_ms(rt_clock) - current_time; sleep_time += qemu_get_clock_ms(rt_clock) - current_time;
} }
buffered_flush(s); buffered_flush(s);
ret = qemu_file_get_error(s->file); qemu_mutex_lock_iothread();
if (qemu_file_get_error(s->file)) {
migrate_fd_error(s);
}
} }
if (ret < 0) { qemu_mutex_unlock_iothread();
migrate_fd_error(s);
}
g_free(s->buffer); g_free(s->buffer);
return NULL; return NULL;
} }
...@@ -770,7 +753,6 @@ void migrate_fd_connect(MigrationState *s) ...@@ -770,7 +753,6 @@ void migrate_fd_connect(MigrationState *s)
s->expected_downtime = max_downtime/1000000; s->expected_downtime = max_downtime/1000000;
s->xfer_limit = s->bandwidth_limit / XFER_LIMIT_RATIO; s->xfer_limit = s->bandwidth_limit / XFER_LIMIT_RATIO;
s->complete = false;
s->file = qemu_fopen_ops(s, &buffered_file_ops); s->file = qemu_fopen_ops(s, &buffered_file_ops);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册