[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PATCH v3 13/17] migration/snapshot: Block layer support in qemu-snapsho
From: |
nikita . lapshin |
Subject: |
[PATCH v3 13/17] migration/snapshot: Block layer support in qemu-snapshot |
Date: |
Thu, 16 Jun 2022 13:28:07 +0300 |
From: Nikita Lapshin <nikita.lapshin@openvz.org>
This commit enables few functions to simplify block layer work
for qemu-snapshot tool.
Signed-off-by: Nikita Lapshin <nikita.lapshin@openvz.org>
---
include/qemu-snapshot.h | 3 +
migration/meson.build | 1 +
migration/qemu-snapshot-io.c | 112 +++++++++++++++++++++++++++++++++++
3 files changed, 116 insertions(+)
create mode 100644 migration/qemu-snapshot-io.c
diff --git a/include/qemu-snapshot.h b/include/qemu-snapshot.h
index 8e548e7630..be2557f6a0 100644
--- a/include/qemu-snapshot.h
+++ b/include/qemu-snapshot.h
@@ -62,4 +62,7 @@ StateLoadCtx *get_load_context(void);
int coroutine_fn save_state_main(StateSaveCtx *s);
int coroutine_fn load_state_main(StateLoadCtx *s);
+QEMUFile *qemu_fopen_bdrv_vmstate(BlockDriverState *bs, int is_writable);
+void qemu_fsplice(QEMUFile *f_dst, QEMUFile *f_src, size_t size);
+size_t qemu_fsplice_tail(QEMUFile *f_dst, QEMUFile *f_src);
#endif /* QEMU_SNAPSHOT_H */
diff --git a/migration/meson.build b/migration/meson.build
index 13498a6db3..3a04576c30 100644
--- a/migration/meson.build
+++ b/migration/meson.build
@@ -9,6 +9,7 @@ migration_files = files(
'yank_functions.c',
'migration.c',
'qemu-snapshot.c',
+ 'qemu-snapshot-io.c'
)
softmmu_ss.add(migration_files)
diff --git a/migration/qemu-snapshot-io.c b/migration/qemu-snapshot-io.c
new file mode 100644
index 0000000000..904cb92c84
--- /dev/null
+++ b/migration/qemu-snapshot-io.c
@@ -0,0 +1,112 @@
+/*
+ * QEMU External Snapshot Utility
+ *
+ * Copyright Virtuozzo GmbH, 2021
+ *
+ * Authors:
+ * Andrey Gruzdev <andrey.gruzdev@virtuozzo.com>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or
+ * later. See the COPYING file in the top-level directory.
+ */
+
+#include "qemu/osdep.h"
+#include "qemu/coroutine.h"
+#include "sysemu/block-backend.h"
+#include "migration/qemu-file.h"
+#include "qemu-snapshot.h"
+
+static ssize_t bdrv_vmstate_get_buffer(void *opaque, uint8_t *buf, int64_t pos,
+ size_t size, Error **errp)
+{
+ return bdrv_load_vmstate((BlockDriverState *) opaque, buf, pos, size);
+}
+
+static ssize_t bdrv_vmstate_writev_buffer(void *opaque, struct iovec *iov,
+ int iovcnt, int64_t pos, Error **errp)
+{
+ QEMUIOVector qiov;
+ int res;
+
+ qemu_iovec_init_external(&qiov, iov, iovcnt);
+
+ res = bdrv_writev_vmstate((BlockDriverState *) opaque, &qiov, pos);
+ if (res < 0) {
+ return res;
+ }
+
+ return qiov.size;
+}
+
+static int bdrv_vmstate_fclose(void *opaque, Error **errp)
+{
+ return bdrv_flush((BlockDriverState *) opaque);
+}
+
+static const QEMUFileOps bdrv_vmstate_read_ops = {
+ .get_buffer = bdrv_vmstate_get_buffer,
+ .close = bdrv_vmstate_fclose,
+};
+
+static const QEMUFileOps bdrv_vmstate_write_ops = {
+ .writev_buffer = bdrv_vmstate_writev_buffer,
+ .close = bdrv_vmstate_fclose,
+};
+
+/* Create QEMUFile to access vmstate stream on QCOW2 image */
+QEMUFile *qemu_fopen_bdrv_vmstate(BlockDriverState *bs, int is_writable)
+{
+ if (is_writable) {
+ return qemu_fopen_ops(bs, &bdrv_vmstate_write_ops, true);
+ }
+
+ return qemu_fopen_ops(bs, &bdrv_vmstate_read_ops, true);
+}
+
+/* Move number of bytes from the source QEMUFile to destination */
+void qemu_fsplice(QEMUFile *f_dst, QEMUFile *f_src, size_t size)
+{
+ size_t rest = size;
+
+ while (rest) {
+ uint8_t *ptr = NULL;
+ size_t req_size;
+ size_t count;
+
+ req_size = MIN(rest, INPLACE_READ_MAX);
+ count = qemu_peek_buffer(f_src, &ptr, req_size, 0);
+ qemu_file_skip(f_src, count);
+
+ qemu_put_buffer(f_dst, ptr, count);
+ rest -= count;
+ }
+}
+
+/*
+ * Move data from source QEMUFile to destination
+ * until EOF is reached on source.
+ */
+size_t qemu_fsplice_tail(QEMUFile *f_dst, QEMUFile *f_src)
+{
+ bool eof = false;
+ size_t res = 0;
+
+ while (!eof) {
+ const size_t size = INPLACE_READ_MAX;
+ uint8_t *buffer = NULL;
+ size_t count;
+
+ count = qemu_peek_buffer(f_src, &buffer, size, 0);
+ qemu_file_skip(f_src, count);
+
+ /* Reached EOF on source? */
+ if (count != size) {
+ eof = true;
+ }
+
+ qemu_put_buffer(f_dst, buffer, count);
+ res += count;
+ }
+
+ return res;
+}
--
2.31.1
- [PATCH v3 01/17] migration: Implemented new parameter stream_content, (continued)
- [PATCH v3 01/17] migration: Implemented new parameter stream_content, nikita . lapshin, 2022/06/16
- [PATCH v3 02/17] migration: should_skip() implemented, nikita . lapshin, 2022/06/16
- [PATCH v3 03/17] migration: Add vmstate part of migration stream, nikita . lapshin, 2022/06/16
- [PATCH v3 05/17] migration: Add block part of migration stream, nikita . lapshin, 2022/06/16
- [PATCH v3 06/17] migration: Add RAM part of migration stream, nikita . lapshin, 2022/06/16
- [PATCH v3 07/17] migration: analyze-migration script changed, nikita . lapshin, 2022/06/16
- [PATCH v3 08/17] migration: Test for RAM and vmstate parts, nikita . lapshin, 2022/06/16
- [PATCH v3 11/17] migration/qemu-file: Fix qemu_ftell() for non-writable file, nikita . lapshin, 2022/06/16
- [PATCH v3 13/17] migration/snapshot: Block layer support in qemu-snapshot,
nikita . lapshin <=
- [PATCH v3 14/17] migration/snpashot: Implement API for RAMBlock, nikita . lapshin, 2022/06/16
- [PATCH v3 04/17] migration: Add dirty-bitmaps part of migration stream, nikita . lapshin, 2022/06/16
- [PATCH v3 09/17] migration/snapshot: Introduce qemu-snapshot tool, nikita . lapshin, 2022/06/16
- [PATCH v3 10/17] migration/snapshot: Build changes for qemu-snapshot-tool, nikita . lapshin, 2022/06/16
- [PATCH v3 12/17] migration/snapshot: Move RAM_SAVE_FLAG_xxx defines to migration/ram.h, nikita . lapshin, 2022/06/16
- [PATCH v3 16/17] migration/snapshot: Precopy load implemented, nikita . lapshin, 2022/06/16
- [PATCH v3 15/17] migration/snapshot: Save part implement, nikita . lapshin, 2022/06/16
- [PATCH v3 17/17] migration/snapshot: Postcopy load implemented, nikita . lapshin, 2022/06/16