* [PATCH 00/30] move to new migration APIs
@ 2026-08-25 21:37 Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 01/30] tests/unit/test-vmstate: " Vladimir Sementsov-Ogievskiy
` (29 more replies)
0 siblings, 30 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov
Hi all!
That's a new version for old
[RFC 00/22] migration: convert vmstate_load/save_state
after the core patches converting migration code
are already merged into master.
Let's now convert the whole code base.
Vladimir Sementsov-Ogievskiy (30):
tests/unit/test-vmstate: move to new migration APIs
ui/vdagent: move to new migration APIs
hw/virtio: extra state: move to new migration APIs
hw/virtio: config save/load: move to new migration APIs
hw/virtio: make virtio_save() and virtio_load() static
hw/virtio: remaining: move to new migration APIs
hw/s390x/virtio-ccw.c: move to new migration APIs
hw/scsi/spapr_vscsi: move to new migration APIs
hw/scsi/scsi-bus.c: use new migration APIs
hw/vfio/pci: move to new migration APIs
hw/pci/pci: move to new migration APIs
hw/pci/msix.c: use new migration APIs
hw/pci/shpc.c: use new migration APIs
hw/display/virtio-gpu: move to new migration APIs
hw/net/virtio-net.c: use new migration APIs
hw/nvram/eeprom93xx.c: use new migration APIs
hw/nvram/fw_cfg.c: use new migration APIs
hw/usb/redirect.c: move to new migration APIs
alpha/machine: move to new migration APIs
avr/machine: move to new migration APIs
or1k/machine: move to new migration APIs
microblaze/machine: move to new migration APIs
hppa/machine: move to new migration APIs
sparc/machine: move to new migration APIs
ppc/machine: move to new migration APIs
mips/machine: move to new migration APIs
arm/machine: move to new migration APIs
migration/vmstate-types: convert vmstate_info_g_byte_array to new APIs
migration: VMStateInfo: remove old .get / .set handlers
migration: finally drop vmstate_save/load_state() functions
hw/display/virtio-gpu.c | 99 +++++++++++----------
hw/net/virtio-net.c | 133 ++++++++++++++--------------
hw/nvram/eeprom93xx.c | 17 ++--
hw/nvram/fw_cfg.c | 24 ++---
hw/pci/msix.c | 17 ++--
hw/pci/pci.c | 85 +++++++++---------
hw/pci/shpc.c | 20 +++--
hw/s390x/virtio-ccw.c | 40 ++++-----
hw/scsi/scsi-bus.c | 17 ++--
hw/scsi/spapr_vscsi.c | 9 +-
hw/usb/redirect.c | 59 +++++++------
hw/vfio/pci.c | 14 ++-
hw/virtio/vhost-user-fs.c | 68 +++++++-------
hw/virtio/virtio-mmio.c | 31 +++----
hw/virtio/virtio-pci.c | 45 +++++-----
hw/virtio/virtio.c | 157 +++++++++++++++++----------------
include/hw/pci/pci.h | 4 +-
include/hw/virtio/virtio-bus.h | 8 +-
include/hw/virtio/virtio.h | 4 -
include/migration/vmstate.h | 17 ----
migration/vmstate-types.c | 17 ++--
migration/vmstate.c | 32 +------
target/alpha/machine.c | 17 ++--
target/arm/machine.c | 107 +++++++++++-----------
target/avr/machine.c | 50 ++++++-----
target/hppa/machine.c | 34 +++----
target/microblaze/machine.c | 17 ++--
target/mips/system/machine.c | 49 +++++-----
target/or1k/machine.c | 17 ++--
target/ppc/machine.c | 80 ++++++++---------
target/sparc/machine.c | 68 +++++++-------
tests/unit/test-vmstate.c | 118 +++++++------------------
ui/vdagent.c | 38 ++++----
33 files changed, 710 insertions(+), 802 deletions(-)
--
2.43.0
^ permalink raw reply [flat|nested] 39+ messages in thread
* [PATCH 01/30] tests/unit/test-vmstate: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-29 5:55 ` Akihiko Odaki
2026-09-03 17:12 ` Fabiano Rosas
2026-08-25 21:37 ` [PATCH 02/30] ui/vdagent: " Vladimir Sementsov-Ogievskiy
` (28 subsequent siblings)
29 siblings, 2 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Juraj Marcin,
Alexander Mikhalitsyn, Akihiko Odaki
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
tests/unit/test-vmstate.c | 118 ++++++++++----------------------------
1 file changed, 30 insertions(+), 88 deletions(-)
diff --git a/tests/unit/test-vmstate.c b/tests/unit/test-vmstate.c
index df1fb4c7780..23f31730703 100644
--- a/tests/unit/test-vmstate.c
+++ b/tests/unit/test-vmstate.c
@@ -67,14 +67,9 @@ static QEMUFile *open_test_file(bool write)
static void save_vmstate(const VMStateDescription *desc, void *obj)
{
QEMUFile *f = open_test_file(true);
- Error *local_err = NULL;
/* Save file with vmstate */
- int ret = vmstate_save_state(f, desc, obj, NULL, &local_err);
- if (ret) {
- error_report_err(local_err);
- }
- g_assert(!ret);
+ vmstate_save_vmsd(f, desc, obj, NULL, &error_abort);
qemu_put_byte(f, QEMU_VM_EOF);
g_assert(!qemu_file_get_error(f));
qemu_fclose(f);
@@ -112,7 +107,6 @@ static int load_vmstate_one(const VMStateDescription *desc, void *obj,
int version, const uint8_t *wire, size_t size)
{
QEMUFile *f;
- int ret;
Error *local_err = NULL;
f = open_test_file(true);
@@ -120,15 +114,16 @@ static int load_vmstate_one(const VMStateDescription *desc, void *obj,
qemu_fclose(f);
f = open_test_file(false);
- ret = vmstate_load_state(f, desc, obj, version, &local_err);
- if (ret) {
+ if (!vmstate_load_vmsd(f, desc, obj, version, &local_err)) {
error_report_err(local_err);
g_assert(qemu_file_get_error(f));
- } else{
- g_assert(!qemu_file_get_error(f));
+ qemu_fclose(f);
+ return -EINVAL;
}
+
+ g_assert(!qemu_file_get_error(f));
qemu_fclose(f);
- return ret;
+ return 0;
}
@@ -362,8 +357,6 @@ static const VMStateDescription vmstate_versioned = {
static void test_load_v1(void)
{
- Error *local_err = NULL;
- int ret;
uint8_t buf[] = {
0, 0, 0, 10, /* a */
0, 0, 0, 30, /* c */
@@ -374,10 +367,7 @@ static void test_load_v1(void)
QEMUFile *loading = open_test_file(false);
TestStruct obj = { .b = 200, .e = 500, .f = 600 };
- ret = vmstate_load_state(loading, &vmstate_versioned, &obj, 1, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(loading, &vmstate_versioned, &obj, 1, &error_abort);
g_assert(!qemu_file_get_error(loading));
g_assert_cmpint(obj.a, ==, 10);
g_assert_cmpint(obj.b, ==, 200);
@@ -390,8 +380,6 @@ static void test_load_v1(void)
static void test_load_v2(void)
{
- Error *local_err = NULL;
- int ret;
uint8_t buf[] = {
0, 0, 0, 10, /* a */
0, 0, 0, 20, /* b */
@@ -405,10 +393,7 @@ static void test_load_v2(void)
QEMUFile *loading = open_test_file(false);
TestStruct obj;
- ret = vmstate_load_state(loading, &vmstate_versioned, &obj, 2, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(loading, &vmstate_versioned, &obj, 2, &error_abort);
g_assert_cmpint(obj.a, ==, 10);
g_assert_cmpint(obj.b, ==, 20);
g_assert_cmpint(obj.c, ==, 30);
@@ -442,16 +427,10 @@ static const VMStateDescription vmstate_skipping = {
static void test_save_noskip(void)
{
- Error *local_err = NULL;
QEMUFile *fsave = open_test_file(true);
TestStruct obj = { .a = 1, .b = 2, .c = 3, .d = 4, .e = 5, .f = 6,
.skip_c_e = false };
- int ret = vmstate_save_state(fsave, &vmstate_skipping, &obj, NULL,
- &local_err);
- if (ret) {
- error_report_err(local_err);
- }
- g_assert(!ret);
+ vmstate_save_vmsd(fsave, &vmstate_skipping, &obj, NULL, &error_abort);
g_assert(!qemu_file_get_error(fsave));
uint8_t expected[] = {
@@ -469,16 +448,10 @@ static void test_save_noskip(void)
static void test_save_skip(void)
{
- Error *local_err = NULL;
QEMUFile *fsave = open_test_file(true);
TestStruct obj = { .a = 1, .b = 2, .c = 3, .d = 4, .e = 5, .f = 6,
.skip_c_e = true };
- int ret = vmstate_save_state(fsave, &vmstate_skipping, &obj, NULL,
- &local_err);
- if (ret) {
- error_report_err(local_err);
- }
- g_assert(!ret);
+ vmstate_save_vmsd(fsave, &vmstate_skipping, &obj, NULL, &error_abort);
g_assert(!qemu_file_get_error(fsave));
uint8_t expected[] = {
@@ -494,8 +467,6 @@ static void test_save_skip(void)
static void test_load_noskip(void)
{
- Error *local_err = NULL;
- int ret;
uint8_t buf[] = {
0, 0, 0, 10, /* a */
0, 0, 0, 20, /* b */
@@ -509,10 +480,7 @@ static void test_load_noskip(void)
QEMUFile *loading = open_test_file(false);
TestStruct obj = { .skip_c_e = false };
- ret = vmstate_load_state(loading, &vmstate_skipping, &obj, 2, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(loading, &vmstate_skipping, &obj, 2, &error_abort);
g_assert(!qemu_file_get_error(loading));
g_assert_cmpint(obj.a, ==, 10);
g_assert_cmpint(obj.b, ==, 20);
@@ -525,8 +493,6 @@ static void test_load_noskip(void)
static void test_load_skip(void)
{
- Error *local_err = NULL;
- int ret;
uint8_t buf[] = {
0, 0, 0, 10, /* a */
0, 0, 0, 20, /* b */
@@ -538,10 +504,7 @@ static void test_load_skip(void)
QEMUFile *loading = open_test_file(false);
TestStruct obj = { .skip_c_e = true, .c = 300, .e = 500 };
- ret = vmstate_load_state(loading, &vmstate_skipping, &obj, 2, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(loading, &vmstate_skipping, &obj, 2, &error_abort);
g_assert(!qemu_file_get_error(loading));
g_assert_cmpint(obj.a, ==, 10);
g_assert_cmpint(obj.b, ==, 20);
@@ -863,8 +826,6 @@ static void test_save_q(void)
static void test_load_q(void)
{
- int ret;
- Error *local_err = NULL;
TestQtailq obj_q = {
.i16 = -512,
.i32 = 70000,
@@ -894,10 +855,7 @@ static void test_load_q(void)
TestQtailq tgt;
QTAILQ_INIT(&tgt.q);
- ret = vmstate_load_state(fload, &vmstate_q, &tgt, 1, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(fload, &vmstate_q, &tgt, 1, &error_abort);
char eof = qemu_get_byte(fload);
g_assert(!qemu_file_get_error(fload));
g_assert_cmpint(tgt.i16, ==, obj_q.i16);
@@ -1015,29 +973,29 @@ static void destroy_domain(gpointer data)
g_free(domain);
}
-static int domain_preload(void *opaque)
+static bool domain_preload(void *opaque, Error **errp)
{
TestGTreeDomain *domain = opaque;
domain->mappings = g_tree_new_full((GCompareDataFunc)interval_cmp,
NULL, g_free, g_free);
- return 0;
+ return true;
}
-static int iommu_preload(void *opaque)
+static bool iommu_preload(void *opaque, Error **errp)
{
TestGTreeIOMMU *iommu = opaque;
iommu->domains = g_tree_new_full((GCompareDataFunc)int_cmp,
NULL, NULL, destroy_domain);
- return 0;
+ return true;
}
static const VMStateDescription vmstate_domain = {
.name = "domain",
.version_id = 1,
.minimum_version_id = 1,
- .pre_load = domain_preload,
+ .pre_load_errp = domain_preload,
.fields = (const VMStateField[]) {
VMSTATE_INT32(id, TestGTreeDomain),
VMSTATE_GTREE_V(mappings, TestGTreeDomain, 1,
@@ -1073,7 +1031,7 @@ static const VMStateDescription vmstate_iommu = {
.name = "iommu",
.version_id = 1,
.minimum_version_id = 1,
- .pre_load = iommu_preload,
+ .pre_load_errp = iommu_preload,
.fields = (const VMStateField[]) {
VMSTATE_INT32(id, TestGTreeIOMMU),
VMSTATE_GTREE_DIRECT_KEY_V(domains, TestGTreeIOMMU, 1,
@@ -1239,8 +1197,6 @@ static void diff_iommu(TestGTreeIOMMU *iommu1, TestGTreeIOMMU *iommu2)
static void test_gtree_load_domain(void)
{
- Error *local_err = NULL;
- int ret;
TestGTreeDomain *dest_domain = g_new0(TestGTreeDomain, 1);
TestGTreeDomain *orig_domain = create_first_domain();
QEMUFile *fload, *fsave;
@@ -1253,11 +1209,7 @@ static void test_gtree_load_domain(void)
fload = open_test_file(false);
- ret = vmstate_load_state(fload, &vmstate_domain, dest_domain, 1,
- &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(fload, &vmstate_domain, dest_domain, 1, &error_abort);
eof = qemu_get_byte(fload);
g_assert(!qemu_file_get_error(fload));
g_assert_cmpint(orig_domain->id, ==, dest_domain->id);
@@ -1360,8 +1312,6 @@ static void test_gtree_save_iommu(void)
static void test_gtree_load_iommu(void)
{
- Error *local_err = NULL;
- int ret;
TestGTreeIOMMU *dest_iommu = g_new0(TestGTreeIOMMU, 1);
TestGTreeIOMMU *orig_iommu = create_iommu();
QEMUFile *fsave, *fload;
@@ -1373,10 +1323,7 @@ static void test_gtree_load_iommu(void)
qemu_fclose(fsave);
fload = open_test_file(false);
- ret = vmstate_load_state(fload, &vmstate_iommu, dest_iommu, 1, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(fload, &vmstate_iommu, dest_iommu, 1, &error_abort);
eof = qemu_get_byte(fload);
g_assert(!qemu_file_get_error(fload));
g_assert_cmpint(orig_iommu->id, ==, dest_iommu->id);
@@ -1498,8 +1445,6 @@ static void test_save_qlist(void)
static void test_load_qlist(void)
{
- Error *local_err = NULL;
- int ret;
QEMUFile *fsave, *fload;
TestQListContainer *orig_container = alloc_container();
TestQListContainer *dest_container = g_new0(TestQListContainer, 1);
@@ -1513,11 +1458,8 @@ static void test_load_qlist(void)
qemu_fclose(fsave);
fload = open_test_file(false);
- ret = vmstate_load_state(fload, &vmstate_container, dest_container, 1,
- &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ vmstate_load_vmsd(fload, &vmstate_container, dest_container, 1,
+ &error_abort);
eof = qemu_get_byte(fload);
g_assert(!qemu_file_get_error(fload));
g_assert_cmpint(eof, ==, QEMU_VM_EOF);
@@ -1534,22 +1476,22 @@ typedef struct TmpTestStruct {
int64_t diff;
} TmpTestStruct;
-static int tmp_child_pre_save(void *opaque)
+static bool tmp_child_pre_save(void *opaque, Error **errp)
{
struct TmpTestStruct *tts = opaque;
tts->diff = tts->parent->b - tts->parent->a;
- return 0;
+ return true;
}
-static int tmp_child_post_load(void *opaque, int version_id)
+static bool tmp_child_post_load(void *opaque, int version_id, Error **errp)
{
struct TmpTestStruct *tts = opaque;
tts->parent->b = tts->parent->a + tts->diff;
- return 0;
+ return true;
}
static const VMStateDescription vmstate_tmp_back_to_parent = {
@@ -1562,8 +1504,8 @@ static const VMStateDescription vmstate_tmp_back_to_parent = {
static const VMStateDescription vmstate_tmp_child = {
.name = "test/tmp_child",
- .pre_save = tmp_child_pre_save,
- .post_load = tmp_child_post_load,
+ .pre_save_errp = tmp_child_pre_save,
+ .post_load_errp = tmp_child_post_load,
.fields = (const VMStateField[]) {
VMSTATE_INT64(diff, TmpTestStruct),
VMSTATE_STRUCT_POINTER(parent, TmpTestStruct,
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 02/30] ui/vdagent: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 01/30] tests/unit/test-vmstate: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 03/30] hw/virtio: extra state: " Vladimir Sementsov-Ogievskiy
` (27 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Marc-André Lureau
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
ui/vdagent.c | 38 +++++++++++++++++---------------------
1 file changed, 17 insertions(+), 21 deletions(-)
diff --git a/ui/vdagent.c b/ui/vdagent.c
index b9784d4d9b9..a3a1be30404 100644
--- a/ui/vdagent.c
+++ b/ui/vdagent.c
@@ -938,7 +938,7 @@ static void vdagent_chr_class_init(ObjectClass *oc, const void *data)
set_migration_blocked);
}
-static int post_load(void *opaque, int version_id)
+static bool post_load(void *opaque, int version_id, Error **errp)
{
VDAgentChardev *vd = QEMU_VDAGENT_CHARDEV(opaque);
@@ -950,7 +950,7 @@ static int post_load(void *opaque, int version_id)
vdagent_clipboard_peer_register(vd);
}
- return 0;
+ return true;
}
static const VMStateDescription vmstate_chunk = {
@@ -979,15 +979,16 @@ static const VMStateDescription vmstate_cbinfo_array = {
}
};
-static int put_cbinfo(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_cbinfo(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
VDAgentChardev *vd = QEMU_VDAGENT_CHARDEV(pv);
struct CBInfoArray cbinfo = {};
int i;
if (!have_clipboard(vd)) {
- return 0;
+ return true;
}
for (i = 0; i < QEMU_CLIPBOARD_SELECTION__COUNT; i++) {
@@ -996,29 +997,24 @@ static int put_cbinfo(QEMUFile *f, void *pv, size_t size,
}
}
- return vmstate_save_state(f, &vmstate_cbinfo_array, &cbinfo, vmdesc,
- &error_fatal);
+ return vmstate_save_vmsd(f, &vmstate_cbinfo_array, &cbinfo, vmdesc, errp);
}
-static int get_cbinfo(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_cbinfo(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
VDAgentChardev *vd = QEMU_VDAGENT_CHARDEV(pv);
struct CBInfoArray cbinfo = {};
- int i, ret;
- Error *local_err = NULL;
+ int i;
if (!have_clipboard(vd)) {
- return 0;
+ return true;
}
vdagent_clipboard_peer_register(vd);
- ret = vmstate_load_state(f, &vmstate_cbinfo_array, &cbinfo, 0,
- &local_err);
- if (ret) {
- error_report_err(local_err);
- return ret;
+ if (!vmstate_load_vmsd(f, &vmstate_cbinfo_array, &cbinfo, 0, errp)) {
+ return false;
}
for (i = 0; i < cbinfo.n; i++) {
@@ -1029,20 +1025,20 @@ static int get_cbinfo(QEMUFile *f, void *pv, size_t size,
qemu_clipboard_update(info);
}
- return 0;
+ return true;
}
static const VMStateInfo vmstate_cbinfos = {
.name = "vdagent/cbinfos",
- .get = get_cbinfo,
- .put = put_cbinfo,
+ .load = load_cbinfo,
+ .save = save_cbinfo,
};
static const VMStateDescription vmstate_vdagent = {
.name = "vdagent",
.version_id = 0,
.minimum_version_id = 0,
- .post_load = post_load,
+ .post_load_errp = post_load,
.fields = (const VMStateField[]) {
VMSTATE_BOOL(connected, VDAgentChardev),
VMSTATE_UINT32(caps, VDAgentChardev),
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 03/30] hw/virtio: extra state: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 01/30] tests/unit/test-vmstate: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 02/30] ui/vdagent: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 04/30] hw/virtio: config save/load: " Vladimir Sementsov-Ogievskiy
` (26 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin
Stop ignoring the error on save path.
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/virtio/virtio-mmio.c | 21 ++++++---------------
hw/virtio/virtio-pci.c | 21 ++++++---------------
hw/virtio/virtio.c | 24 +++++++++++++-----------
include/hw/virtio/virtio-bus.h | 4 ++--
4 files changed, 27 insertions(+), 43 deletions(-)
diff --git a/hw/virtio/virtio-mmio.c b/hw/virtio/virtio-mmio.c
index 55ceaeef5fc..559363e4438 100644
--- a/hw/virtio/virtio-mmio.c
+++ b/hw/virtio/virtio-mmio.c
@@ -606,29 +606,20 @@ static const VMStateDescription vmstate_virtio_mmio = {
}
};
-static void virtio_mmio_save_extra_state(DeviceState *opaque, QEMUFile *f)
+static bool virtio_mmio_save_extra_state(DeviceState *opaque, QEMUFile *f,
+ Error **errp)
{
VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque);
- Error *local_err = NULL;
- int ret;
- ret = vmstate_save_state(f, &vmstate_virtio_mmio, proxy, NULL, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ return vmstate_save_vmsd(f, &vmstate_virtio_mmio, proxy, NULL, errp);
}
-static int virtio_mmio_load_extra_state(DeviceState *opaque, QEMUFile *f)
+static bool virtio_mmio_load_extra_state(DeviceState *opaque, QEMUFile *f,
+ Error **errp)
{
VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque);
- Error *local_err = NULL;
- int ret;
- ret = vmstate_load_state(f, &vmstate_virtio_mmio, proxy, 1, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
- return ret;
+ return vmstate_load_vmsd(f, &vmstate_virtio_mmio, proxy, 1, errp);
}
static bool virtio_mmio_has_extra_state(DeviceState *opaque)
diff --git a/hw/virtio/virtio-pci.c b/hw/virtio/virtio-pci.c
index 6f5db5fc42b..7a5d4f35e33 100644
--- a/hw/virtio/virtio-pci.c
+++ b/hw/virtio/virtio-pci.c
@@ -184,29 +184,20 @@ static bool virtio_pci_has_extra_state(DeviceState *d)
return true;
}
-static void virtio_pci_save_extra_state(DeviceState *d, QEMUFile *f)
+static bool virtio_pci_save_extra_state(DeviceState *d, QEMUFile *f,
+ Error **errp)
{
VirtIOPCIProxy *proxy = to_virtio_pci_proxy(d);
- Error *local_err = NULL;
- int ret;
- ret = vmstate_save_state(f, &vmstate_virtio_pci, proxy, NULL, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ return vmstate_save_vmsd(f, &vmstate_virtio_pci, proxy, NULL, errp);
}
-static int virtio_pci_load_extra_state(DeviceState *d, QEMUFile *f)
+static bool virtio_pci_load_extra_state(DeviceState *d, QEMUFile *f,
+ Error **errp)
{
VirtIOPCIProxy *proxy = to_virtio_pci_proxy(d);
- Error *local_err = NULL;
- int ret;
- ret = vmstate_load_state(f, &vmstate_virtio_pci, proxy, 1, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
- return ret;
+ return vmstate_load_vmsd(f, &vmstate_virtio_pci, proxy, 1, errp);
}
static void virtio_pci_save_queue(DeviceState *d, int n, QEMUFile *f)
diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c
index daa5607338c..8230a383aff 100644
--- a/hw/virtio/virtio.c
+++ b/hw/virtio/virtio.c
@@ -2914,35 +2914,37 @@ static const VMStateDescription vmstate_virtio_ringsize = {
}
};
-static int get_extra_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_extra_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field,
+ Error **errp)
{
VirtIODevice *vdev = pv;
BusState *qbus = qdev_get_parent_bus(DEVICE(vdev));
VirtioBusClass *k = VIRTIO_BUS_GET_CLASS(qbus);
if (!k->load_extra_state) {
- return -1;
- } else {
- return k->load_extra_state(qbus->parent, f);
+ error_setg(errp, "extra state is unsupported");
+ return false;
}
+
+ return k->load_extra_state(qbus->parent, f, errp);
}
-static int put_extra_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_extra_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
VirtIODevice *vdev = pv;
BusState *qbus = qdev_get_parent_bus(DEVICE(vdev));
VirtioBusClass *k = VIRTIO_BUS_GET_CLASS(qbus);
- k->save_extra_state(qbus->parent, f);
- return 0;
+ return k->save_extra_state(qbus->parent, f, errp);
}
static const VMStateInfo vmstate_info_extra_state = {
.name = "virtqueue_extra_state",
- .get = get_extra_state,
- .put = put_extra_state,
+ .load = load_extra_state,
+ .save = save_extra_state,
};
static const VMStateDescription vmstate_virtio_extra_state = {
diff --git a/include/hw/virtio/virtio-bus.h b/include/hw/virtio/virtio-bus.h
index f80fd714244..255ecb2fcb2 100644
--- a/include/hw/virtio/virtio-bus.h
+++ b/include/hw/virtio/virtio-bus.h
@@ -43,11 +43,11 @@ struct VirtioBusClass {
void (*notify)(DeviceState *d, uint16_t vector);
void (*save_config)(DeviceState *d, QEMUFile *f);
void (*save_queue)(DeviceState *d, int n, QEMUFile *f);
- void (*save_extra_state)(DeviceState *d, QEMUFile *f);
+ bool (*save_extra_state)(DeviceState *d, QEMUFile *f, Error **errp);
int (*load_config)(DeviceState *d, QEMUFile *f);
int (*load_queue)(DeviceState *d, int n, QEMUFile *f);
int (*load_done)(DeviceState *d, QEMUFile *f);
- int (*load_extra_state)(DeviceState *d, QEMUFile *f);
+ bool (*load_extra_state)(DeviceState *d, QEMUFile *f, Error **errp);
bool (*has_extra_state)(DeviceState *d);
bool (*query_guest_notifiers)(DeviceState *d);
int (*set_guest_notifiers)(DeviceState *d, int nvqs, bool assign);
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 04/30] hw/virtio: config save/load: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (2 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 03/30] hw/virtio: extra state: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-09-03 17:41 ` Fabiano Rosas
2026-08-25 21:37 ` [PATCH 05/30] hw/virtio: make virtio_save() and virtio_load() static Vladimir Sementsov-Ogievskiy
` (25 subsequent siblings)
29 siblings, 1 reply; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin,
Cornelia Huck, Halil Pasic, Eric Farman, Richard Henderson,
Ilya Leoshkevich, David Hildenbrand, Matthew Rosato,
Christian Borntraeger, open list:virtio-ccw
Stop ignoring the error on save path.
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/pci/pci.c | 27 +++++++++++----------------
hw/s390x/virtio-ccw.c | 19 ++++---------------
hw/virtio/virtio-mmio.c | 10 +++++++---
hw/virtio/virtio-pci.c | 24 +++++++++++++++---------
hw/virtio/virtio.c | 11 +++++++----
include/hw/pci/pci.h | 4 ++--
include/hw/virtio/virtio-bus.h | 4 ++--
7 files changed, 48 insertions(+), 51 deletions(-)
diff --git a/hw/pci/pci.c b/hw/pci/pci.c
index d3191609e28..76d006fa1d7 100644
--- a/hw/pci/pci.c
+++ b/hw/pci/pci.c
@@ -940,37 +940,32 @@ const VMStateDescription vmstate_pci_device = {
};
-void pci_device_save(PCIDevice *s, QEMUFile *f)
+bool pci_device_save(PCIDevice *s, QEMUFile *f, Error **errp)
{
- Error *local_err = NULL;
- int ret;
+ bool ok;
/* Clear interrupt status bit: it is implicit
* in irq_state which we are saving.
* This makes us compatible with old devices
* which never set or clear this bit. */
s->config[PCI_STATUS] &= ~PCI_STATUS_INTERRUPT;
- ret = vmstate_save_state(f, &vmstate_pci_device, s, NULL, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+
+ ok = vmstate_save_vmsd(f, &vmstate_pci_device, s, NULL, errp);
+
/* Restore the interrupt status bit. */
pci_update_irq_status(s);
+
+ return ok;
}
-int pci_device_load(PCIDevice *s, QEMUFile *f)
+bool pci_device_load(PCIDevice *s, QEMUFile *f, Error **errp)
{
- Error *local_err = NULL;
- int ret;
+ bool ok = vmstate_load_vmsd(f, &vmstate_pci_device, s, s->version_id, errp);
- ret = vmstate_load_state(f, &vmstate_pci_device, s, s->version_id,
- &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
/* Restore the interrupt status bit. */
pci_update_irq_status(s);
- return ret;
+
+ return ok;
}
static void pci_set_default_subsystem_id(PCIDevice *pci_dev)
diff --git a/hw/s390x/virtio-ccw.c b/hw/s390x/virtio-ccw.c
index d82874ed27e..848ed09e94b 100644
--- a/hw/s390x/virtio-ccw.c
+++ b/hw/s390x/virtio-ccw.c
@@ -1129,29 +1129,18 @@ static int virtio_ccw_load_queue(DeviceState *d, int n, QEMUFile *f)
return 0;
}
-static void virtio_ccw_save_config(DeviceState *d, QEMUFile *f)
+static bool virtio_ccw_save_config(DeviceState *d, QEMUFile *f, Error **errp)
{
VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(d);
- Error *local_err = NULL;
- int ret;
- ret = vmstate_save_state(f, &vmstate_virtio_ccw_dev, dev, NULL, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
+ return vmstate_save_vmsd(f, &vmstate_virtio_ccw_dev, dev, NULL, errp);
}
-static int virtio_ccw_load_config(DeviceState *d, QEMUFile *f)
+static bool virtio_ccw_load_config(DeviceState *d, QEMUFile *f, Error **errp)
{
VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(d);
- Error *local_err = NULL;
- int ret;
- ret = vmstate_load_state(f, &vmstate_virtio_ccw_dev, dev, 1, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
- return ret;
+ return vmstate_load_vmsd(f, &vmstate_virtio_ccw_dev, dev, 1, errp);
}
static void virtio_ccw_pre_plugged(DeviceState *d, Error **errp)
diff --git a/hw/virtio/virtio-mmio.c b/hw/virtio/virtio-mmio.c
index 559363e4438..ef34b76913e 100644
--- a/hw/virtio/virtio-mmio.c
+++ b/hw/virtio/virtio-mmio.c
@@ -547,23 +547,27 @@ static void virtio_mmio_update_irq(DeviceState *opaque, uint16_t vector)
qemu_set_irq(proxy->irq, level);
}
-static int virtio_mmio_load_config(DeviceState *opaque, QEMUFile *f)
+static bool virtio_mmio_load_config(DeviceState *opaque, QEMUFile *f,
+ Error **errp)
{
VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque);
proxy->host_features_sel = qemu_get_be32(f);
proxy->guest_features_sel = qemu_get_be32(f);
proxy->guest_page_shift = qemu_get_be32(f);
- return 0;
+ return true;
}
-static void virtio_mmio_save_config(DeviceState *opaque, QEMUFile *f)
+static bool virtio_mmio_save_config(DeviceState *opaque, QEMUFile *f,
+ Error **errp)
{
VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque);
qemu_put_be32(f, proxy->host_features_sel);
qemu_put_be32(f, proxy->guest_features_sel);
qemu_put_be32(f, proxy->guest_page_shift);
+
+ return true;
}
static const VMStateDescription vmstate_virtio_mmio_queue_state = {
diff --git a/hw/virtio/virtio-pci.c b/hw/virtio/virtio-pci.c
index 7a5d4f35e33..07941319be2 100644
--- a/hw/virtio/virtio-pci.c
+++ b/hw/virtio/virtio-pci.c
@@ -84,15 +84,21 @@ static void virtio_pci_notify(DeviceState *d, uint16_t vector)
}
}
-static void virtio_pci_save_config(DeviceState *d, QEMUFile *f)
+static bool virtio_pci_save_config(DeviceState *d, QEMUFile *f, Error **errp)
{
VirtIOPCIProxy *proxy = to_virtio_pci_proxy(d);
VirtIODevice *vdev = virtio_bus_get_device(&proxy->bus);
- pci_device_save(&proxy->pci_dev, f);
+ if (!pci_device_save(&proxy->pci_dev, f, errp)) {
+ return false;
+ }
+
msix_save(&proxy->pci_dev, f);
- if (msix_present(&proxy->pci_dev))
+ if (msix_present(&proxy->pci_dev)) {
qemu_put_be16(f, vdev->config_vector);
+ }
+
+ return true;
}
static const VMStateDescription vmstate_virtio_pci_modern_queue_state = {
@@ -209,24 +215,24 @@ static void virtio_pci_save_queue(DeviceState *d, int n, QEMUFile *f)
qemu_put_be16(f, virtio_queue_vector(vdev, n));
}
-static int virtio_pci_load_config(DeviceState *d, QEMUFile *f)
+static bool virtio_pci_load_config(DeviceState *d, QEMUFile *f, Error **errp)
{
VirtIOPCIProxy *proxy = to_virtio_pci_proxy(d);
VirtIODevice *vdev = virtio_bus_get_device(&proxy->bus);
uint16_t vector;
- int ret;
- ret = pci_device_load(&proxy->pci_dev, f);
- if (ret) {
- return ret;
+ if (!pci_device_load(&proxy->pci_dev, f, errp)) {
+ return false;
}
+
msix_unuse_all_vectors(&proxy->pci_dev);
msix_load(&proxy->pci_dev, f);
if (msix_present(&proxy->pci_dev)) {
qemu_get_be16s(f, &vector);
if (vector != VIRTIO_NO_VECTOR && vector >= proxy->nvectors) {
- return -EINVAL;
+ error_setg(errp, "load config: unexpected vector %" PRIu16, vector);
+ return false;
}
} else {
vector = VIRTIO_NO_VECTOR;
diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c
index 8230a383aff..0f7c8acead0 100644
--- a/hw/virtio/virtio.c
+++ b/hw/virtio/virtio.c
@@ -3077,7 +3077,10 @@ int virtio_save(VirtIODevice *vdev, QEMUFile *f)
Error *local_err = NULL;
if (k->save_config) {
- k->save_config(qbus->parent, f);
+ if (!k->save_config(qbus->parent, f, &local_err)) {
+ error_report_err(local_err);
+ return -EINVAL;
+ }
}
qemu_put_8s(f, &vdev->status);
@@ -3526,9 +3529,9 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
vdev->device_endian = VIRTIO_DEVICE_ENDIAN_UNKNOWN;
if (k->load_config) {
- ret = k->load_config(qbus->parent, f);
- if (ret)
- return ret;
+ if (!k->load_config(qbus->parent, f, &local_err)) {
+ return -EINVAL;
+ }
}
qemu_get_8s(f, &vdev->status);
diff --git a/include/hw/pci/pci.h b/include/hw/pci/pci.h
index f2448e941a0..7c3fdc05630 100644
--- a/include/hw/pci/pci.h
+++ b/include/hw/pci/pci.h
@@ -270,8 +270,8 @@ uint32_t pci_default_read_config(PCIDevice *d,
uint32_t address, int len);
void pci_default_write_config(PCIDevice *d,
uint32_t address, uint32_t val, int len);
-void pci_device_save(PCIDevice *s, QEMUFile *f);
-int pci_device_load(PCIDevice *s, QEMUFile *f);
+bool pci_device_save(PCIDevice *s, QEMUFile *f, Error **errp);
+bool pci_device_load(PCIDevice *s, QEMUFile *f, Error **errp);
MemoryRegion *pci_address_space(PCIDevice *dev);
MemoryRegion *pci_address_space_io(PCIDevice *dev);
diff --git a/include/hw/virtio/virtio-bus.h b/include/hw/virtio/virtio-bus.h
index 255ecb2fcb2..1b9867002b8 100644
--- a/include/hw/virtio/virtio-bus.h
+++ b/include/hw/virtio/virtio-bus.h
@@ -41,10 +41,10 @@ struct VirtioBusClass {
/* This is what a VirtioBus must implement */
BusClass parent;
void (*notify)(DeviceState *d, uint16_t vector);
- void (*save_config)(DeviceState *d, QEMUFile *f);
+ bool (*save_config)(DeviceState *d, QEMUFile *f, Error **errp);
void (*save_queue)(DeviceState *d, int n, QEMUFile *f);
bool (*save_extra_state)(DeviceState *d, QEMUFile *f, Error **errp);
- int (*load_config)(DeviceState *d, QEMUFile *f);
+ bool (*load_config)(DeviceState *d, QEMUFile *f, Error **errp);
int (*load_queue)(DeviceState *d, int n, QEMUFile *f);
int (*load_done)(DeviceState *d, QEMUFile *f);
bool (*load_extra_state)(DeviceState *d, QEMUFile *f, Error **errp);
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 05/30] hw/virtio: make virtio_save() and virtio_load() static
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (3 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 04/30] hw/virtio: config save/load: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 06/30] hw/virtio: remaining: move to new migration APIs Vladimir Sementsov-Ogievskiy
` (24 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin
These functions are used only in virtio.c, no reason to make
them public.
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/virtio/virtio.c | 7 +++++--
include/hw/virtio/virtio.h | 4 ----
2 files changed, 5 insertions(+), 6 deletions(-)
diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c
index 0f7c8acead0..a9338af6d00 100644
--- a/hw/virtio/virtio.c
+++ b/hw/virtio/virtio.c
@@ -62,6 +62,9 @@
*/
#define VIRTIO_PCI_VRING_ALIGN 4096
+static int coroutine_mixed_fn
+virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id);
+
typedef struct VRingDesc
{
uint64_t addr;
@@ -3067,7 +3070,7 @@ static const VMStateDescription vmstate_virtio = {
}
};
-int virtio_save(VirtIODevice *vdev, QEMUFile *f)
+static int virtio_save(VirtIODevice *vdev, QEMUFile *f)
{
BusState *qbus = qdev_get_parent_bus(DEVICE(vdev));
VirtioBusClass *k = VIRTIO_BUS_GET_CLASS(qbus);
@@ -3510,7 +3513,7 @@ size_t virtio_get_config_size(const VirtIOConfigSizeParams *params,
return config_size;
}
-int coroutine_mixed_fn
+static int coroutine_mixed_fn
virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
{
int i, ret;
diff --git a/include/hw/virtio/virtio.h b/include/hw/virtio/virtio.h
index c99cb19d886..9628ae3bcb8 100644
--- a/include/hw/virtio/virtio.h
+++ b/include/hw/virtio/virtio.h
@@ -338,8 +338,6 @@ int virtqueue_get_avail_bytes(VirtQueue *vq, unsigned int *in_bytes,
void virtio_notify(VirtIODevice *vdev, VirtQueue *vq);
-int virtio_save(VirtIODevice *vdev, QEMUFile *f);
-
/**
* virtio_new_shmem_region() - Create a new shared memory region
* @vdev: VirtIODevice
@@ -443,8 +441,6 @@ extern const VMStateInfo virtio_vmstate_info;
.flags = VMS_SINGLE, \
}
-int virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id);
-
/**
* virtio_notify_config() - signal a change to device config
* @vdev: the virtio device
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 06/30] hw/virtio: remaining: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (4 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 05/30] hw/virtio: make virtio_save() and virtio_load() static Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 07/30] hw/s390x/virtio-ccw.c: " Vladimir Sementsov-Ogievskiy
` (23 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin,
Stefano Garzarella, Stefan Hajnoczi, open list:virtiofs
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/virtio/vhost-user-fs.c | 68 +++++++++----------
hw/virtio/virtio.c | 133 +++++++++++++++++++-------------------
2 files changed, 100 insertions(+), 101 deletions(-)
diff --git a/hw/virtio/vhost-user-fs.c b/hw/virtio/vhost-user-fs.c
index 209993918a3..215aff77282 100644
--- a/hw/virtio/vhost-user-fs.c
+++ b/hw/virtio/vhost-user-fs.c
@@ -307,49 +307,50 @@ static struct vhost_dev *vuf_get_vhost(VirtIODevice *vdev)
/**
* Fetch the internal state from virtiofsd and save it to `f`.
*/
-static int vuf_save_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool vuf_save_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
+ ERRP_GUARD();
VirtIODevice *vdev = pv;
VHostUserFS *fs = VHOST_USER_FS(vdev);
- Error *local_error = NULL;
int ret;
- ret = vhost_save_backend_state(&fs->vhost_dev, f, &local_error);
+ ret = vhost_save_backend_state(&fs->vhost_dev, f, errp);
if (ret < 0) {
- error_reportf_err(local_error,
- "Error saving back-end state of %s device %s "
- "(tag: \"%s\"): ",
- vdev->name, vdev->parent_obj.canonical_path,
- fs->conf.tag ?: "<none>");
- return ret;
+ error_prepend(errp,
+ "Error saving back-end state of %s device %s "
+ "(tag: \"%s\"): ",
+ vdev->name, vdev->parent_obj.canonical_path,
+ fs->conf.tag ?: "<none>");
+ return false;
}
- return 0;
+ return true;
}
/**
* Load virtiofsd's internal state from `f` and send it over to virtiofsd.
*/
-static int vuf_load_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool vuf_load_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
+ ERRP_GUARD();
VirtIODevice *vdev = pv;
VHostUserFS *fs = VHOST_USER_FS(vdev);
- Error *local_error = NULL;
int ret;
- ret = vhost_load_backend_state(&fs->vhost_dev, f, &local_error);
+ ret = vhost_load_backend_state(&fs->vhost_dev, f, errp);
if (ret < 0) {
- error_reportf_err(local_error,
- "Error loading back-end state of %s device %s "
- "(tag: \"%s\"): ",
- vdev->name, vdev->parent_obj.canonical_path,
- fs->conf.tag ?: "<none>");
- return ret;
+ error_prepend(errp,
+ "Error loading back-end state of %s device %s "
+ "(tag: \"%s\"): ",
+ vdev->name, vdev->parent_obj.canonical_path,
+ fs->conf.tag ?: "<none>");
+ return false;
}
- return 0;
+ return true;
}
static bool vuf_is_internal_migration(void *opaque)
@@ -358,20 +359,21 @@ static bool vuf_is_internal_migration(void *opaque)
return true;
}
-static int vuf_check_migration_support(void *opaque)
+static bool vuf_check_migration_support(void *opaque, Error **errp)
{
VirtIODevice *vdev = opaque;
VHostUserFS *fs = VHOST_USER_FS(vdev);
if (!vhost_supports_device_state(&fs->vhost_dev)) {
- error_report("Back-end of %s device %s (tag: \"%s\") does not support "
- "migration through qemu",
- vdev->name, vdev->parent_obj.canonical_path,
- fs->conf.tag ?: "<none>");
- return -ENOTSUP;
+ error_setg(errp,
+ "Back-end of %s device %s (tag: \"%s\") does not support "
+ "migration through qemu",
+ vdev->name, vdev->parent_obj.canonical_path,
+ fs->conf.tag ?: "<none>");
+ return false;
}
- return 0;
+ return true;
}
static const VMStateDescription vuf_backend_vmstate;
@@ -393,15 +395,15 @@ static const VMStateDescription vuf_backend_vmstate = {
.name = "vhost-user-fs-backend",
.version_id = 0,
.needed = vuf_is_internal_migration,
- .pre_load = vuf_check_migration_support,
- .pre_save = vuf_check_migration_support,
+ .pre_load_errp = vuf_check_migration_support,
+ .pre_save_errp = vuf_check_migration_support,
.fields = (const VMStateField[]) {
{
.name = "back-end",
.info = &(const VMStateInfo) {
.name = "virtio-fs back-end state",
- .get = vuf_load_state,
- .put = vuf_save_state,
+ .load = vuf_load_state,
+ .save = vuf_save_state,
},
},
VMSTATE_END_OF_LIST()
diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c
index a9338af6d00..0b1ec41ac97 100644
--- a/hw/virtio/virtio.c
+++ b/hw/virtio/virtio.c
@@ -62,8 +62,8 @@
*/
#define VIRTIO_PCI_VRING_ALIGN 4096
-static int coroutine_mixed_fn
-virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id);
+static bool coroutine_mixed_fn
+virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id, Error **errp);
typedef struct VRingDesc
{
@@ -3070,19 +3070,17 @@ static const VMStateDescription vmstate_virtio = {
}
};
-static int virtio_save(VirtIODevice *vdev, QEMUFile *f)
+static bool virtio_save(VirtIODevice *vdev, QEMUFile *f, Error **errp)
{
BusState *qbus = qdev_get_parent_bus(DEVICE(vdev));
VirtioBusClass *k = VIRTIO_BUS_GET_CLASS(qbus);
VirtioDeviceClass *vdc = VIRTIO_DEVICE_GET_CLASS(vdev);
uint32_t guest_features_lo = (vdev->guest_features & 0xffffffff);
- int i, ret;
- Error *local_err = NULL;
+ int i;
if (k->save_config) {
- if (!k->save_config(qbus->parent, f, &local_err)) {
- error_report_err(local_err);
- return -EINVAL;
+ if (!k->save_config(qbus->parent, f, errp)) {
+ return false;
}
}
@@ -3124,19 +3122,13 @@ static int virtio_save(VirtIODevice *vdev, QEMUFile *f)
}
if (vdc->vmsd) {
- ret = vmstate_save_state(f, vdc->vmsd, vdev, NULL, &local_err);
- if (ret) {
- error_report_err(local_err);
- return ret;
+ if (!vmstate_save_vmsd(f, vdc->vmsd, vdev, NULL, errp)) {
+ return false;
}
}
/* Subsections */
- ret = vmstate_save_state(f, &vmstate_virtio, vdev, NULL, &local_err);
- if (ret < 0) {
- error_report_err(local_err);
- }
- return ret;
+ return vmstate_save_vmsd(f, &vmstate_virtio, vdev, NULL, errp);
}
VirtioSharedMemory *virtio_new_shmem_region(VirtIODevice *vdev, uint8_t shmid, uint64_t size)
@@ -3307,27 +3299,28 @@ void virtio_del_shmem_map(VirtioSharedMemory *shmem, hwaddr offset,
}
/* A wrapper for use as a VMState .put function */
-static int virtio_device_put(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool virtio_device_save(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
- return virtio_save(VIRTIO_DEVICE(opaque), f);
+ return virtio_save(VIRTIO_DEVICE(opaque), f, errp);
}
/* A wrapper for use as a VMState .get function */
-static int coroutine_mixed_fn
-virtio_device_get(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool coroutine_mixed_fn
+virtio_device_load(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
VirtIODevice *vdev = VIRTIO_DEVICE(opaque);
DeviceClass *dc = DEVICE_CLASS(VIRTIO_DEVICE_GET_CLASS(vdev));
- return virtio_load(vdev, f, dc->vmsd->version_id);
+ return virtio_load(vdev, f, dc->vmsd->version_id, errp);
}
const VMStateInfo virtio_vmstate_info = {
.name = "virtio",
- .get = virtio_device_get,
- .put = virtio_device_put,
+ .load = virtio_device_load,
+ .save = virtio_device_save,
};
static int virtio_set_features_nocheck(VirtIODevice *vdev, const uint64_t *val)
@@ -3513,8 +3506,8 @@ size_t virtio_get_config_size(const VirtIOConfigSizeParams *params,
return config_size;
}
-static int coroutine_mixed_fn
-virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
+static bool coroutine_mixed_fn
+virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id, Error **errp)
{
int i, ret;
uint32_t config_len;
@@ -3523,7 +3516,6 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
BusState *qbus = qdev_get_parent_bus(DEVICE(vdev));
VirtioBusClass *k = VIRTIO_BUS_GET_CLASS(qbus);
VirtioDeviceClass *vdc = VIRTIO_DEVICE_GET_CLASS(vdev);
- Error *local_err = NULL;
/*
* We poison the endianness to ensure it does not get used before
@@ -3532,8 +3524,8 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
vdev->device_endian = VIRTIO_DEVICE_ENDIAN_UNKNOWN;
if (k->load_config) {
- if (!k->load_config(qbus->parent, f, &local_err)) {
- return -EINVAL;
+ if (!k->load_config(qbus->parent, f, errp)) {
+ return false;
}
}
@@ -3541,7 +3533,9 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
qemu_get_8s(f, &vdev->isr);
qemu_get_be16s(f, &vdev->queue_sel);
if (vdev->queue_sel >= VIRTIO_QUEUE_MAX) {
- return -1;
+ error_setg(errp, "virtio_load: queue_sel %u out of range",
+ vdev->queue_sel);
+ return false;
}
qemu_get_be32s(f, &features);
@@ -3566,7 +3560,9 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
while (config_len > vdev->config_len) {
if (qemu_file_get_error(f)) {
- return -1;
+ error_setg(errp, "virtio_load: stream error while skipping "
+ "excess config");
+ return false;
}
qemu_get_byte(f);
config_len--;
@@ -3575,24 +3571,25 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
num = qemu_get_be32(f);
if (num > VIRTIO_QUEUE_MAX) {
- error_report("Invalid number of virtqueues: 0x%x", num);
- return -1;
+ error_setg(errp, "Invalid number of virtqueues: 0x%x", num);
+ return false;
}
if (vdc->pre_load_queues) {
ret = vdc->pre_load_queues(vdev, num);
if (ret) {
- return ret;
+ error_setg(errp, "virtio_load: pre_load_queues failed");
+ return false;
}
}
for (i = 0; i < num; i++) {
vdev->vq[i].vring.num = qemu_get_be32(f);
if (vdev->vq[i].vring.num > vdev->vq[i].vring.num_default) {
- error_report("VQ %d vring.num %u exceeds allocated max %u",
- i, vdev->vq[i].vring.num,
- vdev->vq[i].vring.num_default);
- return -1;
+ error_setg(errp, "VQ %d vring.num %u exceeds allocated max %u",
+ i, vdev->vq[i].vring.num,
+ vdev->vq[i].vring.num_default);
+ return false;
}
if (k->has_variable_vring_alignment) {
vdev->vq[i].vring.align = qemu_get_be32(f);
@@ -3603,15 +3600,17 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
vdev->vq[i].notification = true;
if (!vdev->vq[i].vring.desc && vdev->vq[i].last_avail_idx) {
- error_report("VQ %d address 0x0 "
- "inconsistent with Host index 0x%x",
- i, vdev->vq[i].last_avail_idx);
- return -1;
+ error_setg(errp, "VQ %d address 0x0 "
+ "inconsistent with Host index 0x%x",
+ i, vdev->vq[i].last_avail_idx);
+ return false;
}
if (k->load_queue) {
ret = k->load_queue(qbus->parent, i, f);
- if (ret)
- return ret;
+ if (ret) {
+ error_setg(errp, "virtio_load: load_queue failed for vq %d", i);
+ return false;
+ }
}
}
@@ -3620,23 +3619,20 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
if (vdc->load != NULL) {
ret = vdc->load(vdev, f, version_id);
if (ret) {
- return ret;
+ error_setg(errp, "virtio_load: device load failed");
+ return false;
}
}
if (vdc->vmsd) {
- ret = vmstate_load_state(f, vdc->vmsd, vdev, version_id, &local_err);
- if (ret) {
- error_report_err(local_err);
- return ret;
+ if (!vmstate_load_vmsd(f, vdc->vmsd, vdev, version_id, errp)) {
+ return false;
}
}
/* Subsections */
- ret = vmstate_load_state(f, &vmstate_virtio, vdev, 1, &local_err);
- if (ret) {
- error_report_err(local_err);
- return ret;
+ if (!vmstate_load_vmsd(f, &vmstate_virtio, vdev, 1, errp)) {
+ return false;
}
if (vdev->device_endian == VIRTIO_DEVICE_ENDIAN_UNKNOWN) {
@@ -3649,11 +3645,11 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
*/
if (virtio_set_features_nocheck_maybe_co(vdev,
vdev->guest_features_ex) < 0) {
- error_report("Features 0x" VIRTIO_FEATURES_FMT " unsupported. "
- "Allowed features: 0x" VIRTIO_FEATURES_FMT,
- VIRTIO_FEATURES_PR(vdev->guest_features_ex),
- VIRTIO_FEATURES_PR(vdev->host_features_ex));
- return -1;
+ error_setg(errp, "Features 0x" VIRTIO_FEATURES_FMT " unsupported. "
+ "Allowed features: 0x" VIRTIO_FEATURES_FMT,
+ VIRTIO_FEATURES_PR(vdev->guest_features_ex),
+ VIRTIO_FEATURES_PR(vdev->host_features_ex));
+ return false;
}
if (!virtio_device_started(vdev, vdev->status) &&
@@ -3710,12 +3706,12 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
vdev->vq[i].inuse = (uint16_t)(vdev->vq[i].last_avail_idx -
vdev->vq[i].used_idx);
if (vdev->vq[i].inuse > vdev->vq[i].vring.num) {
- error_report("VQ %d size 0x%x < last_avail_idx 0x%x - "
- "used_idx 0x%x",
- i, vdev->vq[i].vring.num,
- vdev->vq[i].last_avail_idx,
- vdev->vq[i].used_idx);
- return -1;
+ error_setg(errp, "VQ %d size 0x%x < last_avail_idx 0x%x - "
+ "used_idx 0x%x",
+ i, vdev->vq[i].vring.num,
+ vdev->vq[i].last_avail_idx,
+ vdev->vq[i].used_idx);
+ return false;
}
}
}
@@ -3723,11 +3719,12 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
if (vdc->post_load) {
ret = vdc->post_load(vdev);
if (ret) {
- return ret;
+ error_setg(errp, "virtio_load: post_load failed");
+ return false;
}
}
- return 0;
+ return true;
}
void virtio_cleanup(VirtIODevice *vdev)
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 07/30] hw/s390x/virtio-ccw.c: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (5 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 06/30] hw/virtio: remaining: move to new migration APIs Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 08/30] hw/scsi/spapr_vscsi: " Vladimir Sementsov-Ogievskiy
` (22 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Cornelia Huck, Halil Pasic,
Eric Farman, Michael S. Tsirkin, Matthew Rosato,
Richard Henderson, Ilya Leoshkevich, David Hildenbrand,
Christian Borntraeger, open list:virtio-ccw
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/s390x/virtio-ccw.c | 21 +++++++++++----------
1 file changed, 11 insertions(+), 10 deletions(-)
diff --git a/hw/s390x/virtio-ccw.c b/hw/s390x/virtio-ccw.c
index 848ed09e94b..6bc901a64ec 100644
--- a/hw/s390x/virtio-ccw.c
+++ b/hw/s390x/virtio-ccw.c
@@ -40,7 +40,7 @@
bool have_virtio_ccw = true;
-static int virtio_ccw_dev_post_load(void *opaque, int version_id)
+static bool virtio_ccw_dev_post_load(void *opaque, int version_id, Error **errp)
{
VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(opaque);
CcwDevice *ccw_dev = CCW_DEVICE(dev);
@@ -56,7 +56,7 @@ static int virtio_ccw_dev_post_load(void *opaque, int version_id)
if (ck->refill_ids) {
ck->refill_ids(ccw_dev);
}
- return 0;
+ return true;
}
typedef struct VirtioCcwDeviceTmp {
@@ -64,7 +64,7 @@ typedef struct VirtioCcwDeviceTmp {
uint16_t config_vector;
} VirtioCcwDeviceTmp;
-static int virtio_ccw_dev_tmp_pre_save(void *opaque)
+static bool virtio_ccw_dev_tmp_pre_save(void *opaque, Error **errp)
{
VirtioCcwDeviceTmp *tmp = opaque;
VirtioCcwDevice *dev = tmp->parent;
@@ -72,23 +72,24 @@ static int virtio_ccw_dev_tmp_pre_save(void *opaque)
tmp->config_vector = vdev->config_vector;
- return 0;
+ return true;
}
-static int virtio_ccw_dev_tmp_post_load(void *opaque, int version_id)
+static bool virtio_ccw_dev_tmp_post_load(void *opaque, int version_id,
+ Error **errp)
{
VirtioCcwDeviceTmp *tmp = opaque;
VirtioCcwDevice *dev = tmp->parent;
VirtIODevice *vdev = virtio_bus_get_device(&dev->bus);
vdev->config_vector = tmp->config_vector;
- return 0;
+ return true;
}
const VMStateDescription vmstate_virtio_ccw_dev_tmp = {
.name = "s390_virtio_ccw_dev_tmp",
- .pre_save = virtio_ccw_dev_tmp_pre_save,
- .post_load = virtio_ccw_dev_tmp_post_load,
+ .pre_save_errp = virtio_ccw_dev_tmp_pre_save,
+ .post_load_errp = virtio_ccw_dev_tmp_post_load,
.fields = (const VMStateField[]) {
VMSTATE_UINT16(config_vector, VirtioCcwDeviceTmp),
VMSTATE_END_OF_LIST()
@@ -99,7 +100,7 @@ const VMStateDescription vmstate_virtio_ccw_dev = {
.name = "s390_virtio_ccw_dev",
.version_id = 1,
.minimum_version_id = 1,
- .post_load = virtio_ccw_dev_post_load,
+ .post_load_errp = virtio_ccw_dev_post_load,
.fields = (const VMStateField[]) {
VMSTATE_CCW_DEVICE(parent_obj, VirtioCcwDevice),
VMSTATE_PTR_TO_IND_ADDR(indicators, VirtioCcwDevice),
@@ -107,7 +108,7 @@ const VMStateDescription vmstate_virtio_ccw_dev = {
VMSTATE_PTR_TO_IND_ADDR(summary_indicator, VirtioCcwDevice),
/*
* Ugly hack because VirtIODevice does not migrate itself.
- * This also makes legacy via vmstate_save_state possible.
+ * This also makes legacy via vmstate_save_vmsd possible.
*/
VMSTATE_WITH_TMP(VirtioCcwDevice, VirtioCcwDeviceTmp,
vmstate_virtio_ccw_dev_tmp),
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 08/30] hw/scsi/spapr_vscsi: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (6 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 07/30] hw/s390x/virtio-ccw.c: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 09/30] hw/scsi/scsi-bus.c: use " Vladimir Sementsov-Ogievskiy
` (21 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Paolo Bonzini, Fam Zheng,
Nicholas Piggin, Harsh Prateek Bora, Amit Machhiwal,
open list:sPAPR (pseries)
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/scsi/spapr_vscsi.c | 9 +++------
1 file changed, 3 insertions(+), 6 deletions(-)
diff --git a/hw/scsi/spapr_vscsi.c b/hw/scsi/spapr_vscsi.c
index b4c8f94d22a..5938a392b95 100644
--- a/hw/scsi/spapr_vscsi.c
+++ b/hw/scsi/spapr_vscsi.c
@@ -629,12 +629,11 @@ static void vscsi_save_request(QEMUFile *f, SCSIRequest *sreq)
{
vscsi_req *req = sreq->hba_private;
Error *local_err = NULL;
- int rc;
assert(req->active);
- rc = vmstate_save_state(f, &vmstate_spapr_vscsi_req, req, NULL, &local_err);
- if (rc < 0) {
+ if (!vmstate_save_vmsd(f, &vmstate_spapr_vscsi_req, req, NULL,
+ &local_err)) {
error_report_err(local_err);
return;
}
@@ -647,7 +646,6 @@ static void *vscsi_load_request(QEMUFile *f, SCSIRequest *sreq)
SCSIBus *bus = sreq->bus;
VSCSIState *s = VIO_SPAPR_VSCSI_DEVICE(bus->qbus.parent);
vscsi_req *req;
- int rc;
Error *local_err = NULL;
assert(sreq->tag < VSCSI_REQ_LIMIT);
@@ -655,8 +653,7 @@ static void *vscsi_load_request(QEMUFile *f, SCSIRequest *sreq)
assert(!req->active);
memset(req, 0, sizeof(*req));
- rc = vmstate_load_state(f, &vmstate_spapr_vscsi_req, req, 1, &local_err);
- if (rc) {
+ if (!vmstate_load_vmsd(f, &vmstate_spapr_vscsi_req, req, 1, &local_err)) {
fprintf(stderr, "VSCSI: failed loading request tag#%u\n", sreq->tag);
error_report_err(local_err);
return NULL;
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 09/30] hw/scsi/scsi-bus.c: use new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (7 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 08/30] hw/scsi/spapr_vscsi: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 10/30] hw/vfio/pci: move to " Vladimir Sementsov-Ogievskiy
` (20 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Paolo Bonzini, Fam Zheng
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/scsi/scsi-bus.c | 17 +++++++++--------
1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/hw/scsi/scsi-bus.c b/hw/scsi/scsi-bus.c
index deb43d5560e..d455c0b46b5 100644
--- a/hw/scsi/scsi-bus.c
+++ b/hw/scsi/scsi-bus.c
@@ -1888,18 +1888,19 @@ static void put_scsi_req(SCSIRequest *req, void *opaque)
}
}
-static int put_scsi_requests(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool put_scsi_requests(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
SCSIDevice *s = pv;
scsi_device_for_each_req_sync(s, put_scsi_req, f);
qemu_put_sbyte(f, 0);
- return 0;
+ return true;
}
-static int get_scsi_requests(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool get_scsi_requests(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
SCSIDevice *s = pv;
SCSIBus *bus = DO_UPCAST(SCSIBus, qbus, s->qdev.parent_bus);
@@ -1938,13 +1939,13 @@ static int get_scsi_requests(QEMUFile *f, void *pv, size_t size,
scsi_req_unref(req);
}
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_scsi_requests = {
.name = "scsi-requests",
- .get = get_scsi_requests,
- .put = put_scsi_requests,
+ .load = get_scsi_requests,
+ .save = put_scsi_requests,
};
static bool scsi_sense_state_needed(void *opaque)
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 10/30] hw/vfio/pci: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (8 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 09/30] hw/scsi/scsi-bus.c: use " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 11/30] hw/pci/pci: " Vladimir Sementsov-Ogievskiy
` (19 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Alex Williamson,
Cédric Le Goater
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/vfio/pci.c | 14 ++++++--------
1 file changed, 6 insertions(+), 8 deletions(-)
diff --git a/hw/vfio/pci.c b/hw/vfio/pci.c
index 428ab2f0698..ec59c30495d 100644
--- a/hw/vfio/pci.c
+++ b/hw/vfio/pci.c
@@ -3000,8 +3000,8 @@ static int vfio_pci_save_config(VFIODevice *vbasedev, QEMUFile *f, Error **errp)
{
VFIOPCIDevice *vdev = container_of(vbasedev, VFIOPCIDevice, vbasedev);
- return vmstate_save_state(f, &vmstate_vfio_pci_config, vdev, NULL,
- errp);
+ return vmstate_save_vmsd(
+ f, &vmstate_vfio_pci_config, vdev, NULL, errp) ? 0 : -EINVAL;
}
static int vfio_pci_load_config(VFIODevice *vbasedev, QEMUFile *f)
@@ -3009,18 +3009,16 @@ static int vfio_pci_load_config(VFIODevice *vbasedev, QEMUFile *f)
VFIOPCIDevice *vdev = container_of(vbasedev, VFIOPCIDevice, vbasedev);
PCIDevice *pdev = PCI_DEVICE(vdev);
pcibus_t old_addr[PCI_NUM_REGIONS - 1];
- int bar, ret;
+ int bar;
Error *local_err = NULL;
for (bar = 0; bar < PCI_ROM_SLOT; bar++) {
old_addr[bar] = pdev->io_regions[bar].addr;
}
- ret = vmstate_load_state(f, &vmstate_vfio_pci_config, vdev, 1,
- &local_err);
- if (ret) {
+ if (!vmstate_load_vmsd(f, &vmstate_vfio_pci_config, vdev, 1, &local_err)) {
error_report_err(local_err);
- return ret;
+ return -EINVAL;
}
vfio_pci_write_config(pdev, PCI_COMMAND,
@@ -3044,7 +3042,7 @@ static int vfio_pci_load_config(VFIODevice *vbasedev, QEMUFile *f)
vfio_msix_enable(vdev);
}
- return ret;
+ return 0;
}
/* Transform from VFIODevice to VFIOPCIDevice. Return NULL if fails. */
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 11/30] hw/pci/pci: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (9 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 10/30] hw/vfio/pci: move to " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 12/30] hw/pci/msix.c: use " Vladimir Sementsov-Ogievskiy
` (18 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/pci/pci.c | 58 ++++++++++++++++++++++++++++------------------------
1 file changed, 31 insertions(+), 27 deletions(-)
diff --git a/hw/pci/pci.c b/hw/pci/pci.c
index 76d006fa1d7..0f70f0f7af8 100644
--- a/hw/pci/pci.c
+++ b/hw/pci/pci.c
@@ -807,8 +807,9 @@ int pci_bus_numa_node(PCIBus *bus)
return PCI_BUS_GET_CLASS(bus)->numa_node(bus);
}
-static int get_pci_config_device(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_pci_config_device(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field,
+ Error **errp)
{
PCIDevice *s = container_of(pv, PCIDevice, config);
uint8_t *config;
@@ -821,12 +822,12 @@ static int get_pci_config_device(QEMUFile *f, void *pv, size_t size,
for (i = 0; i < size; ++i) {
if ((config[i] ^ s->config[i]) &
s->cmask[i] & ~s->wmask[i] & ~s->w1cmask[i]) {
- error_report("%s: Bad config data: i=0x%x read: %x device: %x "
- "cmask: %x wmask: %x w1cmask:%x", __func__,
- i, config[i], s->config[i],
- s->cmask[i], s->wmask[i], s->w1cmask[i]);
+ error_setg(errp, "%s: Bad config data: i=0x%x read: %x device: %x "
+ "cmask: %x wmask: %x w1cmask:%x", __func__,
+ i, config[i], s->config[i],
+ s->cmask[i], s->wmask[i], s->w1cmask[i]);
g_free(config);
- return -EINVAL;
+ return false;
}
}
memcpy(s->config, config, size);
@@ -840,28 +841,30 @@ static int get_pci_config_device(QEMUFile *f, void *pv, size_t size,
& PCI_COMMAND_MASTER);
g_free(config);
- return 0;
+ return true;
}
/* just put buffer */
-static int put_pci_config_device(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_pci_config_device(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
const uint8_t **v = pv;
assert(size == pci_config_size(container_of(pv, PCIDevice, config)));
qemu_put_buffer(f, *v, size);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_pci_config = {
.name = "pci config",
- .get = get_pci_config_device,
- .put = put_pci_config_device,
+ .load = load_pci_config_device,
+ .save = save_pci_config_device,
};
-static int get_pci_irq_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_pci_irq_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field,
+ Error **errp)
{
PCIDevice *s = container_of(pv, PCIDevice, irq_state);
uint32_t irq_state[PCI_NUM_PINS];
@@ -869,9 +872,9 @@ static int get_pci_irq_state(QEMUFile *f, void *pv, size_t size,
for (i = 0; i < PCI_NUM_PINS; ++i) {
irq_state[i] = qemu_get_be32(f);
if (irq_state[i] != 0x1 && irq_state[i] != 0) {
- fprintf(stderr, "irq state %d: must be 0 or 1.\n",
- irq_state[i]);
- return -EINVAL;
+ error_setg(errp, "irq state %d: must be 0 or 1.",
+ irq_state[i]);
+ return false;
}
}
@@ -879,11 +882,12 @@ static int get_pci_irq_state(QEMUFile *f, void *pv, size_t size,
pci_set_irq_state(s, i, irq_state[i]);
}
- return 0;
+ return true;
}
-static int put_pci_irq_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_pci_irq_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
int i;
PCIDevice *s = container_of(pv, PCIDevice, irq_state);
@@ -892,13 +896,13 @@ static int put_pci_irq_state(QEMUFile *f, void *pv, size_t size,
qemu_put_be32(f, pci_irq_state(s, i));
}
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_pci_irq_state = {
.name = "pci irq state",
- .get = get_pci_irq_state,
- .put = put_pci_irq_state,
+ .load = load_pci_irq_state,
+ .save = save_pci_irq_state,
};
static bool migrate_is_pcie(void *opaque, int version_id)
@@ -911,17 +915,17 @@ static bool migrate_is_not_pcie(void *opaque, int version_id)
return !pci_is_express((PCIDevice *)opaque);
}
-static int pci_post_load(void *opaque, int version_id)
+static bool pci_post_load(void *opaque, int version_id, Error **errp)
{
pcie_sriov_pf_post_load(opaque);
- return 0;
+ return true;
}
const VMStateDescription vmstate_pci_device = {
.name = "PCIDevice",
.version_id = 2,
.minimum_version_id = 1,
- .post_load = pci_post_load,
+ .post_load_errp = pci_post_load,
.fields = (const VMStateField[]) {
VMSTATE_INT32_POSITIVE_LE(version_id, PCIDevice),
VMSTATE_BUFFER_UNSAFE_INFO_TEST(config, PCIDevice,
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 12/30] hw/pci/msix.c: use new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (10 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 11/30] hw/pci/pci: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 13/30] hw/pci/shpc.c: " Vladimir Sementsov-Ogievskiy
` (17 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/pci/msix.c | 17 +++++++++--------
1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/hw/pci/msix.c b/hw/pci/msix.c
index 1b23eaf1007..4dcb7c36770 100644
--- a/hw/pci/msix.c
+++ b/hw/pci/msix.c
@@ -685,25 +685,26 @@ void msix_unset_vector_notifiers(PCIDevice *dev)
dev->msix_vector_poll_notifier = NULL;
}
-static int put_msix_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool put_msix_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
msix_save(pv, f);
- return 0;
+ return true;
}
-static int get_msix_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool get_msix_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
msix_load(pv, f);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_msix = {
.name = "msix state",
- .get = get_msix_state,
- .put = put_msix_state,
+ .load = get_msix_state,
+ .save = put_msix_state,
};
const VMStateDescription vmstate_msix = {
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 13/30] hw/pci/shpc.c: use new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (11 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 12/30] hw/pci/msix.c: use " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 14/30] hw/display/virtio-gpu: move to " Vladimir Sementsov-Ogievskiy
` (16 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/pci/shpc.c | 20 +++++++++++---------
1 file changed, 11 insertions(+), 9 deletions(-)
diff --git a/hw/pci/shpc.c b/hw/pci/shpc.c
index 938602866d7..cdd2d0564ea 100644
--- a/hw/pci/shpc.c
+++ b/hw/pci/shpc.c
@@ -758,31 +758,33 @@ void shpc_cap_write_config(PCIDevice *d, uint32_t addr, uint32_t val, int l)
shpc_cap_update_dword(d);
}
-static int shpc_save(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool shpc_save(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
PCIDevice *d = container_of(pv, PCIDevice, shpc);
qemu_put_buffer(f, d->shpc->config, SHPC_SIZEOF(d));
- return 0;
+ return true;
}
-static int shpc_load(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool shpc_load(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
PCIDevice *d = container_of(pv, PCIDevice, shpc);
int ret = qemu_get_buffer(f, d->shpc->config, SHPC_SIZEOF(d));
if (ret != SHPC_SIZEOF(d)) {
- return -EINVAL;
+ error_setg(errp, "Failed to load SHPC config");
+ return false;
}
/* Make sure we don't lose notifications. An extra interrupt is harmless. */
d->shpc->msi_requested = 0;
shpc_interrupt_update(d);
- return 0;
+ return true;
}
const VMStateInfo shpc_vmstate_info = {
.name = "shpc",
- .get = shpc_load,
- .put = shpc_save,
+ .load = shpc_load,
+ .save = shpc_save,
};
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 14/30] hw/display/virtio-gpu: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (12 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 13/30] hw/pci/shpc.c: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-29 6:54 ` Akihiko Odaki
2026-08-25 21:37 ` [PATCH 15/30] hw/net/virtio-net.c: use " Vladimir Sementsov-Ogievskiy
` (15 subsequent siblings)
29 siblings, 1 reply; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin,
Alex Bennée, Akihiko Odaki, Dmitry Osipenko
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/display/virtio-gpu.c | 99 ++++++++++++++++++++++-------------------
1 file changed, 52 insertions(+), 47 deletions(-)
diff --git a/hw/display/virtio-gpu.c b/hw/display/virtio-gpu.c
index fbb6fec7a0a..1af640accdc 100644
--- a/hw/display/virtio-gpu.c
+++ b/hw/display/virtio-gpu.c
@@ -1308,13 +1308,13 @@ static const VMStateDescription vmstate_virtio_gpu_scanouts = {
},
};
-static int virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
VirtIOGPU *g = opaque;
struct virtio_gpu_simple_resource *res;
- Error *err = NULL;
- int i, ret;
+ int i;
/* in 2d mode we should never find unprocessed commands here */
assert(QTAILQ_EMPTY(&g->cmdq));
@@ -1337,12 +1337,7 @@ static int virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
}
qemu_put_be32(f, 0); /* end of list */
- ret = vmstate_save_state(f, &vmstate_virtio_gpu_scanouts, g, NULL,
- &err);
- if (ret < 0) {
- error_report_err(err);
- }
- return ret;
+ return vmstate_save_vmsd(f, &vmstate_virtio_gpu_scanouts, g, NULL, errp);
}
static bool virtio_gpu_load_restore_mapping(VirtIOGPU *g,
@@ -1374,14 +1369,13 @@ static bool virtio_gpu_load_restore_mapping(VirtIOGPU *g,
return true;
}
-static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
VirtIOGPU *g = opaque;
- Error *err = NULL;
struct virtio_gpu_simple_resource *res;
uint32_t resource_id, pformat, hostmem, rowstride_bytes;
- int i, ret;
+ int i;
g->hostmem = 0;
@@ -1389,7 +1383,8 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
while (resource_id != 0) {
res = virtio_gpu_find_resource(g, resource_id);
if (res) {
- return -EINVAL;
+ error_setg(errp, "Failed to find resource %" PRIu32, resource_id);
+ return false;
}
res = g_new0(struct virtio_gpu_simple_resource, 1);
@@ -1402,14 +1397,16 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
/* allocate */
pformat = virtio_gpu_get_pixman_format(res->format);
if (!pformat) {
+ error_setg(errp, "Unknown pixman format %" PRIu32, res->format);
g_free(res);
- return -EINVAL;
+ return false;
}
if (!calc_image_hostmem(pformat, res->width, res->height,
&hostmem, &rowstride_bytes)) {
g_free(res);
- return -EINVAL;
+ error_setg(errp, "Failed to calculate image hostmem");
+ return false;
}
res->hostmem = hostmem;
if (!qemu_pixman_image_new_shareable(&res->image,
@@ -1419,10 +1416,9 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
res->width,
res->height,
rowstride_bytes,
- &err)) {
- warn_report_err(err);
+ errp)) {
g_free(res);
- return -EINVAL;
+ return false;
}
res->addrs = g_try_new(uint64_t, res->iov_cnt);
@@ -1432,7 +1428,8 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
g_free(res->addrs);
g_free(res->iov);
g_free(res);
- return -EINVAL;
+ error_setg(errp, "Failed to allocate iov arrays");
+ return false;
}
/* read data */
@@ -1446,22 +1443,20 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
if (!virtio_gpu_load_restore_mapping(g, res)) {
pixman_image_unref(res->image);
g_free(res);
- return -EINVAL;
+ error_setg(errp, "Failed to load restore mapping");
+ return false;
}
resource_id = qemu_get_be32(f);
}
/* load & apply scanout state */
- ret = vmstate_load_state(f, &vmstate_virtio_gpu_scanouts, g, 1, &err);
- if (ret < 0) {
- error_report_err(err);
- }
- return ret;
+ return vmstate_load_vmsd(f, &vmstate_virtio_gpu_scanouts, g, 1, errp);
}
-static int virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
VirtIOGPU *g = opaque;
struct virtio_gpu_simple_resource *res;
@@ -1485,11 +1480,11 @@ static int virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
}
qemu_put_be32(f, 0); /* end of list */
- return 0;
+ return true;
}
-static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
VirtIOGPU *g = opaque;
struct virtio_gpu_simple_resource *res;
@@ -1500,7 +1495,8 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
while (resource_id != 0) {
res = virtio_gpu_find_resource(g, resource_id);
if (res) {
- return -EINVAL;
+ error_setg(errp, "Failed to find resource %" PRIu32, resource_id);
+ return false;
}
res = g_new0(struct virtio_gpu_simple_resource, 1);
@@ -1514,7 +1510,8 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
g_free(res->addrs);
g_free(res->iov);
g_free(res);
- return -EINVAL;
+ error_setg(errp, "Failed to allocate iov arrays");
+ return false;
}
/* read data */
@@ -1525,15 +1522,19 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
if (res->iov_cnt > 0 &&
iov_size(res->iov, res->iov_cnt) < res->blob_size) {
+ error_setg(errp, "iov size %" PRIu64 " < blob_size %" PRIu64,
+ (uint64_t)iov_size(res->iov, res->iov_cnt),
+ res->blob_size);
g_free(res->addrs);
g_free(res->iov);
g_free(res);
- return -EINVAL;
+ return false;
}
if (!virtio_gpu_load_restore_mapping(g, res)) {
g_free(res);
- return -EINVAL;
+ error_setg(errp, "Failed to load restore mapping");
+ return false;
}
virtio_gpu_init_udmabuf(res);
@@ -1541,10 +1542,10 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
resource_id = qemu_get_be32(f);
}
- return 0;
+ return true;
}
-static int virtio_gpu_post_load(void *opaque, int version_id)
+static bool virtio_gpu_post_load(void *opaque, int version_id, Error **errp)
{
VirtIOGPU *g = opaque;
struct virtio_gpu_scanout *scanout;
@@ -1559,7 +1560,9 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
res = virtio_gpu_find_resource(g, scanout->resource_id);
if (!res) {
- return -EINVAL;
+ error_setg(errp, "Failed to find resource %" PRIu32,
+ scanout->resource_id);
+ return false;
}
if (scanout->fb.format != 0) {
@@ -1572,12 +1575,14 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
};
if (!virtio_gpu_do_set_scanout(g, i, &scanout->fb, res, &r, &error)) {
- return -EINVAL;
+ error_setg(errp, "Failed to set scanout");
+ return false;
}
} else {
/* legacy v1 migration support */
if (!res->image) {
- return -EINVAL;
+ error_setg(errp, "No image");
+ return false;
}
scanout->ds = qemu_create_displaysurface_pixman(res->image);
qemu_displaysurface_set_share_handle(scanout->ds, res->share_handle, 0);
@@ -1591,7 +1596,7 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
res->scanout_bitmask |= (1 << i);
}
- return 0;
+ return true;
}
void virtio_gpu_device_realize(DeviceState *qdev, Error **errp)
@@ -1777,8 +1782,8 @@ const VMStateDescription vmstate_virtio_gpu_blob_state = {
.name = "virtio-gpu/blob",
.info = &(const VMStateInfo) {
.name = "blob",
- .get = virtio_gpu_blob_load,
- .put = virtio_gpu_blob_save,
+ .load = virtio_gpu_blob_load,
+ .save = virtio_gpu_blob_save,
},
.flags = VMS_SINGLE,
} /* device */,
@@ -1804,8 +1809,8 @@ static const VMStateDescription vmstate_virtio_gpu = {
.name = "virtio-gpu",
.info = &(const VMStateInfo) {
.name = "virtio-gpu",
- .get = virtio_gpu_load,
- .put = virtio_gpu_save,
+ .load = virtio_gpu_load,
+ .save = virtio_gpu_save,
},
.flags = VMS_SINGLE,
} /* device */,
@@ -1815,7 +1820,7 @@ static const VMStateDescription vmstate_virtio_gpu = {
&vmstate_virtio_gpu_blob_state,
NULL
},
- .post_load = virtio_gpu_post_load,
+ .post_load_errp = virtio_gpu_post_load,
};
static const Property virtio_gpu_properties[] = {
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 15/30] hw/net/virtio-net.c: use new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (13 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 14/30] hw/display/virtio-gpu: move to " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 16/30] hw/nvram/eeprom93xx.c: " Vladimir Sementsov-Ogievskiy
` (14 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Michael S. Tsirkin, Jason Wang
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/net/virtio-net.c | 133 ++++++++++++++++++++++----------------------
1 file changed, 66 insertions(+), 67 deletions(-)
diff --git a/hw/net/virtio-net.c b/hw/net/virtio-net.c
index 814b99a43d2..a48c87e2453 100644
--- a/hw/net/virtio-net.c
+++ b/hw/net/virtio-net.c
@@ -3198,7 +3198,8 @@ static void virtio_net_get_features(VirtIODevice *vdev, uint64_t *features,
}
}
-static int virtio_net_post_load_device(void *opaque, int version_id)
+static bool virtio_net_post_load_device(void *opaque, int version_id,
+ Error **errp)
{
VirtIONet *n = opaque;
VirtIODevice *vdev = VIRTIO_DEVICE(n);
@@ -3261,7 +3262,7 @@ static int virtio_net_post_load_device(void *opaque, int version_id)
}
virtio_net_commit_rss_config(n);
- return 0;
+ return true;
}
static int virtio_net_post_load_virtio(VirtIODevice *vdev)
@@ -3327,7 +3328,7 @@ struct VirtIONetMigTmp {
* pointer and count and also validate the count.
*/
-static int virtio_net_tx_waiting_pre_save(void *opaque)
+static bool virtio_net_tx_waiting_pre_save(void *opaque, Error **errp)
{
struct VirtIONetMigTmp *tmp = opaque;
@@ -3337,30 +3338,31 @@ static int virtio_net_tx_waiting_pre_save(void *opaque)
tmp->curr_queue_pairs_1 = 0;
}
- return 0;
+ return true;
}
-static int virtio_net_tx_waiting_pre_load(void *opaque)
+static bool virtio_net_tx_waiting_pre_load(void *opaque, Error **errp)
{
struct VirtIONetMigTmp *tmp = opaque;
/* Reuse the pointer setup from save */
- virtio_net_tx_waiting_pre_save(opaque);
+ /* TODO: handle the error in a follow-up patch */
+ virtio_net_tx_waiting_pre_save(opaque, NULL);
if (tmp->parent->curr_queue_pairs > tmp->parent->max_queue_pairs) {
- error_report("virtio-net: curr_queue_pairs %x > max_queue_pairs %x",
+ error_setg(errp, "virtio-net: curr_queue_pairs %x > max_queue_pairs %x",
tmp->parent->curr_queue_pairs, tmp->parent->max_queue_pairs);
- return -EINVAL;
+ return false;
}
- return 0; /* all good */
+ return true;
}
static const VMStateDescription vmstate_virtio_net_tx_waiting = {
.name = "virtio-net-tx_waiting",
- .pre_load = virtio_net_tx_waiting_pre_load,
- .pre_save = virtio_net_tx_waiting_pre_save,
+ .pre_load_errp = virtio_net_tx_waiting_pre_load,
+ .pre_save_errp = virtio_net_tx_waiting_pre_save,
.fields = (const VMStateField[]) {
VMSTATE_STRUCT_VARRAY_POINTER_UINT16(vqs_1, struct VirtIONetMigTmp,
curr_queue_pairs_1,
@@ -3373,31 +3375,31 @@ static const VMStateDescription vmstate_virtio_net_tx_waiting = {
/* the 'has_ufo' flag is just tested; if the incoming stream has the
* flag set we need to check that we have it
*/
-static int virtio_net_ufo_post_load(void *opaque, int version_id)
+static bool virtio_net_ufo_post_load(void *opaque, int version_id, Error **errp)
{
struct VirtIONetMigTmp *tmp = opaque;
if (tmp->has_ufo && !peer_has_ufo(tmp->parent)) {
- error_report("virtio-net: saved image requires TUN_F_UFO support");
- return -EINVAL;
+ error_setg(errp, "virtio-net: saved image requires TUN_F_UFO support");
+ return false;
}
- return 0;
+ return true;
}
-static int virtio_net_ufo_pre_save(void *opaque)
+static bool virtio_net_ufo_pre_save(void *opaque, Error **errp)
{
struct VirtIONetMigTmp *tmp = opaque;
tmp->has_ufo = tmp->parent->has_ufo;
- return 0;
+ return true;
}
static const VMStateDescription vmstate_virtio_net_has_ufo = {
.name = "virtio-net-ufo",
- .post_load = virtio_net_ufo_post_load,
- .pre_save = virtio_net_ufo_pre_save,
+ .post_load_errp = virtio_net_ufo_post_load,
+ .pre_save_errp = virtio_net_ufo_pre_save,
.fields = (const VMStateField[]) {
VMSTATE_UINT8(has_ufo, struct VirtIONetMigTmp),
VMSTATE_END_OF_LIST()
@@ -3407,38 +3409,39 @@ static const VMStateDescription vmstate_virtio_net_has_ufo = {
/* the 'has_vnet_hdr' flag is just tested; if the incoming stream has the
* flag set we need to check that we have it
*/
-static int virtio_net_vnet_post_load(void *opaque, int version_id)
+static bool virtio_net_vnet_post_load(void *opaque, int version_id,
+ Error **errp)
{
struct VirtIONetMigTmp *tmp = opaque;
if (tmp->has_vnet_hdr && !peer_has_vnet_hdr(tmp->parent)) {
- error_report("virtio-net: saved image requires vnet_hdr=on");
- return -EINVAL;
+ error_setg(errp, "virtio-net: saved image requires vnet_hdr=on");
+ return false;
}
- return 0;
+ return true;
}
-static int virtio_net_vnet_pre_save(void *opaque)
+static bool virtio_net_vnet_pre_save(void *opaque, Error **errp)
{
struct VirtIONetMigTmp *tmp = opaque;
tmp->has_vnet_hdr = tmp->parent->has_vnet_hdr;
- return 0;
+ return true;
}
static const VMStateDescription vmstate_virtio_net_has_vnet = {
.name = "virtio-net-vnet",
- .post_load = virtio_net_vnet_post_load,
- .pre_save = virtio_net_vnet_pre_save,
+ .post_load_errp = virtio_net_vnet_post_load,
+ .pre_save_errp = virtio_net_vnet_pre_save,
.fields = (const VMStateField[]) {
VMSTATE_UINT32(has_vnet_hdr, struct VirtIONetMigTmp),
VMSTATE_END_OF_LIST()
},
};
-static int virtio_net_rss_post_load(void *opaque, int version_id)
+static bool virtio_net_rss_post_load(void *opaque, int version_id, Error **errp)
{
VirtIONet *n = VIRTIO_NET(opaque);
@@ -3447,13 +3450,13 @@ static int virtio_net_rss_post_load(void *opaque, int version_id)
}
if (!virtio_net_rss_indirections_len_valid(n->rss_data.indirections_len)) {
- error_report("virtio-net: saved image has invalid RSS "
- "indirections_len: %u",
- n->rss_data.indirections_len);
- return -EINVAL;
+ error_setg(errp, "virtio-net: saved image has invalid RSS "
+ "indirections_len: %u",
+ n->rss_data.indirections_len);
+ return false;
}
- return 0;
+ return true;
}
static bool virtio_net_rss_needed(void *opaque)
@@ -3465,7 +3468,7 @@ static const VMStateDescription vmstate_virtio_net_rss = {
.name = "virtio-net-device/rss",
.version_id = 2,
.minimum_version_id = 1,
- .post_load = virtio_net_rss_post_load,
+ .post_load_errp = virtio_net_rss_post_load,
.needed = virtio_net_rss_needed,
.fields = (const VMStateField[]) {
VMSTATE_BOOL(rss_data.enabled, VirtIONet),
@@ -3507,61 +3510,57 @@ static struct vhost_dev *virtio_net_get_vhost(VirtIODevice *vdev)
return &net->dev;
}
-static int vhost_user_net_save_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field,
- JSONWriter *vmdesc)
+static bool vhost_user_net_save_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
+ ERRP_GUARD();
VirtIONet *n = pv;
VirtIODevice *vdev = VIRTIO_DEVICE(n);
struct vhost_dev *vhdev;
- Error *local_error = NULL;
int ret;
vhdev = virtio_net_get_vhost(vdev);
if (vhdev == NULL) {
- error_reportf_err(local_error,
- "Error getting vhost back-end of %s device %s: ",
- vdev->name, vdev->parent_obj.canonical_path);
- return -1;
+ error_setg(errp, "Error getting vhost back-end of %s device %s",
+ vdev->name, vdev->parent_obj.canonical_path);
+ return false;
}
- ret = vhost_save_backend_state(vhdev, f, &local_error);
+ ret = vhost_save_backend_state(vhdev, f, errp);
if (ret < 0) {
- error_reportf_err(local_error,
- "Error saving back-end state of %s device %s: ",
- vdev->name, vdev->parent_obj.canonical_path);
- return ret;
+ error_prepend(errp, "Error saving back-end state of %s device %s: ",
+ vdev->name, vdev->parent_obj.canonical_path);
+ return false;
}
- return 0;
+ return true;
}
-static int vhost_user_net_load_state(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool vhost_user_net_load_state(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
+ ERRP_GUARD();
VirtIONet *n = pv;
VirtIODevice *vdev = VIRTIO_DEVICE(n);
struct vhost_dev *vhdev;
- Error *local_error = NULL;
int ret;
vhdev = virtio_net_get_vhost(vdev);
if (vhdev == NULL) {
- error_reportf_err(local_error,
- "Error getting vhost back-end of %s device %s: ",
- vdev->name, vdev->parent_obj.canonical_path);
- return -1;
+ error_setg(errp, "Error getting vhost back-end of %s device %s",
+ vdev->name, vdev->parent_obj.canonical_path);
+ return false;
}
- ret = vhost_load_backend_state(vhdev, f, &local_error);
+ ret = vhost_load_backend_state(vhdev, f, errp);
if (ret < 0) {
- error_reportf_err(local_error,
- "Error loading back-end state of %s device %s: ",
- vdev->name, vdev->parent_obj.canonical_path);
- return ret;
+ error_prepend(errp, "Error loading back-end state of %s device %s: ",
+ vdev->name, vdev->parent_obj.canonical_path);
+ return false;
}
- return 0;
+ return true;
}
static bool vhost_user_net_is_internal_migration(void *opaque)
@@ -3587,8 +3586,8 @@ static const VMStateDescription vhost_user_net_backend_state = {
.name = "backend",
.info = &(const VMStateInfo) {
.name = "virtio-net vhost-user backend state",
- .get = vhost_user_net_load_state,
- .put = vhost_user_net_save_state,
+ .load = vhost_user_net_load_state,
+ .save = vhost_user_net_save_state,
},
},
VMSTATE_END_OF_LIST()
@@ -3599,7 +3598,7 @@ static const VMStateDescription vmstate_virtio_net_device = {
.name = "virtio-net-device",
.version_id = VIRTIO_NET_VM_VERSION,
.minimum_version_id = VIRTIO_NET_VM_VERSION,
- .post_load = virtio_net_post_load_device,
+ .post_load_errp = virtio_net_post_load_device,
.fields = (const VMStateField[]) {
VMSTATE_UINT8_ARRAY(mac, VirtIONet, ETH_ALEN),
VMSTATE_STRUCT_POINTER(vqs, VirtIONet,
@@ -4169,7 +4168,7 @@ static void virtio_net_instance_init(Object *obj)
ebpf_rss_init(&n->ebpf_rss);
}
-static int virtio_net_pre_save(void *opaque)
+static bool virtio_net_pre_save(void *opaque, Error **errp)
{
VirtIONet *n = opaque;
@@ -4177,7 +4176,7 @@ static int virtio_net_pre_save(void *opaque)
* it might keep writing to memory. */
assert(!n->vhost_started);
- return 0;
+ return true;
}
static bool primary_unplug_pending(void *opaque)
@@ -4210,7 +4209,7 @@ static const VMStateDescription vmstate_virtio_net = {
VMSTATE_VIRTIO_DEVICE,
VMSTATE_END_OF_LIST()
},
- .pre_save = virtio_net_pre_save,
+ .pre_save_errp = virtio_net_pre_save,
.dev_unplug_pending = dev_unplug_pending,
};
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 16/30] hw/nvram/eeprom93xx.c: use new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (14 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 15/30] hw/net/virtio-net.c: use " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 17/30] hw/nvram/fw_cfg.c: " Vladimir Sementsov-Ogievskiy
` (13 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Stefan Weil
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/nvram/eeprom93xx.c | 17 +++++++++--------
1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/hw/nvram/eeprom93xx.c b/hw/nvram/eeprom93xx.c
index 73b3d248d44..de689322567 100644
--- a/hw/nvram/eeprom93xx.c
+++ b/hw/nvram/eeprom93xx.c
@@ -95,28 +95,29 @@ struct _eeprom_t {
This is a Big hack, but it is how the old state did it.
*/
-static int get_uint16_from_uint8(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool get_uint16_from_uint8(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
uint16_t *v = pv;
*v = qemu_get_ubyte(f);
- return 0;
+ return true;
}
-static int put_unused(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool put_unused(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
fprintf(stderr, "uint16_from_uint8 is used only for backwards compatibility.\n");
fprintf(stderr, "Never should be used to write a new state.\n");
exit(0);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_hack_uint16_from_uint8 = {
.name = "uint16_from_uint8",
- .get = get_uint16_from_uint8,
- .put = put_unused,
+ .load = get_uint16_from_uint8,
+ .save = put_unused,
};
#define VMSTATE_UINT16_HACK_TEST(_f, _s, _t) \
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 17/30] hw/nvram/fw_cfg.c: use new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (15 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 16/30] hw/nvram/eeprom93xx.c: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 18/30] hw/usb/redirect.c: move to " Vladimir Sementsov-Ogievskiy
` (12 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Gerd Hoffmann
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/nvram/fw_cfg.c | 24 +++++++++++++-----------
1 file changed, 13 insertions(+), 11 deletions(-)
diff --git a/hw/nvram/fw_cfg.c b/hw/nvram/fw_cfg.c
index b057d870c00..5f67f5ff618 100644
--- a/hw/nvram/fw_cfg.c
+++ b/hw/nvram/fw_cfg.c
@@ -565,27 +565,28 @@ static void fw_cfg_reset(DeviceState *d)
Or we broke compatibility in the state, or we can't use struct tm
*/
-static int get_uint32_as_uint16(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool get_uint32_as_uint16(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
uint32_t *v = pv;
*v = qemu_get_be16(f);
- return 0;
+ return true;
}
-static int put_unused(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool put_unused(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
fprintf(stderr, "uint32_as_uint16 is only used for backward compatibility.\n");
fprintf(stderr, "This functions shouldn't be called.\n");
- return 0;
+ return true;
}
static const VMStateInfo vmstate_hack_uint32_as_uint16 = {
.name = "int32_as_uint16",
- .get = get_uint32_as_uint16,
- .put = put_unused,
+ .load = get_uint32_as_uint16,
+ .save = put_unused,
};
#define VMSTATE_UINT16_HACK(_f, _s, _t) \
@@ -631,7 +632,8 @@ static void fw_cfg_update_mr(FWCfgState *s, uint16_t key, size_t size)
memory_region_ram_resize(mr, size, &error_abort);
}
-static int fw_cfg_acpi_mr_restore_post_load(void *opaque, int version_id)
+static bool fw_cfg_acpi_mr_restore_post_load(void *opaque, int version_id,
+ Error **errp)
{
FWCfgState *s = opaque;
int i, index;
@@ -650,7 +652,7 @@ static int fw_cfg_acpi_mr_restore_post_load(void *opaque, int version_id)
}
}
- return 0;
+ return true;
}
static const VMStateDescription vmstate_fw_cfg_dma = {
@@ -667,7 +669,7 @@ static const VMStateDescription vmstate_fw_cfg_acpi_mr = {
.version_id = 1,
.minimum_version_id = 1,
.needed = fw_cfg_acpi_mr_restore,
- .post_load = fw_cfg_acpi_mr_restore_post_load,
+ .post_load_errp = fw_cfg_acpi_mr_restore_post_load,
.fields = (const VMStateField[]) {
VMSTATE_UINT64(table_mr_size, FWCfgState),
VMSTATE_UINT64(linker_mr_size, FWCfgState),
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 18/30] hw/usb/redirect.c: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (16 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 17/30] hw/nvram/fw_cfg.c: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 19/30] alpha/machine: " Vladimir Sementsov-Ogievskiy
` (11 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Paolo Bonzini,
Marc-André Lureau, Thomas Huth, Philippe Mathieu-Daudé,
Matthew Penney
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
hw/usb/redirect.c | 59 ++++++++++++++++++++++++++---------------------
1 file changed, 33 insertions(+), 26 deletions(-)
diff --git a/hw/usb/redirect.c b/hw/usb/redirect.c
index dfd9e8bb50c..f4196b944d5 100644
--- a/hw/usb/redirect.c
+++ b/hw/usb/redirect.c
@@ -2267,8 +2267,9 @@ static int usbredir_post_load(void *priv, int version_id)
}
/* For usbredirparser migration */
-static int usbredir_put_parser(QEMUFile *f, void *priv, size_t unused,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool usbredir_save_parser(QEMUFile *f, void *priv, size_t unused,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
USBRedirDevice *dev = priv;
uint8_t *data;
@@ -2276,7 +2277,7 @@ static int usbredir_put_parser(QEMUFile *f, void *priv, size_t unused,
if (dev->parser == NULL) {
qemu_put_be32(f, 0);
- return 0;
+ return true;
}
usbredirparser_serialize(dev->parser, &data, &len);
@@ -2290,11 +2291,11 @@ static int usbredir_put_parser(QEMUFile *f, void *priv, size_t unused,
free(data);
- return 0;
+ return true;
}
-static int usbredir_get_parser(QEMUFile *f, void *priv, size_t unused,
- const VMStateField *field)
+static bool usbredir_load_parser(QEMUFile *f, void *priv, size_t unused,
+ const VMStateField *field, Error **errp)
{
USBRedirDevice *dev = priv;
uint8_t *data;
@@ -2302,7 +2303,7 @@ static int usbredir_get_parser(QEMUFile *f, void *priv, size_t unused,
len = qemu_get_be32(f);
if (len == 0) {
- return 0;
+ return true;
}
/*
@@ -2326,19 +2327,25 @@ static int usbredir_get_parser(QEMUFile *f, void *priv, size_t unused,
g_free(data);
- return ret;
+ if (ret) {
+ error_setg(errp, "usbredirparser_unserialize failed");
+ return false;
+ }
+
+ return true;
}
static const VMStateInfo usbredir_parser_vmstate_info = {
.name = "usb-redir-parser",
- .put = usbredir_put_parser,
- .get = usbredir_get_parser,
+ .save = usbredir_save_parser,
+ .load = usbredir_load_parser,
};
/* For buffered packets (iso/irq) queue migration */
-static int usbredir_put_bufpq(QEMUFile *f, void *priv, size_t unused,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool usbredir_save_bufpq(QEMUFile *f, void *priv, size_t unused,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
struct endp_data *endp = priv;
USBRedirDevice *dev = endp->dev;
@@ -2357,11 +2364,11 @@ static int usbredir_put_bufpq(QEMUFile *f, void *priv, size_t unused,
}
assert(i == endp->bufpq_size);
- return 0;
+ return true;
}
-static int usbredir_get_bufpq(QEMUFile *f, void *priv, size_t unused,
- const VMStateField *field)
+static bool usbredir_load_bufpq(QEMUFile *f, void *priv, size_t unused,
+ const VMStateField *field, Error **errp)
{
struct endp_data *endp = priv;
USBRedirDevice *dev = endp->dev;
@@ -2385,13 +2392,13 @@ static int usbredir_get_bufpq(QEMUFile *f, void *priv, size_t unused,
DPRINTF("get_bufpq %d/%d len %d status %d\n", i + 1, endp->bufpq_size,
bufp->len, bufp->status);
}
- return 0;
+ return true;
}
static const VMStateInfo usbredir_ep_bufpq_vmstate_info = {
.name = "usb-redir-bufpq",
- .put = usbredir_put_bufpq,
- .get = usbredir_get_bufpq,
+ .save = usbredir_save_bufpq,
+ .load = usbredir_load_bufpq,
};
@@ -2468,9 +2475,9 @@ static const VMStateDescription usbredir_ep_vmstate = {
/* For PacketIdQueue migration */
-static int usbredir_put_packet_id_q(QEMUFile *f, void *priv, size_t unused,
+static bool usbredir_save_packet_id_q(QEMUFile *f, void *priv, size_t unused,
const VMStateField *field,
- JSONWriter *vmdesc)
+ JSONWriter *vmdesc, Error **errp)
{
struct PacketIdQueue *q = priv;
USBRedirDevice *dev = q->dev;
@@ -2485,11 +2492,11 @@ static int usbredir_put_packet_id_q(QEMUFile *f, void *priv, size_t unused,
}
assert(remain == 0);
- return 0;
+ return true;
}
-static int usbredir_get_packet_id_q(QEMUFile *f, void *priv, size_t unused,
- const VMStateField *field)
+static bool usbredir_load_packet_id_q(QEMUFile *f, void *priv, size_t unused,
+ const VMStateField *field, Error **errp)
{
struct PacketIdQueue *q = priv;
USBRedirDevice *dev = q->dev;
@@ -2503,13 +2510,13 @@ static int usbredir_get_packet_id_q(QEMUFile *f, void *priv, size_t unused,
packet_id_queue_add(q, id);
}
assert(q->size == size);
- return 0;
+ return true;
}
static const VMStateInfo usbredir_ep_packet_id_q_vmstate_info = {
.name = "usb-redir-packet-id-q",
- .put = usbredir_put_packet_id_q,
- .get = usbredir_get_packet_id_q,
+ .save = usbredir_save_packet_id_q,
+ .load = usbredir_load_packet_id_q,
};
static const VMStateDescription usbredir_ep_packet_id_queue_vmstate = {
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 19/30] alpha/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (17 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 18/30] hw/usb/redirect.c: move to " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:37 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 20/30] avr/machine: " Vladimir Sementsov-Ogievskiy
` (10 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:37 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Richard Henderson
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/alpha/machine.c | 17 +++++++++--------
1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/target/alpha/machine.c b/target/alpha/machine.c
index dcba5d441be..a3f67dd7b81 100644
--- a/target/alpha/machine.c
+++ b/target/alpha/machine.c
@@ -3,26 +3,27 @@
#include "migration/qemu-file-types.h"
#include "migration/vmstate.h"
-static int get_fpcr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_fpcr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
CPUAlphaState *env = opaque;
cpu_alpha_store_fpcr(env, qemu_get_be64(f));
- return 0;
+ return true;
}
-static int put_fpcr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_fpcr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
CPUAlphaState *env = opaque;
qemu_put_be64(f, cpu_alpha_load_fpcr(env));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_fpcr = {
.name = "fpcr",
- .get = get_fpcr,
- .put = put_fpcr,
+ .load = load_fpcr,
+ .save = save_fpcr,
};
static const VMStateField vmstate_env_fields[] = {
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 20/30] avr/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (18 preceding siblings ...)
2026-08-25 21:37 ` [PATCH 19/30] alpha/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 21/30] or1k/machine: " Vladimir Sementsov-Ogievskiy
` (9 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Michael Rolnik
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/avr/machine.c | 50 +++++++++++++++++++++++---------------------
1 file changed, 26 insertions(+), 24 deletions(-)
diff --git a/target/avr/machine.c b/target/avr/machine.c
index 8064a7214a3..2f6283743c7 100644
--- a/target/avr/machine.c
+++ b/target/avr/machine.c
@@ -23,78 +23,80 @@
#include "migration/qemu-file-types.h"
#include "migration/vmstate.h"
-static int get_sreg(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_sreg(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
CPUAVRState *env = opaque;
uint8_t sreg;
sreg = qemu_get_byte(f);
cpu_set_sreg(env, sreg);
- return 0;
+ return true;
}
-static int put_sreg(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_sreg(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
CPUAVRState *env = opaque;
uint8_t sreg = cpu_get_sreg(env);
qemu_put_byte(f, sreg);
- return 0;
+ return true;
}
static const VMStateInfo vms_sreg = {
.name = "sreg",
- .get = get_sreg,
- .put = put_sreg,
+ .load = load_sreg,
+ .save = save_sreg,
};
-static int get_segment(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_segment(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
uint32_t *ramp = opaque;
uint8_t temp;
temp = qemu_get_byte(f);
*ramp = ((uint32_t)temp) << 16;
- return 0;
+ return true;
}
-static int put_segment(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_segment(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
uint32_t *ramp = opaque;
uint8_t temp = *ramp >> 16;
qemu_put_byte(f, temp);
- return 0;
+ return true;
}
static const VMStateInfo vms_rampD = {
.name = "rampD",
- .get = get_segment,
- .put = put_segment,
+ .load = load_segment,
+ .save = save_segment,
};
static const VMStateInfo vms_rampX = {
.name = "rampX",
- .get = get_segment,
- .put = put_segment,
+ .load = load_segment,
+ .save = save_segment,
};
static const VMStateInfo vms_rampY = {
.name = "rampY",
- .get = get_segment,
- .put = put_segment,
+ .load = load_segment,
+ .save = save_segment,
};
static const VMStateInfo vms_rampZ = {
.name = "rampZ",
- .get = get_segment,
- .put = put_segment,
+ .load = load_segment,
+ .save = save_segment,
};
static const VMStateInfo vms_eind = {
.name = "eind",
- .get = get_segment,
- .put = put_segment,
+ .load = load_segment,
+ .save = save_segment,
};
const VMStateDescription vms_avr_cpu = {
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 21/30] or1k/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (19 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 20/30] avr/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 22/30] microblaze/machine: " Vladimir Sementsov-Ogievskiy
` (8 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Stafford Horne
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/or1k/machine.c | 17 +++++++++--------
1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/target/or1k/machine.c b/target/or1k/machine.c
index 2d5ca16c511..800dc4c21cc 100644
--- a/target/or1k/machine.c
+++ b/target/or1k/machine.c
@@ -46,26 +46,27 @@ static const VMStateDescription vmstate_cpu_tlb = {
}
};
-static int get_sr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_sr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
CPUOpenRISCState *env = opaque;
cpu_set_sr(env, qemu_get_be32(f));
- return 0;
+ return true;
}
-static int put_sr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_sr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
CPUOpenRISCState *env = opaque;
qemu_put_be32(f, cpu_get_sr(env));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_sr = {
.name = "sr",
- .get = get_sr,
- .put = put_sr,
+ .load = load_sr,
+ .save = save_sr,
};
static const VMStateDescription vmstate_env = {
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 22/30] microblaze/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (20 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 21/30] or1k/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 23/30] hppa/machine: " Vladimir Sementsov-Ogievskiy
` (7 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Edgar E. Iglesias
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/microblaze/machine.c | 17 +++++++++--------
1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/target/microblaze/machine.c b/target/microblaze/machine.c
index f930ff86091..73e741b6df2 100644
--- a/target/microblaze/machine.c
+++ b/target/microblaze/machine.c
@@ -37,28 +37,29 @@ static const VMStateDescription vmstate_mmu = {
.fields = vmstate_mmu_fields,
};
-static int get_msr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_msr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
CPUMBState *env = container_of(opaque, CPUMBState, msr);
mb_cpu_write_msr(env, qemu_get_be32(f));
- return 0;
+ return true;
}
-static int put_msr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_msr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
CPUMBState *env = container_of(opaque, CPUMBState, msr);
qemu_put_be32(f, mb_cpu_read_msr(env));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_msr = {
.name = "msr",
- .get = get_msr,
- .put = put_msr,
+ .load = load_msr,
+ .save = save_msr,
};
static const VMStateField vmstate_env_fields[] = {
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 23/30] hppa/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (21 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 22/30] microblaze/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 24/30] sparc/machine: " Vladimir Sementsov-Ogievskiy
` (6 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Richard Henderson, Helge Deller
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/hppa/machine.c | 34 ++++++++++++++++++----------------
1 file changed, 18 insertions(+), 16 deletions(-)
diff --git a/target/hppa/machine.c b/target/hppa/machine.c
index 6a143cf8df2..ddd9f27b772 100644
--- a/target/hppa/machine.c
+++ b/target/hppa/machine.c
@@ -23,30 +23,31 @@
#include "migration/vmstate.h"
-static int get_psw(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_psw(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
CPUHPPAState *env = opaque;
cpu_hppa_put_psw(env, qemu_get_be64(f));
- return 0;
+ return true;
}
-static int put_psw(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_psw(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
CPUHPPAState *env = opaque;
qemu_put_be64(f, cpu_hppa_get_psw(env));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_psw = {
.name = "psw",
- .get = get_psw,
- .put = put_psw,
+ .load = load_psw,
+ .save = save_psw,
};
-static int get_tlb(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_tlb(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
HPPATLBEntry *ent = opaque;
uint64_t val;
@@ -69,11 +70,12 @@ static int get_tlb(QEMUFile *f, void *opaque, size_t size,
ent->access_id = extract64(val, 1, 31);
ent->entry_valid = 1;
}
- return 0;
+ return true;
}
-static int put_tlb(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_tlb(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
HPPATLBEntry *ent = opaque;
uint64_t val = 0;
@@ -96,13 +98,13 @@ static int put_tlb(QEMUFile *f, void *opaque, size_t size,
qemu_put_be64(f, ent->itree.last);
qemu_put_be64(f, ent->pa);
qemu_put_be64(f, val);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_tlb_entry = {
.name = "tlb entry",
- .get = get_tlb,
- .put = put_tlb,
+ .load = load_tlb,
+ .save = save_tlb,
};
static int tlb_pre_load(void *opaque)
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 24/30] sparc/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (22 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 23/30] hppa/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 25/30] ppc/machine: " Vladimir Sementsov-Ogievskiy
` (5 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov, Mark Cave-Ayland,
Artyom Tarasenko
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/sparc/machine.c | 68 ++++++++++++++++++++++--------------------
1 file changed, 36 insertions(+), 32 deletions(-)
diff --git a/target/sparc/machine.c b/target/sparc/machine.c
index 0d5d79b5e7b..46f1e12344c 100644
--- a/target/sparc/machine.c
+++ b/target/sparc/machine.c
@@ -51,8 +51,8 @@ static const VMStateDescription vmstate_tlb_entry = {
};
#endif
-static int get_psr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_psr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
SPARCCPU *cpu = opaque;
CPUSPARCState *env = &cpu->env;
@@ -62,11 +62,12 @@ static int get_psr(QEMUFile *f, void *opaque, size_t size,
env->cwp = 0;
cpu_put_psr_raw(env, val);
- return 0;
+ return true;
}
-static int put_psr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_psr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
SPARCCPU *cpu = opaque;
CPUSPARCState *env = &cpu->env;
@@ -75,17 +76,17 @@ static int put_psr(QEMUFile *f, void *opaque, size_t size,
val = cpu_get_psr(env);
qemu_put_be32(f, val);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_psr = {
.name = "psr",
- .get = get_psr,
- .put = put_psr,
+ .load = load_psr,
+ .save = save_psr,
};
-static int get_fsr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_fsr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
SPARCCPU *cpu = opaque;
@@ -95,11 +96,12 @@ static int get_fsr(QEMUFile *f, void *opaque, size_t size,
cpu_put_fsr(&cpu->env, qemu_get_be32(f));
}
- return 0;
+ return true;
}
-static int put_fsr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_fsr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
SPARCCPU *cpu = opaque;
@@ -108,18 +110,18 @@ static int put_fsr(QEMUFile *f, void *opaque, size_t size,
} else {
qemu_put_be32(f, cpu_get_fsr(&cpu->env));
}
- return 0;
+ return true;
}
static const VMStateInfo vmstate_fsr = {
.name = "fsr",
- .get = get_fsr,
- .put = put_fsr,
+ .load = load_fsr,
+ .save = save_fsr,
};
#ifdef TARGET_SPARC64
-static int get_xcc(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_xcc(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
SPARCCPU *cpu = opaque;
CPUSPARCState *env = &cpu->env;
@@ -131,11 +133,12 @@ static int get_xcc(QEMUFile *f, void *opaque, size_t size,
env->xcc_Z = ~val & PSR_ZERO;
env->xcc_C = (val >> PSR_CARRY_SHIFT) & 1;
- return 0;
+ return true;
}
-static int put_xcc(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_xcc(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
SPARCCPU *cpu = opaque;
CPUSPARCState *env = &cpu->env;
@@ -143,17 +146,17 @@ static int put_xcc(QEMUFile *f, void *opaque, size_t size,
/* Extract just xcc out of ccr and shift into legacy position. */
qemu_put_be32(f, (val & 0xf0) << (20 - 4));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_xcc = {
.name = "xcc",
- .get = get_xcc,
- .put = put_xcc,
+ .load = load_xcc,
+ .save = save_xcc,
};
-static int get_cwp(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_cwp(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
SPARCCPU *cpu = opaque;
CPUSPARCState *env = &cpu->env;
@@ -163,24 +166,25 @@ static int get_cwp(QEMUFile *f, void *opaque, size_t size,
env->cwp = 0;
cpu_set_cwp(env, val);
- return 0;
+ return true;
}
-static int put_cwp(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_cwp(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
SPARCCPU *cpu = opaque;
CPUSPARCState *env = &cpu->env;
uint32_t val = env->cwp;
qemu_put_be32(f, val);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_cwp = {
.name = "uint32",
- .get = get_cwp,
- .put = put_cwp,
+ .load = load_cwp,
+ .save = save_cwp,
};
#else
static bool fq_needed(void *opaque)
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 25/30] ppc/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (23 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 24/30] sparc/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 26/30] mips/machine: " Vladimir Sementsov-Ogievskiy
` (4 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Nicholas Piggin, Chinmay Rath,
Glenn Miles, Harsh Prateek Bora, open list:PowerPC TCG CPUs
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/ppc/machine.c | 80 ++++++++++++++++++++++----------------------
1 file changed, 40 insertions(+), 40 deletions(-)
diff --git a/target/ppc/machine.c b/target/ppc/machine.c
index 569536bd02d..f188bb9f5ea 100644
--- a/target/ppc/machine.c
+++ b/target/ppc/machine.c
@@ -23,31 +23,31 @@ static void post_load_update_msr(CPUPPCState *env)
ppc_store_msr(env, msr);
}
-static int get_avr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_avr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
ppc_avr_t *v = pv;
v->u64[0] = qemu_get_be64(f);
v->u64[1] = qemu_get_be64(f);
- return 0;
+ return true;
}
-static int put_avr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_avr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
ppc_avr_t *v = pv;
qemu_put_be64(f, v->u64[0]);
qemu_put_be64(f, v->u64[1]);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_avr = {
.name = "avr",
- .get = get_avr,
- .put = put_avr,
+ .load = load_avr,
+ .save = save_avr,
};
#define VMSTATE_AVR_ARRAY_V(_f, _s, _n, _v) \
@@ -56,29 +56,29 @@ static const VMStateInfo vmstate_info_avr = {
#define VMSTATE_AVR_ARRAY(_f, _s, _n) \
VMSTATE_AVR_ARRAY_V(_f, _s, _n, 0)
-static int get_fpr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_fpr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
ppc_vsr_t *v = pv;
v->VsrD(0) = qemu_get_be64(f);
- return 0;
+ return true;
}
-static int put_fpr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_fpr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
ppc_vsr_t *v = pv;
qemu_put_be64(f, v->VsrD(0));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_fpr = {
.name = "fpr",
- .get = get_fpr,
- .put = put_fpr,
+ .load = load_fpr,
+ .save = save_fpr,
};
#define VMSTATE_FPR_ARRAY_V(_f, _s, _n, _v) \
@@ -87,29 +87,29 @@ static const VMStateInfo vmstate_info_fpr = {
#define VMSTATE_FPR_ARRAY(_f, _s, _n) \
VMSTATE_FPR_ARRAY_V(_f, _s, _n, 0)
-static int get_vsr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_vsr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
ppc_vsr_t *v = pv;
v->VsrD(1) = qemu_get_be64(f);
- return 0;
+ return true;
}
-static int put_vsr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_vsr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
ppc_vsr_t *v = pv;
qemu_put_be64(f, v->VsrD(1));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_vsr = {
.name = "vsr",
- .get = get_vsr,
- .put = put_vsr,
+ .load = load_vsr,
+ .save = save_vsr,
};
#define VMSTATE_VSR_ARRAY_V(_f, _s, _n, _v) \
@@ -344,26 +344,26 @@ static bool altivec_needed(void *opaque)
return cpu->env.insns_flags & PPC_ALTIVEC;
}
-static int get_vscr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_vscr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
PowerPCCPU *cpu = opaque;
ppc_store_vscr(&cpu->env, qemu_get_be32(f));
- return 0;
+ return true;
}
-static int put_vscr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_vscr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
PowerPCCPU *cpu = opaque;
qemu_put_be32(f, ppc_get_vscr(&cpu->env));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_vscr = {
.name = "cpu/altivec/vscr",
- .get = get_vscr,
- .put = put_vscr,
+ .load = load_vscr,
+ .save = save_vscr,
};
static const VMStateDescription vmstate_altivec = {
@@ -465,31 +465,31 @@ static const VMStateDescription vmstate_sr = {
};
#ifdef TARGET_PPC64
-static int get_slbe(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_slbe(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
ppc_slb_t *v = pv;
v->esid = qemu_get_be64(f);
v->vsid = qemu_get_be64(f);
- return 0;
+ return true;
}
-static int put_slbe(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_slbe(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
ppc_slb_t *v = pv;
qemu_put_be64(f, v->esid);
qemu_put_be64(f, v->vsid);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_slbe = {
.name = "slbe",
- .get = get_slbe,
- .put = put_slbe,
+ .load = load_slbe,
+ .save = save_slbe,
};
#define VMSTATE_SLB_ARRAY_V(_f, _s, _n, _v) \
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 26/30] mips/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (24 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 25/30] ppc/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 27/30] arm/machine: " Vladimir Sementsov-Ogievskiy
` (3 subsequent siblings)
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Philippe Mathieu-Daudé,
Aurelien Jarno, Jiaxun Yang, Aleksandar Rikalo
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/mips/system/machine.c | 49 ++++++++++++++++++------------------
1 file changed, 25 insertions(+), 24 deletions(-)
diff --git a/target/mips/system/machine.c b/target/mips/system/machine.c
index bd1e4002cfd..dc8a9920e5a 100644
--- a/target/mips/system/machine.c
+++ b/target/mips/system/machine.c
@@ -22,8 +22,8 @@ static int cpu_post_load(void *opaque, int version_id)
/* FPU state */
-static int get_fpr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_fpr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
int i;
fpr_t *v = pv;
@@ -31,11 +31,11 @@ static int get_fpr(QEMUFile *f, void *pv, size_t size,
for (i = 0; i < MSA_WRLEN / 64; i++) {
qemu_get_sbe64s(f, &v->wr.d[i]);
}
- return 0;
+ return true;
}
-static int put_fpr(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_fpr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
int i;
fpr_t *v = pv;
@@ -44,13 +44,13 @@ static int put_fpr(QEMUFile *f, void *pv, size_t size,
qemu_put_sbe64s(f, &v->wr.d[i]);
}
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_fpr = {
.name = "fpr",
- .get = get_fpr,
- .put = put_fpr,
+ .load = load_fpr,
+ .save = save_fpr,
};
#define VMSTATE_FPR_ARRAY_V(_f, _s, _n, _v) \
@@ -145,8 +145,9 @@ static gboolean put_octeon_llm_tree_entry(gpointer key, gpointer value,
return false;
}
-static int put_octeon_llm_tree(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_octeon_llm_tree(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
QTree *tree = *(QTree **)pv;
OcteonLLMTreePutData data = { .f = f };
@@ -157,11 +158,11 @@ static int put_octeon_llm_tree(QEMUFile *f, void *pv, size_t size,
q_tree_foreach(tree, put_octeon_llm_tree_entry, &data);
}
- return 0;
+ return true;
}
-static int get_octeon_llm_tree(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_octeon_llm_tree(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
QTree **treep = pv;
uint32_t nnodes = qemu_get_be32(f);
@@ -178,13 +179,13 @@ static int get_octeon_llm_tree(QEMUFile *f, void *pv, size_t size,
mips_octeon_llm_store(treep, addr, value);
}
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_octeon_llm_tree = {
.name = "octeon_llm_tree",
- .get = get_octeon_llm_tree,
- .put = put_octeon_llm_tree,
+ .load = load_octeon_llm_tree,
+ .save = save_octeon_llm_tree,
};
#define VMSTATE_OCTEON_LLM_TREE(_f, _s) { \
@@ -210,8 +211,8 @@ static const VMStateDescription vmstate_mvp = {
/* TLB state */
-static int get_tlb(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_tlb(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
r4k_tlb_t *v = pv;
uint16_t flags;
@@ -240,11 +241,11 @@ static int get_tlb(QEMUFile *f, void *pv, size_t size,
qemu_get_be64s(f, &v->PFN[0]);
qemu_get_be64s(f, &v->PFN[1]);
- return 0;
+ return true;
}
-static int put_tlb(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_tlb(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
r4k_tlb_t *v = pv;
@@ -275,13 +276,13 @@ static int put_tlb(QEMUFile *f, void *pv, size_t size,
qemu_put_be64s(f, &v->PFN[0]);
qemu_put_be64s(f, &v->PFN[1]);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_info_tlb = {
.name = "tlb_entry",
- .get = get_tlb,
- .put = put_tlb,
+ .load = load_tlb,
+ .save = save_tlb,
};
#define VMSTATE_TLB_ARRAY_V(_f, _s, _n, _v) \
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 27/30] arm/machine: move to new migration APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (25 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 26/30] mips/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-09-03 17:15 ` Fabiano Rosas
2026-08-25 21:38 ` [PATCH 28/30] migration/vmstate-types: convert vmstate_info_g_byte_array to new APIs Vladimir Sementsov-Ogievskiy
` (2 subsequent siblings)
29 siblings, 1 reply; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx
Cc: farosas, qemu-devel, vsementsov, Peter Maydell,
open list:ARM TCG CPUs
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
target/arm/machine.c | 107 ++++++++++++++++++++++---------------------
1 file changed, 56 insertions(+), 51 deletions(-)
diff --git a/target/arm/machine.c b/target/arm/machine.c
index 89127e5d83c..159a1f0e930 100644
--- a/target/arm/machine.c
+++ b/target/arm/machine.c
@@ -51,8 +51,8 @@ static bool vfp_fpcr_fpsr_needed(void *opaque)
(vfp_get_fpsr(env) & ~FPSCR_FPSR_MASK);
}
-static int get_fpscr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_fpscr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
@@ -62,78 +62,81 @@ static int get_fpscr(QEMUFile *f, void *opaque, size_t size,
/* 0 means we might have the data in the fpcr_fpsr subsection */
vfp_set_fpscr(env, val);
}
- return 0;
+ return true;
}
-static int put_fpscr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_fpscr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
uint32_t fpscr = vfp_fpcr_fpsr_needed(opaque) ? 0 : vfp_get_fpscr(env);
qemu_put_be32(f, fpscr);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_fpscr = {
.name = "fpscr",
- .get = get_fpscr,
- .put = put_fpscr,
+ .load = load_fpscr,
+ .save = save_fpscr,
};
-static int get_fpcr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_fpcr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
uint64_t val = qemu_get_be64(f);
vfp_set_fpcr(env, val);
- return 0;
+ return true;
}
-static int put_fpcr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_fpcr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
qemu_put_be64(f, vfp_get_fpcr(env));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_fpcr = {
.name = "fpcr",
- .get = get_fpcr,
- .put = put_fpcr,
+ .load = load_fpcr,
+ .save = save_fpcr,
};
-static int get_fpsr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_fpsr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
uint64_t val = qemu_get_be64(f);
vfp_set_fpsr(env, val);
- return 0;
+ return true;
}
-static int put_fpsr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_fpsr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
qemu_put_be64(f, vfp_get_fpsr(env));
- return 0;
+ return true;
}
static const VMStateInfo vmstate_fpsr = {
.name = "fpsr",
- .get = get_fpsr,
- .put = put_fpsr,
+ .load = load_fpsr,
+ .save = save_fpsr,
};
static const VMStateDescription vmstate_vfp_fpcr_fpsr = {
@@ -755,8 +758,8 @@ static const VMStateDescription vmstate_m_security = {
}
};
-static int get_cpsr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_cpsr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
@@ -797,22 +800,22 @@ static int get_cpsr(QEMUFile *f, void *opaque, size_t size,
}
/* Ignore the low bits, they are handled by vmstate_m. */
xpsr_write(env, val, ~XPSR_EXCP);
- return 0;
+ return true;
}
env->aarch64 = ((val & PSTATE_nRW) == 0);
if (is_a64(env)) {
pstate_write(env, val);
- return 0;
+ return true;
}
cpsr_write(env, val, 0xffffffff, CPSRWriteRaw);
- return 0;
+ return true;
}
-static int put_cpsr(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_cpsr(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
@@ -828,17 +831,17 @@ static int put_cpsr(QEMUFile *f, void *opaque, size_t size,
}
qemu_put_be32(f, val);
- return 0;
+ return true;
}
static const VMStateInfo vmstate_cpsr = {
.name = "cpsr",
- .get = get_cpsr,
- .put = put_cpsr,
+ .load = load_cpsr,
+ .save = save_cpsr,
};
-static int get_pstate64(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_pstate64(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
@@ -850,11 +853,12 @@ static int get_pstate64(QEMUFile *f, void *opaque, size_t size,
} else {
cpsr_write_from_spsr_elx(env, val);
}
- return 0;
+ return true;
}
-static int put_pstate64(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_pstate64(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field,
+ JSONWriter *vmdesc, Error **errp)
{
ARMCPU *cpu = opaque;
CPUARMState *env = &cpu->env;
@@ -866,7 +870,7 @@ static int put_pstate64(QEMUFile *f, void *opaque, size_t size,
val = cpsr_read_for_spsr_elx(env);
}
qemu_put_be64(f, val);
- return 0;
+ return true;
}
static bool pstate64_needed(void *opaque)
@@ -901,8 +905,8 @@ static const VMStateDescription vmstate_pstate64 = {
.size = sizeof(uint64_t),
.info = &(const VMStateInfo) {
.name = "pstate64",
- .get = get_pstate64,
- .put = put_pstate64,
+ .load = load_pstate64,
+ .save = save_pstate64,
},
.flags = VMS_SINGLE,
.offset = 0,
@@ -911,17 +915,17 @@ static const VMStateDescription vmstate_pstate64 = {
},
};
-static int get_power(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field)
+static bool load_power(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, Error **errp)
{
ARMCPU *cpu = opaque;
bool powered_off = qemu_get_byte(f);
arm_set_cpu_power_state(cpu, powered_off ? PSCI_OFF : PSCI_ON);
- return 0;
+ return true;
}
-static int put_power(QEMUFile *f, void *opaque, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_power(QEMUFile *f, void *opaque, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc, Error **errp)
{
ARMCPU *cpu = opaque;
@@ -931,16 +935,17 @@ static int put_power(QEMUFile *f, void *opaque, size_t size,
cpu->power_state == PSCI_OFF) {
bool powered_off = (cpu->power_state == PSCI_OFF) ? true : false;
qemu_put_byte(f, powered_off);
- return 0;
+ return true;
} else {
- return 1;
+ error_setg(errp, "Migration should not happen during power transition");
+ return false;
}
}
static const VMStateInfo vmstate_powered_off = {
.name = "powered_off",
- .get = get_power,
- .put = put_power,
+ .load = load_power,
+ .save = save_power,
};
static bool syndrome64_needed(void *opaque)
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 28/30] migration/vmstate-types: convert vmstate_info_g_byte_array to new APIs
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (26 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 27/30] arm/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-09-03 17:41 ` Fabiano Rosas
2026-08-25 21:38 ` [PATCH 29/30] migration: VMStateInfo: remove old .get / .set handlers Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 30/30] migration: finally drop vmstate_save/load_state() functions Vladimir Sementsov-Ogievskiy
29 siblings, 1 reply; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
migration/vmstate-types.c | 17 +++++++++--------
1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/migration/vmstate-types.c b/migration/vmstate-types.c
index 8c01215c251..c2d4645f317 100644
--- a/migration/vmstate-types.c
+++ b/migration/vmstate-types.c
@@ -925,30 +925,31 @@ const VMStateInfo vmstate_info_qlist = {
.save = save_qlist,
};
-static int get_g_byte_array(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field)
+static bool load_g_byte_array(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, Error **errp)
{
GByteArray *byte_array = *(GByteArray **)pv;
uint32_t len = qemu_get_be32(f);
g_byte_array_set_size(byte_array, len);
qemu_get_buffer(f, byte_array->data, len);
- return 0;
+ return true;
}
-static int put_g_byte_array(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field, JSONWriter *vmdesc)
+static bool save_g_byte_array(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, JSONWriter *vmdesc,
+ Error **errp)
{
GByteArray *byte_array = *(GByteArray **)pv;
qemu_put_be32(f, byte_array->len);
qemu_put_buffer(f, byte_array->data, byte_array->len);
- return 0;
+ return true;
}
const VMStateInfo vmstate_info_g_byte_array = {
.name = "GByteArray",
- .get = get_g_byte_array,
- .put = put_g_byte_array,
+ .load = load_g_byte_array,
+ .save = save_g_byte_array,
};
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 29/30] migration: VMStateInfo: remove old .get / .set handlers
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (27 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 28/30] migration/vmstate-types: convert vmstate_info_g_byte_array to new APIs Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 30/30] migration: finally drop vmstate_save/load_state() functions Vladimir Sementsov-Ogievskiy
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov
They are unused now.
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
include/migration/vmstate.h | 8 --------
migration/vmstate.c | 20 ++------------------
2 files changed, 2 insertions(+), 26 deletions(-)
diff --git a/include/migration/vmstate.h b/include/migration/vmstate.h
index 1b7f295417e..5e53440115e 100644
--- a/include/migration/vmstate.h
+++ b/include/migration/vmstate.h
@@ -39,17 +39,9 @@ typedef struct VMStateField VMStateField;
* these two parameters should only be used in cases when customized
* handling is needed, such as QTAILQ. For primitive data types such as
* integer, field and vmdesc parameters should be ignored inside load/save.
- *
- * @get and @put are deprecated copies of @load and @save. For new interfaces
- * use @load and @save.
*/
struct VMStateInfo {
const char *name;
- int coroutine_mixed_fn (*get)(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field);
- int coroutine_mixed_fn (*put)(QEMUFile *f, void *pv, size_t size,
- const VMStateField *field,
- JSONWriter *vmdesc);
bool coroutine_mixed_fn (*load)(QEMUFile *f, void *pv, size_t size,
const VMStateField *field,
Error **errp);
diff --git a/migration/vmstate.c b/migration/vmstate.c
index 50ebe378452..a4cf9214d54 100644
--- a/migration/vmstate.c
+++ b/migration/vmstate.c
@@ -189,18 +189,9 @@ static bool vmstate_load_field(QEMUFile *f, void *pv, size_t size,
} else if (field->flags & VMS_VSTRUCT) {
return vmstate_load_vmsd(f, field->vmsd, pv, field->struct_version_id,
errp);
- } else if (field->info->load) {
- return field->info->load(f, pv, size, field, errp);
}
- if (field->info->get(f, pv, size, field) < 0) {
- error_setg(errp,
- "Failed to load element of type %s for %s",
- field->info->name, field->name);
- return false;
- }
-
- return true;
+ return field->info->load(f, pv, size, field, errp);
}
static bool vmstate_post_load(const VMStateDescription *vmsd,
@@ -583,16 +574,9 @@ static bool vmstate_save_field(QEMUFile *f, void *pv, size_t size,
} else if (field->flags & VMS_VSTRUCT) {
return vmstate_save_vmsd_v(f, field->vmsd, pv, vmdesc,
field->struct_version_id, errp);
- } else if (field->info->save) {
- return field->info->save(f, pv, size, field, vmdesc, errp);
}
- if (field->info->put(f, pv, size, field, vmdesc) < 0) {
- error_setg(errp, "put failed");
- return false;
- }
-
- return true;
+ return field->info->save(f, pv, size, field, vmdesc, errp);
}
/*
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* [PATCH 30/30] migration: finally drop vmstate_save/load_state() functions
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
` (28 preceding siblings ...)
2026-08-25 21:38 ` [PATCH 29/30] migration: VMStateInfo: remove old .get / .set handlers Vladimir Sementsov-Ogievskiy
@ 2026-08-25 21:38 ` Vladimir Sementsov-Ogievskiy
29 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-25 21:38 UTC (permalink / raw)
To: peterx; +Cc: farosas, qemu-devel, vsementsov
Now they are unused.
Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
include/migration/vmstate.h | 9 ---------
migration/vmstate.c | 12 ------------
2 files changed, 21 deletions(-)
diff --git a/include/migration/vmstate.h b/include/migration/vmstate.h
index 5e53440115e..b86386f14a9 100644
--- a/include/migration/vmstate.h
+++ b/include/migration/vmstate.h
@@ -1307,15 +1307,6 @@ extern const VMStateInfo vmstate_info_g_byte_array;
.flags = VMS_END, \
}
-/*
- * vmstate_load_state() and vmstate_save_state() are
- * depreacated, use vmstate_load_vmsd() and vmstate_save_vmsd()
- * instead.
- */
-int vmstate_load_state(QEMUFile *f, const VMStateDescription *vmsd,
- void *opaque, int version_id, Error **errp);
-int vmstate_save_state(QEMUFile *f, const VMStateDescription *vmsd,
- void *opaque, JSONWriter *vmdesc, Error **errp);
bool vmstate_load_vmsd(QEMUFile *f, const VMStateDescription *vmsd,
void *opaque, int version_id, Error **errp);
bool vmstate_save_vmsd(QEMUFile *f, const VMStateDescription *vmsd,
diff --git a/migration/vmstate.c b/migration/vmstate.c
index a4cf9214d54..f8424234118 100644
--- a/migration/vmstate.c
+++ b/migration/vmstate.c
@@ -880,15 +880,3 @@ static bool vmstate_subsection_save(QEMUFile *f, const VMStateDescription *vmsd,
return true;
}
-
-int vmstate_save_state(QEMUFile *f, const VMStateDescription *vmsd,
- void *opaque, JSONWriter *vmdesc_id, Error **errp)
-{
- return vmstate_save_vmsd(f, vmsd, opaque, vmdesc_id, errp) ? 0 : -EINVAL;
-}
-
-int vmstate_load_state(QEMUFile *f, const VMStateDescription *vmsd,
- void *opaque, int version_id, Error **errp)
-{
- return vmstate_load_vmsd(f, vmsd, opaque, version_id, errp) ? 0 : -EINVAL;
-}
--
2.43.0
^ permalink raw reply related [flat|nested] 39+ messages in thread
* Re: [PATCH 01/30] tests/unit/test-vmstate: move to new migration APIs
2026-08-25 21:37 ` [PATCH 01/30] tests/unit/test-vmstate: " Vladimir Sementsov-Ogievskiy
@ 2026-08-29 5:55 ` Akihiko Odaki
2026-09-03 17:12 ` Fabiano Rosas
1 sibling, 0 replies; 39+ messages in thread
From: Akihiko Odaki @ 2026-08-29 5:55 UTC (permalink / raw)
To: Vladimir Sementsov-Ogievskiy, peterx
Cc: farosas, qemu-devel, Juraj Marcin, Alexander Mikhalitsyn
On 2026/08/26 6:37, Vladimir Sementsov-Ogievskiy wrote:
> Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
Reviewed-by: Akihiko Odaki <odaki@rsg.ci.i.u-tokyo.ac.jp>
Regards,
Akihiko Odaki
^ permalink raw reply [flat|nested] 39+ messages in thread
* Re: [PATCH 14/30] hw/display/virtio-gpu: move to new migration APIs
2026-08-25 21:37 ` [PATCH 14/30] hw/display/virtio-gpu: move to " Vladimir Sementsov-Ogievskiy
@ 2026-08-29 6:54 ` Akihiko Odaki
2026-08-29 19:30 ` Vladimir Sementsov-Ogievskiy
0 siblings, 1 reply; 39+ messages in thread
From: Akihiko Odaki @ 2026-08-29 6:54 UTC (permalink / raw)
To: Vladimir Sementsov-Ogievskiy, peterx
Cc: farosas, qemu-devel, Michael S. Tsirkin, Alex Bennée,
Dmitry Osipenko
On 2026/08/26 6:37, Vladimir Sementsov-Ogievskiy wrote:
> Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
> ---
> hw/display/virtio-gpu.c | 99 ++++++++++++++++++++++-------------------
> 1 file changed, 52 insertions(+), 47 deletions(-)
>
> diff --git a/hw/display/virtio-gpu.c b/hw/display/virtio-gpu.c
> index fbb6fec7a0a..1af640accdc 100644
> --- a/hw/display/virtio-gpu.c
> +++ b/hw/display/virtio-gpu.c
> @@ -1308,13 +1308,13 @@ static const VMStateDescription vmstate_virtio_gpu_scanouts = {
> },
> };
>
> -static int virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, JSONWriter *vmdesc,
> + Error **errp)
> {
> VirtIOGPU *g = opaque;
> struct virtio_gpu_simple_resource *res;
> - Error *err = NULL;
> - int i, ret;
> + int i;
>
> /* in 2d mode we should never find unprocessed commands here */
> assert(QTAILQ_EMPTY(&g->cmdq));
> @@ -1337,12 +1337,7 @@ static int virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
> }
> qemu_put_be32(f, 0); /* end of list */
>
> - ret = vmstate_save_state(f, &vmstate_virtio_gpu_scanouts, g, NULL,
> - &err);
> - if (ret < 0) {
> - error_report_err(err);
> - }
> - return ret;
> + return vmstate_save_vmsd(f, &vmstate_virtio_gpu_scanouts, g, NULL, errp);
> }
>
> static bool virtio_gpu_load_restore_mapping(VirtIOGPU *g,
> @@ -1374,14 +1369,13 @@ static bool virtio_gpu_load_restore_mapping(VirtIOGPU *g,
> return true;
> }
>
> -static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> VirtIOGPU *g = opaque;
> - Error *err = NULL;
> struct virtio_gpu_simple_resource *res;
> uint32_t resource_id, pformat, hostmem, rowstride_bytes;
> - int i, ret;
> + int i;
>
> g->hostmem = 0;
>
> @@ -1389,7 +1383,8 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
> while (resource_id != 0) {
> res = virtio_gpu_find_resource(g, resource_id);
> if (res) {
> - return -EINVAL;
> + error_setg(errp, "Failed to find resource %" PRIu32, resource_id);
> + return false;
> }
>
> res = g_new0(struct virtio_gpu_simple_resource, 1);
> @@ -1402,14 +1397,16 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
> /* allocate */
> pformat = virtio_gpu_get_pixman_format(res->format);
> if (!pformat) {
> + error_setg(errp, "Unknown pixman format %" PRIu32, res->format);
> g_free(res);
> - return -EINVAL;
> + return false;
> }
>
> if (!calc_image_hostmem(pformat, res->width, res->height,
> &hostmem, &rowstride_bytes)) {
> g_free(res);
> - return -EINVAL;
> + error_setg(errp, "Failed to calculate image hostmem");
> + return false;
> }
> res->hostmem = hostmem;
> if (!qemu_pixman_image_new_shareable(&res->image,
> @@ -1419,10 +1416,9 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
> res->width,
> res->height,
> rowstride_bytes,
> - &err)) {
> - warn_report_err(err);
> + errp)) {
> g_free(res);
> - return -EINVAL;
> + return false;
> }
>
> res->addrs = g_try_new(uint64_t, res->iov_cnt);
> @@ -1432,7 +1428,8 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
> g_free(res->addrs);
> g_free(res->iov);
> g_free(res);
> - return -EINVAL;
> + error_setg(errp, "Failed to allocate iov arrays");
> + return false;
> }
>
> /* read data */
> @@ -1446,22 +1443,20 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
> if (!virtio_gpu_load_restore_mapping(g, res)) {
> pixman_image_unref(res->image);
> g_free(res);
> - return -EINVAL;
> + error_setg(errp, "Failed to load restore mapping");
> + return false;
> }
>
> resource_id = qemu_get_be32(f);
> }
>
> /* load & apply scanout state */
> - ret = vmstate_load_state(f, &vmstate_virtio_gpu_scanouts, g, 1, &err);
> - if (ret < 0) {
> - error_report_err(err);
> - }
> - return ret;
> + return vmstate_load_vmsd(f, &vmstate_virtio_gpu_scanouts, g, 1, errp);
> }
>
> -static int virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, JSONWriter *vmdesc,
> + Error **errp)
> {
> VirtIOGPU *g = opaque;
> struct virtio_gpu_simple_resource *res;
> @@ -1485,11 +1480,11 @@ static int virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
> }
> qemu_put_be32(f, 0); /* end of list */
>
> - return 0;
> + return true;
> }
>
> -static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> VirtIOGPU *g = opaque;
> struct virtio_gpu_simple_resource *res;
> @@ -1500,7 +1495,8 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
> while (resource_id != 0) {
> res = virtio_gpu_find_resource(g, resource_id);
> if (res) {
> - return -EINVAL;
> + error_setg(errp, "Failed to find resource %" PRIu32, resource_id);
> + return false;
> }
>
> res = g_new0(struct virtio_gpu_simple_resource, 1);
> @@ -1514,7 +1510,8 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
> g_free(res->addrs);
> g_free(res->iov);
> g_free(res);
> - return -EINVAL;
> + error_setg(errp, "Failed to allocate iov arrays");
> + return false;
> }
>
> /* read data */
> @@ -1525,15 +1522,19 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
>
> if (res->iov_cnt > 0 &&
> iov_size(res->iov, res->iov_cnt) < res->blob_size) {
> + error_setg(errp, "iov size %" PRIu64 " < blob_size %" PRIu64,
> + (uint64_t)iov_size(res->iov, res->iov_cnt),
nitpick: I somewhat prefer:
error_setg(errp, "iov size %zu < blob_size %" PRIu64,
iov_size(res->iov, res->iov_cnt),
because:
- it does not require thinking about the cast. The conditional above
does perform implicit cast, but it automatically picks the wider type.
The explicit cast here doesn't so requires a little more thought.
- it requries less typing.
And this hunk cannot be applied due to recent virtio-gpu fixes. Please
rebase it.
> + res->blob_size);
> g_free(res->addrs);
> g_free(res->iov);
> g_free(res);
> - return -EINVAL;
> + return false;
> }
>
> if (!virtio_gpu_load_restore_mapping(g, res)) {
> g_free(res);
> - return -EINVAL;
> + error_setg(errp, "Failed to load restore mapping");
Let's say: "Failed to restore loaded mapping"
> + return false;
> }
>
> virtio_gpu_init_udmabuf(res);
> @@ -1541,10 +1542,10 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
> resource_id = qemu_get_be32(f);
> }
>
> - return 0;
> + return true;
> }
>
> -static int virtio_gpu_post_load(void *opaque, int version_id)
> +static bool virtio_gpu_post_load(void *opaque, int version_id, Error **errp)
> {
> VirtIOGPU *g = opaque;
> struct virtio_gpu_scanout *scanout;
> @@ -1559,7 +1560,9 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
>
> res = virtio_gpu_find_resource(g, scanout->resource_id);
> if (!res) {
> - return -EINVAL;
> + error_setg(errp, "Failed to find resource %" PRIu32,
> + scanout->resource_id);
> + return false;
> }
>
> if (scanout->fb.format != 0) {
> @@ -1572,12 +1575,14 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
> };
>
> if (!virtio_gpu_do_set_scanout(g, i, &scanout->fb, res, &r, &error)) {
> - return -EINVAL;
> + error_setg(errp, "Failed to set scanout");
> + return false;
> }
> } else {
> /* legacy v1 migration support */
> if (!res->image) {
> - return -EINVAL;
> + error_setg(errp, "No image");
Let's say: "A blob scanout lacks metadata".
Regards,
Akihiko Odaki
> + return false;
> }
> scanout->ds = qemu_create_displaysurface_pixman(res->image);
> qemu_displaysurface_set_share_handle(scanout->ds, res->share_handle, 0);
> @@ -1591,7 +1596,7 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
> res->scanout_bitmask |= (1 << i);
> }
>
> - return 0;
> + return true;
> }
>
> void virtio_gpu_device_realize(DeviceState *qdev, Error **errp)
> @@ -1777,8 +1782,8 @@ const VMStateDescription vmstate_virtio_gpu_blob_state = {
> .name = "virtio-gpu/blob",
> .info = &(const VMStateInfo) {
> .name = "blob",
> - .get = virtio_gpu_blob_load,
> - .put = virtio_gpu_blob_save,
> + .load = virtio_gpu_blob_load,
> + .save = virtio_gpu_blob_save,
> },
> .flags = VMS_SINGLE,
> } /* device */,
> @@ -1804,8 +1809,8 @@ static const VMStateDescription vmstate_virtio_gpu = {
> .name = "virtio-gpu",
> .info = &(const VMStateInfo) {
> .name = "virtio-gpu",
> - .get = virtio_gpu_load,
> - .put = virtio_gpu_save,
> + .load = virtio_gpu_load,
> + .save = virtio_gpu_save,
> },
> .flags = VMS_SINGLE,
> } /* device */,
> @@ -1815,7 +1820,7 @@ static const VMStateDescription vmstate_virtio_gpu = {
> &vmstate_virtio_gpu_blob_state,
> NULL
> },
> - .post_load = virtio_gpu_post_load,
> + .post_load_errp = virtio_gpu_post_load,
> };
>
> static const Property virtio_gpu_properties[] = {
^ permalink raw reply [flat|nested] 39+ messages in thread
* Re: [PATCH 14/30] hw/display/virtio-gpu: move to new migration APIs
2026-08-29 6:54 ` Akihiko Odaki
@ 2026-08-29 19:30 ` Vladimir Sementsov-Ogievskiy
0 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-08-29 19:30 UTC (permalink / raw)
To: Akihiko Odaki, peterx
Cc: farosas, qemu-devel, Michael S. Tsirkin, Alex Bennée,
Dmitry Osipenko
On 29.08.26 09:54, Akihiko Odaki wrote:
> On 2026/08/26 6:37, Vladimir Sementsov-Ogievskiy wrote:
>> Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
>> ---
>> hw/display/virtio-gpu.c | 99 ++++++++++++++++++++++-------------------
>> 1 file changed, 52 insertions(+), 47 deletions(-)
>>
>> diff --git a/hw/display/virtio-gpu.c b/hw/display/virtio-gpu.c
>> index fbb6fec7a0a..1af640accdc 100644
>> --- a/hw/display/virtio-gpu.c
>> +++ b/hw/display/virtio-gpu.c
>> @@ -1308,13 +1308,13 @@ static const VMStateDescription vmstate_virtio_gpu_scanouts = {
>> },
>> };
>> -static int virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
>> - const VMStateField *field, JSONWriter *vmdesc)
>> +static bool virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
>> + const VMStateField *field, JSONWriter *vmdesc,
>> + Error **errp)
>> {
>> VirtIOGPU *g = opaque;
>> struct virtio_gpu_simple_resource *res;
>> - Error *err = NULL;
>> - int i, ret;
>> + int i;
>> /* in 2d mode we should never find unprocessed commands here */
>> assert(QTAILQ_EMPTY(&g->cmdq));
>> @@ -1337,12 +1337,7 @@ static int virtio_gpu_save(QEMUFile *f, void *opaque, size_t size,
>> }
>> qemu_put_be32(f, 0); /* end of list */
>> - ret = vmstate_save_state(f, &vmstate_virtio_gpu_scanouts, g, NULL,
>> - &err);
>> - if (ret < 0) {
>> - error_report_err(err);
>> - }
>> - return ret;
>> + return vmstate_save_vmsd(f, &vmstate_virtio_gpu_scanouts, g, NULL, errp);
>> }
>> static bool virtio_gpu_load_restore_mapping(VirtIOGPU *g,
>> @@ -1374,14 +1369,13 @@ static bool virtio_gpu_load_restore_mapping(VirtIOGPU *g,
>> return true;
>> }
>> -static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
>> - const VMStateField *field)
>> +static bool virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
>> + const VMStateField *field, Error **errp)
>> {
>> VirtIOGPU *g = opaque;
>> - Error *err = NULL;
>> struct virtio_gpu_simple_resource *res;
>> uint32_t resource_id, pformat, hostmem, rowstride_bytes;
>> - int i, ret;
>> + int i;
>> g->hostmem = 0;
>> @@ -1389,7 +1383,8 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
>> while (resource_id != 0) {
>> res = virtio_gpu_find_resource(g, resource_id);
>> if (res) {
>> - return -EINVAL;
>> + error_setg(errp, "Failed to find resource %" PRIu32, resource_id);
>> + return false;
>> }
>> res = g_new0(struct virtio_gpu_simple_resource, 1);
>> @@ -1402,14 +1397,16 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
>> /* allocate */
>> pformat = virtio_gpu_get_pixman_format(res->format);
>> if (!pformat) {
>> + error_setg(errp, "Unknown pixman format %" PRIu32, res->format);
>> g_free(res);
>> - return -EINVAL;
>> + return false;
>> }
>> if (!calc_image_hostmem(pformat, res->width, res->height,
>> &hostmem, &rowstride_bytes)) {
>> g_free(res);
>> - return -EINVAL;
>> + error_setg(errp, "Failed to calculate image hostmem");
>> + return false;
>> }
>> res->hostmem = hostmem;
>> if (!qemu_pixman_image_new_shareable(&res->image,
>> @@ -1419,10 +1416,9 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
>> res->width,
>> res->height,
>> rowstride_bytes,
>> - &err)) {
>> - warn_report_err(err);
>> + errp)) {
>> g_free(res);
>> - return -EINVAL;
>> + return false;
>> }
>> res->addrs = g_try_new(uint64_t, res->iov_cnt);
>> @@ -1432,7 +1428,8 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
>> g_free(res->addrs);
>> g_free(res->iov);
>> g_free(res);
>> - return -EINVAL;
>> + error_setg(errp, "Failed to allocate iov arrays");
>> + return false;
>> }
>> /* read data */
>> @@ -1446,22 +1443,20 @@ static int virtio_gpu_load(QEMUFile *f, void *opaque, size_t size,
>> if (!virtio_gpu_load_restore_mapping(g, res)) {
>> pixman_image_unref(res->image);
>> g_free(res);
>> - return -EINVAL;
>> + error_setg(errp, "Failed to load restore mapping");
>> + return false;
>> }
>> resource_id = qemu_get_be32(f);
>> }
>> /* load & apply scanout state */
>> - ret = vmstate_load_state(f, &vmstate_virtio_gpu_scanouts, g, 1, &err);
>> - if (ret < 0) {
>> - error_report_err(err);
>> - }
>> - return ret;
>> + return vmstate_load_vmsd(f, &vmstate_virtio_gpu_scanouts, g, 1, errp);
>> }
>> -static int virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
>> - const VMStateField *field, JSONWriter *vmdesc)
>> +static bool virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
>> + const VMStateField *field, JSONWriter *vmdesc,
>> + Error **errp)
>> {
>> VirtIOGPU *g = opaque;
>> struct virtio_gpu_simple_resource *res;
>> @@ -1485,11 +1480,11 @@ static int virtio_gpu_blob_save(QEMUFile *f, void *opaque, size_t size,
>> }
>> qemu_put_be32(f, 0); /* end of list */
>> - return 0;
>> + return true;
>> }
>> -static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
>> - const VMStateField *field)
>> +static bool virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
>> + const VMStateField *field, Error **errp)
>> {
>> VirtIOGPU *g = opaque;
>> struct virtio_gpu_simple_resource *res;
>> @@ -1500,7 +1495,8 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
>> while (resource_id != 0) {
>> res = virtio_gpu_find_resource(g, resource_id);
>> if (res) {
>> - return -EINVAL;
>> + error_setg(errp, "Failed to find resource %" PRIu32, resource_id);
>> + return false;
>> }
>> res = g_new0(struct virtio_gpu_simple_resource, 1);
>> @@ -1514,7 +1510,8 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
>> g_free(res->addrs);
>> g_free(res->iov);
>> g_free(res);
>> - return -EINVAL;
>> + error_setg(errp, "Failed to allocate iov arrays");
>> + return false;
>> }
>> /* read data */
>> @@ -1525,15 +1522,19 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
>> if (res->iov_cnt > 0 &&
>> iov_size(res->iov, res->iov_cnt) < res->blob_size) {
>> + error_setg(errp, "iov size %" PRIu64 " < blob_size %" PRIu64,
>> + (uint64_t)iov_size(res->iov, res->iov_cnt),
>
> nitpick: I somewhat prefer:
>
> error_setg(errp, "iov size %zu < blob_size %" PRIu64,
> iov_size(res->iov, res->iov_cnt),
>
> because:
>
> - it does not require thinking about the cast. The conditional above
> does perform implicit cast, but it automatically picks the wider type.
> The explicit cast here doesn't so requires a little more thought.
>
> - it requries less typing.
>
> And this hunk cannot be applied due to recent virtio-gpu fixes. Please rebase it.
>
>> + res->blob_size);
>> g_free(res->addrs);
>> g_free(res->iov);
>> g_free(res);
>> - return -EINVAL;
>> + return false;
>> }
>> if (!virtio_gpu_load_restore_mapping(g, res)) {
>> g_free(res);
>> - return -EINVAL;
>> + error_setg(errp, "Failed to load restore mapping");
>
> Let's say: "Failed to restore loaded mapping"
>
>> + return false;
>> }
>> virtio_gpu_init_udmabuf(res);
>> @@ -1541,10 +1542,10 @@ static int virtio_gpu_blob_load(QEMUFile *f, void *opaque, size_t size,
>> resource_id = qemu_get_be32(f);
>> }
>> - return 0;
>> + return true;
>> }
>> -static int virtio_gpu_post_load(void *opaque, int version_id)
>> +static bool virtio_gpu_post_load(void *opaque, int version_id, Error **errp)
>> {
>> VirtIOGPU *g = opaque;
>> struct virtio_gpu_scanout *scanout;
>> @@ -1559,7 +1560,9 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
>> res = virtio_gpu_find_resource(g, scanout->resource_id);
>> if (!res) {
>> - return -EINVAL;
>> + error_setg(errp, "Failed to find resource %" PRIu32,
>> + scanout->resource_id);
>> + return false;
>> }
>> if (scanout->fb.format != 0) {
>> @@ -1572,12 +1575,14 @@ static int virtio_gpu_post_load(void *opaque, int version_id)
>> };
>> if (!virtio_gpu_do_set_scanout(g, i, &scanout->fb, res, &r, &error)) {
>> - return -EINVAL;
>> + error_setg(errp, "Failed to set scanout");
>> + return false;
>> }
>> } else {
>> /* legacy v1 migration support */
>> if (!res->image) {
>> - return -EINVAL;
>> + error_setg(errp, "No image");
>
> Let's say: "A blob scanout lacks metadata".
>
> Regards,
> Akihiko Odaki
Thanks for reviewing! Will apply all suggestions in v2.
--
Best regards,
Vladimir
^ permalink raw reply [flat|nested] 39+ messages in thread
* Re: [PATCH 01/30] tests/unit/test-vmstate: move to new migration APIs
2026-08-25 21:37 ` [PATCH 01/30] tests/unit/test-vmstate: " Vladimir Sementsov-Ogievskiy
2026-08-29 5:55 ` Akihiko Odaki
@ 2026-09-03 17:12 ` Fabiano Rosas
1 sibling, 0 replies; 39+ messages in thread
From: Fabiano Rosas @ 2026-09-03 17:12 UTC (permalink / raw)
To: Vladimir Sementsov-Ogievskiy, peterx
Cc: qemu-devel, vsementsov, Juraj Marcin, Alexander Mikhalitsyn,
Akihiko Odaki
Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru> writes:
> Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
> ---
> tests/unit/test-vmstate.c | 118 ++++++++++----------------------------
> 1 file changed, 30 insertions(+), 88 deletions(-)
>
> diff --git a/tests/unit/test-vmstate.c b/tests/unit/test-vmstate.c
> index df1fb4c7780..23f31730703 100644
> --- a/tests/unit/test-vmstate.c
> +++ b/tests/unit/test-vmstate.c
> @@ -67,14 +67,9 @@ static QEMUFile *open_test_file(bool write)
> static void save_vmstate(const VMStateDescription *desc, void *obj)
> {
> QEMUFile *f = open_test_file(true);
> - Error *local_err = NULL;
>
> /* Save file with vmstate */
> - int ret = vmstate_save_state(f, desc, obj, NULL, &local_err);
> - if (ret) {
> - error_report_err(local_err);
> - }
> - g_assert(!ret);
> + vmstate_save_vmsd(f, desc, obj, NULL, &error_abort);
> qemu_put_byte(f, QEMU_VM_EOF);
> g_assert(!qemu_file_get_error(f));
> qemu_fclose(f);
> @@ -112,7 +107,6 @@ static int load_vmstate_one(const VMStateDescription *desc, void *obj,
> int version, const uint8_t *wire, size_t size)
> {
> QEMUFile *f;
> - int ret;
> Error *local_err = NULL;
>
> f = open_test_file(true);
> @@ -120,15 +114,16 @@ static int load_vmstate_one(const VMStateDescription *desc, void *obj,
> qemu_fclose(f);
>
> f = open_test_file(false);
> - ret = vmstate_load_state(f, desc, obj, version, &local_err);
> - if (ret) {
> + if (!vmstate_load_vmsd(f, desc, obj, version, &local_err)) {
> error_report_err(local_err);
> g_assert(qemu_file_get_error(f));
> - } else{
> - g_assert(!qemu_file_get_error(f));
> + qemu_fclose(f);
> + return -EINVAL;
> }
> +
> + g_assert(!qemu_file_get_error(f));
> qemu_fclose(f);
> - return ret;
> + return 0;
> }
>
>
> @@ -362,8 +357,6 @@ static const VMStateDescription vmstate_versioned = {
>
> static void test_load_v1(void)
> {
> - Error *local_err = NULL;
> - int ret;
> uint8_t buf[] = {
> 0, 0, 0, 10, /* a */
> 0, 0, 0, 30, /* c */
> @@ -374,10 +367,7 @@ static void test_load_v1(void)
>
> QEMUFile *loading = open_test_file(false);
> TestStruct obj = { .b = 200, .e = 500, .f = 600 };
> - ret = vmstate_load_state(loading, &vmstate_versioned, &obj, 1, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(loading, &vmstate_versioned, &obj, 1, &error_abort);
> g_assert(!qemu_file_get_error(loading));
> g_assert_cmpint(obj.a, ==, 10);
> g_assert_cmpint(obj.b, ==, 200);
> @@ -390,8 +380,6 @@ static void test_load_v1(void)
>
> static void test_load_v2(void)
> {
> - Error *local_err = NULL;
> - int ret;
> uint8_t buf[] = {
> 0, 0, 0, 10, /* a */
> 0, 0, 0, 20, /* b */
> @@ -405,10 +393,7 @@ static void test_load_v2(void)
>
> QEMUFile *loading = open_test_file(false);
> TestStruct obj;
> - ret = vmstate_load_state(loading, &vmstate_versioned, &obj, 2, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(loading, &vmstate_versioned, &obj, 2, &error_abort);
> g_assert_cmpint(obj.a, ==, 10);
> g_assert_cmpint(obj.b, ==, 20);
> g_assert_cmpint(obj.c, ==, 30);
> @@ -442,16 +427,10 @@ static const VMStateDescription vmstate_skipping = {
>
> static void test_save_noskip(void)
> {
> - Error *local_err = NULL;
> QEMUFile *fsave = open_test_file(true);
> TestStruct obj = { .a = 1, .b = 2, .c = 3, .d = 4, .e = 5, .f = 6,
> .skip_c_e = false };
> - int ret = vmstate_save_state(fsave, &vmstate_skipping, &obj, NULL,
> - &local_err);
> - if (ret) {
> - error_report_err(local_err);
> - }
> - g_assert(!ret);
> + vmstate_save_vmsd(fsave, &vmstate_skipping, &obj, NULL, &error_abort);
> g_assert(!qemu_file_get_error(fsave));
>
> uint8_t expected[] = {
> @@ -469,16 +448,10 @@ static void test_save_noskip(void)
>
> static void test_save_skip(void)
> {
> - Error *local_err = NULL;
> QEMUFile *fsave = open_test_file(true);
> TestStruct obj = { .a = 1, .b = 2, .c = 3, .d = 4, .e = 5, .f = 6,
> .skip_c_e = true };
> - int ret = vmstate_save_state(fsave, &vmstate_skipping, &obj, NULL,
> - &local_err);
> - if (ret) {
> - error_report_err(local_err);
> - }
> - g_assert(!ret);
> + vmstate_save_vmsd(fsave, &vmstate_skipping, &obj, NULL, &error_abort);
> g_assert(!qemu_file_get_error(fsave));
>
> uint8_t expected[] = {
> @@ -494,8 +467,6 @@ static void test_save_skip(void)
>
> static void test_load_noskip(void)
> {
> - Error *local_err = NULL;
> - int ret;
> uint8_t buf[] = {
> 0, 0, 0, 10, /* a */
> 0, 0, 0, 20, /* b */
> @@ -509,10 +480,7 @@ static void test_load_noskip(void)
>
> QEMUFile *loading = open_test_file(false);
> TestStruct obj = { .skip_c_e = false };
> - ret = vmstate_load_state(loading, &vmstate_skipping, &obj, 2, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(loading, &vmstate_skipping, &obj, 2, &error_abort);
> g_assert(!qemu_file_get_error(loading));
> g_assert_cmpint(obj.a, ==, 10);
> g_assert_cmpint(obj.b, ==, 20);
> @@ -525,8 +493,6 @@ static void test_load_noskip(void)
>
> static void test_load_skip(void)
> {
> - Error *local_err = NULL;
> - int ret;
> uint8_t buf[] = {
> 0, 0, 0, 10, /* a */
> 0, 0, 0, 20, /* b */
> @@ -538,10 +504,7 @@ static void test_load_skip(void)
>
> QEMUFile *loading = open_test_file(false);
> TestStruct obj = { .skip_c_e = true, .c = 300, .e = 500 };
> - ret = vmstate_load_state(loading, &vmstate_skipping, &obj, 2, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(loading, &vmstate_skipping, &obj, 2, &error_abort);
> g_assert(!qemu_file_get_error(loading));
> g_assert_cmpint(obj.a, ==, 10);
> g_assert_cmpint(obj.b, ==, 20);
> @@ -863,8 +826,6 @@ static void test_save_q(void)
>
> static void test_load_q(void)
> {
> - int ret;
> - Error *local_err = NULL;
> TestQtailq obj_q = {
> .i16 = -512,
> .i32 = 70000,
> @@ -894,10 +855,7 @@ static void test_load_q(void)
> TestQtailq tgt;
>
> QTAILQ_INIT(&tgt.q);
> - ret = vmstate_load_state(fload, &vmstate_q, &tgt, 1, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(fload, &vmstate_q, &tgt, 1, &error_abort);
> char eof = qemu_get_byte(fload);
> g_assert(!qemu_file_get_error(fload));
> g_assert_cmpint(tgt.i16, ==, obj_q.i16);
> @@ -1015,29 +973,29 @@ static void destroy_domain(gpointer data)
> g_free(domain);
> }
>
> -static int domain_preload(void *opaque)
> +static bool domain_preload(void *opaque, Error **errp)
> {
> TestGTreeDomain *domain = opaque;
>
> domain->mappings = g_tree_new_full((GCompareDataFunc)interval_cmp,
> NULL, g_free, g_free);
> - return 0;
> + return true;
> }
>
> -static int iommu_preload(void *opaque)
> +static bool iommu_preload(void *opaque, Error **errp)
> {
> TestGTreeIOMMU *iommu = opaque;
>
> iommu->domains = g_tree_new_full((GCompareDataFunc)int_cmp,
> NULL, NULL, destroy_domain);
> - return 0;
> + return true;
> }
>
> static const VMStateDescription vmstate_domain = {
> .name = "domain",
> .version_id = 1,
> .minimum_version_id = 1,
> - .pre_load = domain_preload,
> + .pre_load_errp = domain_preload,
> .fields = (const VMStateField[]) {
> VMSTATE_INT32(id, TestGTreeDomain),
> VMSTATE_GTREE_V(mappings, TestGTreeDomain, 1,
> @@ -1073,7 +1031,7 @@ static const VMStateDescription vmstate_iommu = {
> .name = "iommu",
> .version_id = 1,
> .minimum_version_id = 1,
> - .pre_load = iommu_preload,
> + .pre_load_errp = iommu_preload,
> .fields = (const VMStateField[]) {
> VMSTATE_INT32(id, TestGTreeIOMMU),
> VMSTATE_GTREE_DIRECT_KEY_V(domains, TestGTreeIOMMU, 1,
> @@ -1239,8 +1197,6 @@ static void diff_iommu(TestGTreeIOMMU *iommu1, TestGTreeIOMMU *iommu2)
>
> static void test_gtree_load_domain(void)
> {
> - Error *local_err = NULL;
> - int ret;
> TestGTreeDomain *dest_domain = g_new0(TestGTreeDomain, 1);
> TestGTreeDomain *orig_domain = create_first_domain();
> QEMUFile *fload, *fsave;
> @@ -1253,11 +1209,7 @@ static void test_gtree_load_domain(void)
>
> fload = open_test_file(false);
>
> - ret = vmstate_load_state(fload, &vmstate_domain, dest_domain, 1,
> - &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(fload, &vmstate_domain, dest_domain, 1, &error_abort);
> eof = qemu_get_byte(fload);
> g_assert(!qemu_file_get_error(fload));
> g_assert_cmpint(orig_domain->id, ==, dest_domain->id);
> @@ -1360,8 +1312,6 @@ static void test_gtree_save_iommu(void)
>
> static void test_gtree_load_iommu(void)
> {
> - Error *local_err = NULL;
> - int ret;
> TestGTreeIOMMU *dest_iommu = g_new0(TestGTreeIOMMU, 1);
> TestGTreeIOMMU *orig_iommu = create_iommu();
> QEMUFile *fsave, *fload;
> @@ -1373,10 +1323,7 @@ static void test_gtree_load_iommu(void)
> qemu_fclose(fsave);
>
> fload = open_test_file(false);
> - ret = vmstate_load_state(fload, &vmstate_iommu, dest_iommu, 1, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(fload, &vmstate_iommu, dest_iommu, 1, &error_abort);
> eof = qemu_get_byte(fload);
> g_assert(!qemu_file_get_error(fload));
> g_assert_cmpint(orig_iommu->id, ==, dest_iommu->id);
> @@ -1498,8 +1445,6 @@ static void test_save_qlist(void)
>
> static void test_load_qlist(void)
> {
> - Error *local_err = NULL;
> - int ret;
> QEMUFile *fsave, *fload;
> TestQListContainer *orig_container = alloc_container();
> TestQListContainer *dest_container = g_new0(TestQListContainer, 1);
> @@ -1513,11 +1458,8 @@ static void test_load_qlist(void)
> qemu_fclose(fsave);
>
> fload = open_test_file(false);
> - ret = vmstate_load_state(fload, &vmstate_container, dest_container, 1,
> - &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + vmstate_load_vmsd(fload, &vmstate_container, dest_container, 1,
> + &error_abort);
> eof = qemu_get_byte(fload);
> g_assert(!qemu_file_get_error(fload));
> g_assert_cmpint(eof, ==, QEMU_VM_EOF);
> @@ -1534,22 +1476,22 @@ typedef struct TmpTestStruct {
> int64_t diff;
> } TmpTestStruct;
>
> -static int tmp_child_pre_save(void *opaque)
> +static bool tmp_child_pre_save(void *opaque, Error **errp)
> {
> struct TmpTestStruct *tts = opaque;
>
> tts->diff = tts->parent->b - tts->parent->a;
>
> - return 0;
> + return true;
> }
>
> -static int tmp_child_post_load(void *opaque, int version_id)
> +static bool tmp_child_post_load(void *opaque, int version_id, Error **errp)
> {
> struct TmpTestStruct *tts = opaque;
>
> tts->parent->b = tts->parent->a + tts->diff;
>
> - return 0;
> + return true;
> }
>
> static const VMStateDescription vmstate_tmp_back_to_parent = {
> @@ -1562,8 +1504,8 @@ static const VMStateDescription vmstate_tmp_back_to_parent = {
>
> static const VMStateDescription vmstate_tmp_child = {
> .name = "test/tmp_child",
> - .pre_save = tmp_child_pre_save,
> - .post_load = tmp_child_post_load,
> + .pre_save_errp = tmp_child_pre_save,
> + .post_load_errp = tmp_child_post_load,
> .fields = (const VMStateField[]) {
> VMSTATE_INT64(diff, TmpTestStruct),
> VMSTATE_STRUCT_POINTER(parent, TmpTestStruct,
Reviewed-by: Fabiano Rosas <farosas@suse.de>
^ permalink raw reply [flat|nested] 39+ messages in thread
* Re: [PATCH 27/30] arm/machine: move to new migration APIs
2026-08-25 21:38 ` [PATCH 27/30] arm/machine: " Vladimir Sementsov-Ogievskiy
@ 2026-09-03 17:15 ` Fabiano Rosas
0 siblings, 0 replies; 39+ messages in thread
From: Fabiano Rosas @ 2026-09-03 17:15 UTC (permalink / raw)
To: Vladimir Sementsov-Ogievskiy, peterx
Cc: qemu-devel, vsementsov, Peter Maydell, open list:ARM TCG CPUs
Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru> writes:
> Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
> ---
> target/arm/machine.c | 107 ++++++++++++++++++++++---------------------
> 1 file changed, 56 insertions(+), 51 deletions(-)
>
> diff --git a/target/arm/machine.c b/target/arm/machine.c
> index 89127e5d83c..159a1f0e930 100644
> --- a/target/arm/machine.c
> +++ b/target/arm/machine.c
> @@ -51,8 +51,8 @@ static bool vfp_fpcr_fpsr_needed(void *opaque)
> (vfp_get_fpsr(env) & ~FPSCR_FPSR_MASK);
> }
>
> -static int get_fpscr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool load_fpscr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> @@ -62,78 +62,81 @@ static int get_fpscr(QEMUFile *f, void *opaque, size_t size,
> /* 0 means we might have the data in the fpcr_fpsr subsection */
> vfp_set_fpscr(env, val);
> }
> - return 0;
> + return true;
> }
>
> -static int put_fpscr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool save_fpscr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field,
> + JSONWriter *vmdesc, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> uint32_t fpscr = vfp_fpcr_fpsr_needed(opaque) ? 0 : vfp_get_fpscr(env);
>
> qemu_put_be32(f, fpscr);
> - return 0;
> + return true;
> }
>
> static const VMStateInfo vmstate_fpscr = {
> .name = "fpscr",
> - .get = get_fpscr,
> - .put = put_fpscr,
> + .load = load_fpscr,
> + .save = save_fpscr,
> };
>
> -static int get_fpcr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool load_fpcr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> uint64_t val = qemu_get_be64(f);
>
> vfp_set_fpcr(env, val);
> - return 0;
> + return true;
> }
>
> -static int put_fpcr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool save_fpcr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field,
> + JSONWriter *vmdesc, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
>
> qemu_put_be64(f, vfp_get_fpcr(env));
> - return 0;
> + return true;
> }
>
> static const VMStateInfo vmstate_fpcr = {
> .name = "fpcr",
> - .get = get_fpcr,
> - .put = put_fpcr,
> + .load = load_fpcr,
> + .save = save_fpcr,
> };
>
> -static int get_fpsr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool load_fpsr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> uint64_t val = qemu_get_be64(f);
>
> vfp_set_fpsr(env, val);
> - return 0;
> + return true;
> }
>
> -static int put_fpsr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool save_fpsr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field,
> + JSONWriter *vmdesc, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
>
> qemu_put_be64(f, vfp_get_fpsr(env));
> - return 0;
> + return true;
> }
>
> static const VMStateInfo vmstate_fpsr = {
> .name = "fpsr",
> - .get = get_fpsr,
> - .put = put_fpsr,
> + .load = load_fpsr,
> + .save = save_fpsr,
> };
>
> static const VMStateDescription vmstate_vfp_fpcr_fpsr = {
> @@ -755,8 +758,8 @@ static const VMStateDescription vmstate_m_security = {
> }
> };
>
> -static int get_cpsr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool load_cpsr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> @@ -797,22 +800,22 @@ static int get_cpsr(QEMUFile *f, void *opaque, size_t size,
> }
> /* Ignore the low bits, they are handled by vmstate_m. */
> xpsr_write(env, val, ~XPSR_EXCP);
> - return 0;
> + return true;
> }
>
> env->aarch64 = ((val & PSTATE_nRW) == 0);
>
> if (is_a64(env)) {
> pstate_write(env, val);
> - return 0;
> + return true;
> }
>
> cpsr_write(env, val, 0xffffffff, CPSRWriteRaw);
> - return 0;
> + return true;
> }
>
> -static int put_cpsr(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool save_cpsr(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, JSONWriter *vmdesc, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> @@ -828,17 +831,17 @@ static int put_cpsr(QEMUFile *f, void *opaque, size_t size,
> }
>
> qemu_put_be32(f, val);
> - return 0;
> + return true;
> }
>
> static const VMStateInfo vmstate_cpsr = {
> .name = "cpsr",
> - .get = get_cpsr,
> - .put = put_cpsr,
> + .load = load_cpsr,
> + .save = save_cpsr,
> };
>
> -static int get_pstate64(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool load_pstate64(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> @@ -850,11 +853,12 @@ static int get_pstate64(QEMUFile *f, void *opaque, size_t size,
> } else {
> cpsr_write_from_spsr_elx(env, val);
> }
> - return 0;
> + return true;
> }
>
> -static int put_pstate64(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool save_pstate64(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field,
> + JSONWriter *vmdesc, Error **errp)
> {
> ARMCPU *cpu = opaque;
> CPUARMState *env = &cpu->env;
> @@ -866,7 +870,7 @@ static int put_pstate64(QEMUFile *f, void *opaque, size_t size,
> val = cpsr_read_for_spsr_elx(env);
> }
> qemu_put_be64(f, val);
> - return 0;
> + return true;
> }
>
> static bool pstate64_needed(void *opaque)
> @@ -901,8 +905,8 @@ static const VMStateDescription vmstate_pstate64 = {
> .size = sizeof(uint64_t),
> .info = &(const VMStateInfo) {
> .name = "pstate64",
> - .get = get_pstate64,
> - .put = put_pstate64,
> + .load = load_pstate64,
> + .save = save_pstate64,
> },
> .flags = VMS_SINGLE,
> .offset = 0,
> @@ -911,17 +915,17 @@ static const VMStateDescription vmstate_pstate64 = {
> },
> };
>
> -static int get_power(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field)
> +static bool load_power(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, Error **errp)
> {
> ARMCPU *cpu = opaque;
> bool powered_off = qemu_get_byte(f);
> arm_set_cpu_power_state(cpu, powered_off ? PSCI_OFF : PSCI_ON);
> - return 0;
> + return true;
> }
>
> -static int put_power(QEMUFile *f, void *opaque, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool save_power(QEMUFile *f, void *opaque, size_t size,
> + const VMStateField *field, JSONWriter *vmdesc, Error **errp)
> {
> ARMCPU *cpu = opaque;
>
> @@ -931,16 +935,17 @@ static int put_power(QEMUFile *f, void *opaque, size_t size,
> cpu->power_state == PSCI_OFF) {
> bool powered_off = (cpu->power_state == PSCI_OFF) ? true : false;
> qemu_put_byte(f, powered_off);
> - return 0;
> + return true;
> } else {
> - return 1;
> + error_setg(errp, "Migration should not happen during power transition");
> + return false;
> }
> }
>
> static const VMStateInfo vmstate_powered_off = {
> .name = "powered_off",
> - .get = get_power,
> - .put = put_power,
> + .load = load_power,
> + .save = save_power,
> };
>
> static bool syndrome64_needed(void *opaque)
../target/arm/machine.c: In function ‘save_power’:
../target/arm/machine.c:940:9: error: implicit declaration of function ‘error_setg’ [-Wimplicit-function-declaration]
940 | error_setg(errp, "Migration should not happen during power transition");
| ^~~~~~~~~~
../target/arm/machine.c:940:9: error: nested extern declaration of ‘error_setg’ [-Werror=nested-externs]
^ permalink raw reply [flat|nested] 39+ messages in thread
* Re: [PATCH 04/30] hw/virtio: config save/load: move to new migration APIs
2026-08-25 21:37 ` [PATCH 04/30] hw/virtio: config save/load: " Vladimir Sementsov-Ogievskiy
@ 2026-09-03 17:41 ` Fabiano Rosas
2026-09-04 21:01 ` Vladimir Sementsov-Ogievskiy
0 siblings, 1 reply; 39+ messages in thread
From: Fabiano Rosas @ 2026-09-03 17:41 UTC (permalink / raw)
To: Vladimir Sementsov-Ogievskiy, peterx
Cc: qemu-devel, vsementsov, Michael S. Tsirkin, Cornelia Huck,
Halil Pasic, Eric Farman, Richard Henderson, Ilya Leoshkevich,
David Hildenbrand, Matthew Rosato, Christian Borntraeger,
open list:virtio-ccw
Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru> writes:
> Stop ignoring the error on save path.
>
> Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
> ---
> hw/pci/pci.c | 27 +++++++++++----------------
> hw/s390x/virtio-ccw.c | 19 ++++---------------
> hw/virtio/virtio-mmio.c | 10 +++++++---
> hw/virtio/virtio-pci.c | 24 +++++++++++++++---------
> hw/virtio/virtio.c | 11 +++++++----
> include/hw/pci/pci.h | 4 ++--
> include/hw/virtio/virtio-bus.h | 4 ++--
> 7 files changed, 48 insertions(+), 51 deletions(-)
>
> diff --git a/hw/pci/pci.c b/hw/pci/pci.c
> index d3191609e28..76d006fa1d7 100644
> --- a/hw/pci/pci.c
> +++ b/hw/pci/pci.c
> @@ -940,37 +940,32 @@ const VMStateDescription vmstate_pci_device = {
> };
>
>
> -void pci_device_save(PCIDevice *s, QEMUFile *f)
> +bool pci_device_save(PCIDevice *s, QEMUFile *f, Error **errp)
> {
> - Error *local_err = NULL;
> - int ret;
> + bool ok;
>
> /* Clear interrupt status bit: it is implicit
> * in irq_state which we are saving.
> * This makes us compatible with old devices
> * which never set or clear this bit. */
> s->config[PCI_STATUS] &= ~PCI_STATUS_INTERRUPT;
> - ret = vmstate_save_state(f, &vmstate_pci_device, s, NULL, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> +
> + ok = vmstate_save_vmsd(f, &vmstate_pci_device, s, NULL, errp);
> +
> /* Restore the interrupt status bit. */
> pci_update_irq_status(s);
> +
> + return ok;
> }
>
> -int pci_device_load(PCIDevice *s, QEMUFile *f)
> +bool pci_device_load(PCIDevice *s, QEMUFile *f, Error **errp)
> {
> - Error *local_err = NULL;
> - int ret;
> + bool ok = vmstate_load_vmsd(f, &vmstate_pci_device, s, s->version_id, errp);
>
> - ret = vmstate_load_state(f, &vmstate_pci_device, s, s->version_id,
> - &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> /* Restore the interrupt status bit. */
> pci_update_irq_status(s);
> - return ret;
> +
> + return ok;
> }
>
> static void pci_set_default_subsystem_id(PCIDevice *pci_dev)
> diff --git a/hw/s390x/virtio-ccw.c b/hw/s390x/virtio-ccw.c
> index d82874ed27e..848ed09e94b 100644
> --- a/hw/s390x/virtio-ccw.c
> +++ b/hw/s390x/virtio-ccw.c
> @@ -1129,29 +1129,18 @@ static int virtio_ccw_load_queue(DeviceState *d, int n, QEMUFile *f)
> return 0;
> }
>
> -static void virtio_ccw_save_config(DeviceState *d, QEMUFile *f)
> +static bool virtio_ccw_save_config(DeviceState *d, QEMUFile *f, Error **errp)
> {
> VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(d);
> - Error *local_err = NULL;
> - int ret;
>
> - ret = vmstate_save_state(f, &vmstate_virtio_ccw_dev, dev, NULL, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> + return vmstate_save_vmsd(f, &vmstate_virtio_ccw_dev, dev, NULL, errp);
> }
>
> -static int virtio_ccw_load_config(DeviceState *d, QEMUFile *f)
> +static bool virtio_ccw_load_config(DeviceState *d, QEMUFile *f, Error **errp)
> {
> VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(d);
> - Error *local_err = NULL;
> - int ret;
>
> - ret = vmstate_load_state(f, &vmstate_virtio_ccw_dev, dev, 1, &local_err);
> - if (ret < 0) {
> - error_report_err(local_err);
> - }
> - return ret;
> + return vmstate_load_vmsd(f, &vmstate_virtio_ccw_dev, dev, 1, errp);
> }
>
> static void virtio_ccw_pre_plugged(DeviceState *d, Error **errp)
> diff --git a/hw/virtio/virtio-mmio.c b/hw/virtio/virtio-mmio.c
> index 559363e4438..ef34b76913e 100644
> --- a/hw/virtio/virtio-mmio.c
> +++ b/hw/virtio/virtio-mmio.c
> @@ -547,23 +547,27 @@ static void virtio_mmio_update_irq(DeviceState *opaque, uint16_t vector)
> qemu_set_irq(proxy->irq, level);
> }
>
> -static int virtio_mmio_load_config(DeviceState *opaque, QEMUFile *f)
> +static bool virtio_mmio_load_config(DeviceState *opaque, QEMUFile *f,
> + Error **errp)
> {
> VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque);
>
> proxy->host_features_sel = qemu_get_be32(f);
> proxy->guest_features_sel = qemu_get_be32(f);
> proxy->guest_page_shift = qemu_get_be32(f);
> - return 0;
> + return true;
> }
>
> -static void virtio_mmio_save_config(DeviceState *opaque, QEMUFile *f)
> +static bool virtio_mmio_save_config(DeviceState *opaque, QEMUFile *f,
> + Error **errp)
> {
> VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque);
>
> qemu_put_be32(f, proxy->host_features_sel);
> qemu_put_be32(f, proxy->guest_features_sel);
> qemu_put_be32(f, proxy->guest_page_shift);
> +
> + return true;
> }
>
> static const VMStateDescription vmstate_virtio_mmio_queue_state = {
> diff --git a/hw/virtio/virtio-pci.c b/hw/virtio/virtio-pci.c
> index 7a5d4f35e33..07941319be2 100644
> --- a/hw/virtio/virtio-pci.c
> +++ b/hw/virtio/virtio-pci.c
> @@ -84,15 +84,21 @@ static void virtio_pci_notify(DeviceState *d, uint16_t vector)
> }
> }
>
> -static void virtio_pci_save_config(DeviceState *d, QEMUFile *f)
> +static bool virtio_pci_save_config(DeviceState *d, QEMUFile *f, Error **errp)
> {
> VirtIOPCIProxy *proxy = to_virtio_pci_proxy(d);
> VirtIODevice *vdev = virtio_bus_get_device(&proxy->bus);
>
> - pci_device_save(&proxy->pci_dev, f);
> + if (!pci_device_save(&proxy->pci_dev, f, errp)) {
> + return false;
> + }
> +
> msix_save(&proxy->pci_dev, f);
> - if (msix_present(&proxy->pci_dev))
> + if (msix_present(&proxy->pci_dev)) {
> qemu_put_be16(f, vdev->config_vector);
> + }
> +
> + return true;
> }
>
> static const VMStateDescription vmstate_virtio_pci_modern_queue_state = {
> @@ -209,24 +215,24 @@ static void virtio_pci_save_queue(DeviceState *d, int n, QEMUFile *f)
> qemu_put_be16(f, virtio_queue_vector(vdev, n));
> }
>
> -static int virtio_pci_load_config(DeviceState *d, QEMUFile *f)
> +static bool virtio_pci_load_config(DeviceState *d, QEMUFile *f, Error **errp)
> {
This function is returning 0
> VirtIOPCIProxy *proxy = to_virtio_pci_proxy(d);
> VirtIODevice *vdev = virtio_bus_get_device(&proxy->bus);
> uint16_t vector;
>
> - int ret;
> - ret = pci_device_load(&proxy->pci_dev, f);
> - if (ret) {
> - return ret;
> + if (!pci_device_load(&proxy->pci_dev, f, errp)) {
> + return false;
> }
> +
> msix_unuse_all_vectors(&proxy->pci_dev);
> msix_load(&proxy->pci_dev, f);
> if (msix_present(&proxy->pci_dev)) {
> qemu_get_be16s(f, &vector);
>
> if (vector != VIRTIO_NO_VECTOR && vector >= proxy->nvectors) {
> - return -EINVAL;
> + error_setg(errp, "load config: unexpected vector %" PRIu16, vector);
> + return false;
> }
> } else {
> vector = VIRTIO_NO_VECTOR;
> diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c
> index 8230a383aff..0f7c8acead0 100644
> --- a/hw/virtio/virtio.c
> +++ b/hw/virtio/virtio.c
> @@ -3077,7 +3077,10 @@ int virtio_save(VirtIODevice *vdev, QEMUFile *f)
> Error *local_err = NULL;
>
> if (k->save_config) {
> - k->save_config(qbus->parent, f);
> + if (!k->save_config(qbus->parent, f, &local_err)) {
> + error_report_err(local_err);
> + return -EINVAL;
> + }
> }
>
> qemu_put_8s(f, &vdev->status);
> @@ -3526,9 +3529,9 @@ virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
> vdev->device_endian = VIRTIO_DEVICE_ENDIAN_UNKNOWN;
>
> if (k->load_config) {
> - ret = k->load_config(qbus->parent, f);
> - if (ret)
> - return ret;
> + if (!k->load_config(qbus->parent, f, &local_err)) {
> + return -EINVAL;
> + }
> }
>
> qemu_get_8s(f, &vdev->status);
> diff --git a/include/hw/pci/pci.h b/include/hw/pci/pci.h
> index f2448e941a0..7c3fdc05630 100644
> --- a/include/hw/pci/pci.h
> +++ b/include/hw/pci/pci.h
> @@ -270,8 +270,8 @@ uint32_t pci_default_read_config(PCIDevice *d,
> uint32_t address, int len);
> void pci_default_write_config(PCIDevice *d,
> uint32_t address, uint32_t val, int len);
> -void pci_device_save(PCIDevice *s, QEMUFile *f);
> -int pci_device_load(PCIDevice *s, QEMUFile *f);
> +bool pci_device_save(PCIDevice *s, QEMUFile *f, Error **errp);
> +bool pci_device_load(PCIDevice *s, QEMUFile *f, Error **errp);
> MemoryRegion *pci_address_space(PCIDevice *dev);
> MemoryRegion *pci_address_space_io(PCIDevice *dev);
>
> diff --git a/include/hw/virtio/virtio-bus.h b/include/hw/virtio/virtio-bus.h
> index 255ecb2fcb2..1b9867002b8 100644
> --- a/include/hw/virtio/virtio-bus.h
> +++ b/include/hw/virtio/virtio-bus.h
> @@ -41,10 +41,10 @@ struct VirtioBusClass {
> /* This is what a VirtioBus must implement */
> BusClass parent;
> void (*notify)(DeviceState *d, uint16_t vector);
> - void (*save_config)(DeviceState *d, QEMUFile *f);
> + bool (*save_config)(DeviceState *d, QEMUFile *f, Error **errp);
> void (*save_queue)(DeviceState *d, int n, QEMUFile *f);
> bool (*save_extra_state)(DeviceState *d, QEMUFile *f, Error **errp);
> - int (*load_config)(DeviceState *d, QEMUFile *f);
> + bool (*load_config)(DeviceState *d, QEMUFile *f, Error **errp);
> int (*load_queue)(DeviceState *d, int n, QEMUFile *f);
> int (*load_done)(DeviceState *d, QEMUFile *f);
> bool (*load_extra_state)(DeviceState *d, QEMUFile *f, Error **errp);
^ permalink raw reply [flat|nested] 39+ messages in thread
* Re: [PATCH 28/30] migration/vmstate-types: convert vmstate_info_g_byte_array to new APIs
2026-08-25 21:38 ` [PATCH 28/30] migration/vmstate-types: convert vmstate_info_g_byte_array to new APIs Vladimir Sementsov-Ogievskiy
@ 2026-09-03 17:41 ` Fabiano Rosas
0 siblings, 0 replies; 39+ messages in thread
From: Fabiano Rosas @ 2026-09-03 17:41 UTC (permalink / raw)
To: Vladimir Sementsov-Ogievskiy, peterx; +Cc: qemu-devel, vsementsov
Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru> writes:
> Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
> ---
> migration/vmstate-types.c | 17 +++++++++--------
> 1 file changed, 9 insertions(+), 8 deletions(-)
>
> diff --git a/migration/vmstate-types.c b/migration/vmstate-types.c
> index 8c01215c251..c2d4645f317 100644
> --- a/migration/vmstate-types.c
> +++ b/migration/vmstate-types.c
> @@ -925,30 +925,31 @@ const VMStateInfo vmstate_info_qlist = {
> .save = save_qlist,
> };
>
> -static int get_g_byte_array(QEMUFile *f, void *pv, size_t size,
> - const VMStateField *field)
> +static bool load_g_byte_array(QEMUFile *f, void *pv, size_t size,
> + const VMStateField *field, Error **errp)
> {
> GByteArray *byte_array = *(GByteArray **)pv;
> uint32_t len = qemu_get_be32(f);
>
> g_byte_array_set_size(byte_array, len);
> qemu_get_buffer(f, byte_array->data, len);
> - return 0;
> + return true;
> }
>
> -static int put_g_byte_array(QEMUFile *f, void *pv, size_t size,
> - const VMStateField *field, JSONWriter *vmdesc)
> +static bool save_g_byte_array(QEMUFile *f, void *pv, size_t size,
> + const VMStateField *field, JSONWriter *vmdesc,
> + Error **errp)
> {
> GByteArray *byte_array = *(GByteArray **)pv;
>
> qemu_put_be32(f, byte_array->len);
> qemu_put_buffer(f, byte_array->data, byte_array->len);
>
> - return 0;
> + return true;
> }
>
> const VMStateInfo vmstate_info_g_byte_array = {
> .name = "GByteArray",
> - .get = get_g_byte_array,
> - .put = put_g_byte_array,
> + .load = load_g_byte_array,
> + .save = save_g_byte_array,
> };
Reviewed-by: Fabiano Rosas <farosas@suse.de>
^ permalink raw reply [flat|nested] 39+ messages in thread
* Re: [PATCH 04/30] hw/virtio: config save/load: move to new migration APIs
2026-09-03 17:41 ` Fabiano Rosas
@ 2026-09-04 21:01 ` Vladimir Sementsov-Ogievskiy
0 siblings, 0 replies; 39+ messages in thread
From: Vladimir Sementsov-Ogievskiy @ 2026-09-04 21:01 UTC (permalink / raw)
To: Fabiano Rosas, peterx
Cc: qemu-devel, Michael S. Tsirkin, Cornelia Huck, Halil Pasic,
Eric Farman, Richard Henderson, Ilya Leoshkevich,
David Hildenbrand, Matthew Rosato, Christian Borntraeger,
open list:virtio-ccw
On 03.09.26 20:41, Fabiano Rosas wrote:
>> }
>>
>> -static int virtio_pci_load_config(DeviceState *d, QEMUFile *f)
>> +static bool virtio_pci_load_config(DeviceState *d, QEMUFile *f, Error **errp)
>> {
> This function is returning 0
Oops right, thanks! Will fix.
--
Best regards,
Vladimir
^ permalink raw reply [flat|nested] 39+ messages in thread
end of thread, other threads:[~2026-09-04 21:01 UTC | newest]
Thread overview: 39+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-08-25 21:37 [PATCH 00/30] move to new migration APIs Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 01/30] tests/unit/test-vmstate: " Vladimir Sementsov-Ogievskiy
2026-08-29 5:55 ` Akihiko Odaki
2026-09-03 17:12 ` Fabiano Rosas
2026-08-25 21:37 ` [PATCH 02/30] ui/vdagent: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 03/30] hw/virtio: extra state: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 04/30] hw/virtio: config save/load: " Vladimir Sementsov-Ogievskiy
2026-09-03 17:41 ` Fabiano Rosas
2026-09-04 21:01 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 05/30] hw/virtio: make virtio_save() and virtio_load() static Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 06/30] hw/virtio: remaining: move to new migration APIs Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 07/30] hw/s390x/virtio-ccw.c: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 08/30] hw/scsi/spapr_vscsi: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 09/30] hw/scsi/scsi-bus.c: use " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 10/30] hw/vfio/pci: move to " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 11/30] hw/pci/pci: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 12/30] hw/pci/msix.c: use " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 13/30] hw/pci/shpc.c: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 14/30] hw/display/virtio-gpu: move to " Vladimir Sementsov-Ogievskiy
2026-08-29 6:54 ` Akihiko Odaki
2026-08-29 19:30 ` Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 15/30] hw/net/virtio-net.c: use " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 16/30] hw/nvram/eeprom93xx.c: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 17/30] hw/nvram/fw_cfg.c: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 18/30] hw/usb/redirect.c: move to " Vladimir Sementsov-Ogievskiy
2026-08-25 21:37 ` [PATCH 19/30] alpha/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 20/30] avr/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 21/30] or1k/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 22/30] microblaze/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 23/30] hppa/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 24/30] sparc/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 25/30] ppc/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 26/30] mips/machine: " Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 27/30] arm/machine: " Vladimir Sementsov-Ogievskiy
2026-09-03 17:15 ` Fabiano Rosas
2026-08-25 21:38 ` [PATCH 28/30] migration/vmstate-types: convert vmstate_info_g_byte_array to new APIs Vladimir Sementsov-Ogievskiy
2026-09-03 17:41 ` Fabiano Rosas
2026-08-25 21:38 ` [PATCH 29/30] migration: VMStateInfo: remove old .get / .set handlers Vladimir Sementsov-Ogievskiy
2026-08-25 21:38 ` [PATCH 30/30] migration: finally drop vmstate_save/load_state() functions Vladimir Sementsov-Ogievskiy
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.