diff mbox series

[V1,16/26] physmem: set ram block idstr earlier

Message ID 1714406135-451286-17-git-send-email-steven.sistare@oracle.com (mailing list archive)
State New, archived
Headers show
Series Live update: cpr-exec | expand

Commit Message

Steven Sistare April 29, 2024, 3:55 p.m. UTC
Set the idstr for a ram block earlier, prior to calling ram_block_add,
so it can be used in a subsequent patch to find CPR attributes for the
block before it is created.

The id depends on the block's device path and its mr.  As as sanity check,
verify that the id has not changed (due to these dependencies changing)
by the time vmstate_register_ram is called (where the id was previously
assigned).

Signed-off-by: Steve Sistare <steven.sistare@oracle.com>
---
 include/exec/cpu-common.h |  3 +--
 migration/savevm.c        |  4 +---
 system/physmem.c          | 46 +++++++++++++++++++++++-----------------------
 3 files changed, 25 insertions(+), 28 deletions(-)
diff mbox series

Patch

diff --git a/include/exec/cpu-common.h b/include/exec/cpu-common.h
index 6d53188..ffab5d9 100644
--- a/include/exec/cpu-common.h
+++ b/include/exec/cpu-common.h
@@ -82,8 +82,7 @@  RAMBlock *qemu_ram_block_by_name(const char *name);
 RAMBlock *qemu_ram_block_from_host(void *ptr, bool round_offset,
                                    ram_addr_t *offset);
 ram_addr_t qemu_ram_block_host_offset(RAMBlock *rb, void *host);
-void qemu_ram_set_idstr(RAMBlock *block, const char *name, DeviceState *dev);
-void qemu_ram_unset_idstr(RAMBlock *block);
+void qemu_ram_verify_idstr(RAMBlock *block, DeviceState *dev);
 const char *qemu_ram_get_idstr(RAMBlock *rb);
 void *qemu_ram_get_host_addr(RAMBlock *rb);
 ram_addr_t qemu_ram_get_offset(RAMBlock *rb);
diff --git a/migration/savevm.c b/migration/savevm.c
index 01ed78c..8463ddf 100644
--- a/migration/savevm.c
+++ b/migration/savevm.c
@@ -3566,14 +3566,12 @@  bool delete_snapshot(const char *name, bool has_devices,
 
 void vmstate_register_ram(MemoryRegion *mr, DeviceState *dev)
 {
-    qemu_ram_set_idstr(mr->ram_block,
-                       memory_region_name(mr), dev);
+    qemu_ram_verify_idstr(mr->ram_block, dev);
     qemu_ram_set_migratable(mr->ram_block);
 }
 
 void vmstate_unregister_ram(MemoryRegion *mr, DeviceState *dev)
 {
-    qemu_ram_unset_idstr(mr->ram_block);
     qemu_ram_unset_migratable(mr->ram_block);
 }
 
diff --git a/system/physmem.c b/system/physmem.c
index b57462d..c736af5 100644
--- a/system/physmem.c
+++ b/system/physmem.c
@@ -1597,35 +1597,20 @@  int qemu_ram_get_fd(RAMBlock *rb)
 }
 
 /* Called with the BQL held.  */
-void qemu_ram_set_idstr(RAMBlock *new_block, const char *name, DeviceState *dev)
+static void qemu_ram_set_idstr(char *idstr, MemoryRegion *mr, DeviceState *dev)
 {
-    RAMBlock *block;
+    const char *name = memory_region_name(mr);
+    g_autofree char *id = dev ? qdev_get_dev_path(dev) : NULL;
 
-    assert(new_block);
-    assert(!new_block->idstr[0]);
-
-    if (dev) {
-        char *id = qdev_get_dev_path(dev);
-        if (id) {
-            snprintf(new_block->idstr, sizeof(new_block->idstr), "%s/", id);
-            g_free(id);
-        }
-    }
-    pstrcat(new_block->idstr, sizeof(new_block->idstr), name);
-
-    RCU_READ_LOCK_GUARD();
-    RAMBLOCK_FOREACH(block) {
-        if (block != new_block &&
-            !strcmp(block->idstr, new_block->idstr)) {
-            fprintf(stderr, "RAMBlock \"%s\" already registered, abort!\n",
-                    new_block->idstr);
-            abort();
-        }
+    if (id) {
+        snprintf(idstr, sizeof(VMStateId), "%s/%s", id, name);
+    } else {
+        pstrcpy(idstr, sizeof(VMStateId), name);
     }
 }
 
 /* Called with the BQL held.  */
-void qemu_ram_unset_idstr(RAMBlock *block)
+static void qemu_ram_unset_idstr(RAMBlock *block)
 {
     /* FIXME: arch_init.c assumes that this is not called throughout
      * migration.  Ignore the problem since hot-unplug during migration
@@ -1636,6 +1621,13 @@  void qemu_ram_unset_idstr(RAMBlock *block)
     }
 }
 
+void qemu_ram_verify_idstr(RAMBlock *new_block, DeviceState *dev)
+{
+    VMStateId idstr;
+    qemu_ram_set_idstr(idstr, new_block->mr, dev);
+    assert(!strcmp(new_block->idstr, idstr));
+}
+
 size_t qemu_ram_pagesize(RAMBlock *rb)
 {
     return rb->page_size;
@@ -1869,6 +1861,12 @@  static void ram_block_add(RAMBlock *new_block)
      * tail, so save the last element in last_block.
      */
     RAMBLOCK_FOREACH(block) {
+        if (!strcmp(block->idstr, new_block->idstr)) {
+            fprintf(stderr, "RAMBlock \"%s\" already added, abort!\n",
+                    new_block->idstr);
+            abort();
+        }
+
         last_block = block;
         if (block->max_length < new_block->max_length) {
             break;
@@ -1915,6 +1913,7 @@  static RAMBlock *ram_block_create(MemoryRegion *mr, ram_addr_t size,
 {
     RAMBlock *rb = g_malloc0(sizeof(*rb));
 
+    qemu_ram_set_idstr(rb->idstr, mr, mr->dev);
     rb->used_length = size;
     rb->max_length = max_size;
     rb->fd = -1;
@@ -2142,6 +2141,7 @@  void qemu_ram_free(RAMBlock *block)
     }
 
     qemu_mutex_lock_ramlist();
+    qemu_ram_unset_idstr(block);
     QLIST_REMOVE_RCU(block, next);
     ram_list.mru_block = NULL;
     /* Write list before version */