Skip to contentSkip to conversation

target/riscv/kvm: Add SBI STA register sync and migration support

PATCH Applied Wang Yechao 3 participants 7 messages Oct 22 – Nov 11 RISC-V

lore
Share & tools
lore
#0 lore raw

v2 cover target/riscv/kvm: Add SBI STA register sync and migration support

KVM already exposes the SBI STA extension and its shmem address through the one-reg interface, but QEMU does not consume it. As a result, the guest-configured shmem address is not kept in sync between KVM and QEMU, and is lost on migration, breaking STA for the guest after live migration.

This series probes for SBI STA support via get-reg-list, synchronizes the shmem address (shmem_lo/shmem_hi) between KVM and QEMU (skipping the put at reset, since the address is configured by the guest), and saves the address in vmstate so STA keeps working after live migration. Only the STA shmem address is saved for now; other SBI state can be appended to kvm_sbi_state later.

Changes in v2:
- patch03, only save the sbi sta state if kvm sbi sta supported.
- rebase on riscv-to-apply.next.

- Link to v1:
https://lore.kernel.org/qemu-devel/[email protected]/

Wang Yechao (3):
target/riscv/kvm: Detect SBI STA extension support target/riscv/kvm: Sync SBI STA shmem registers with KVM target/riscv: Add SBI STA state to vmstate

 target/riscv/cpu.h           |   6 ++
 target/riscv/kvm/kvm-cpu.c   | 122 +++++++++++++++++++++++++++++++++++
 target/riscv/kvm/kvm_riscv.h |   1 +
 target/riscv/machine.c       |  18 ++++++
 4 files changed, 147 insertions(+)
Signature · 1 line
2.27.0
#1 lore raw

PATCH v2 1/3 target/riscv/kvm: Detect SBI STA extension support

Probe for the SBI STA extension by searching for a one-reg id built from KVM_REG_RISCV_SBI_EXT and KVM_RISCV_SBI_EXT_STA in the register list returned by KVM, following the existing SBI DBCN pattern, and record the result in kvm_sbi_sta.supported.

This patch only adds capability detection; nothing consumes kvm_sbi_sta.supported yet. The register synchronization that uses it is added by a subsequent patch.

---
 target/riscv/kvm/kvm-cpu.c | 20 ++++++++++++++++++++
 1 file changed, 20 insertions(+)
target/riscv/kvm/kvm-cpu.c +20 -0
index c085b22b23..8ab43432dd 100644
@@ -473,6 +473,12 @@ static KVMCPUConfig kvm_sbi_dbcn = {
                   KVM_REG_RISCV_SBI_EXT | KVM_RISCV_SBI_EXT_DBCN
 };
 
+static KVMCPUConfig kvm_sbi_sta = {
+    .name = "sbi_sta",
+    .kvm_reg_id = KVM_REG_RISCV | KVM_REG_SIZE_U64 |
+                  KVM_REG_RISCV_SBI_EXT | KVM_RISCV_SBI_EXT_STA
+};
+
 static void kvm_riscv_update_cpu_cfg_isa_ext(RISCVCPU *cpu, CPUState *cs)
 {
     uint64_t id, reg;
@@ -1233,6 +1239,19 @@ static void kvm_riscv_check_sbi_dbcn_support(RISCVCPU *cpu,
     }
 }
 
+static void kvm_riscv_check_sbi_sta_support(RISCVCPU *cpu,
+                                            struct kvm_reg_list *reglist)
+{
+    struct kvm_reg_list *reg_search;
+
+    reg_search = bsearch(&kvm_sbi_sta.kvm_reg_id, reglist->reg, reglist->n,
+                         sizeof(uint64_t), uint64_cmp);
+
+    if (reg_search) {
+        kvm_sbi_sta.supported = true;
+    }
+}
+
 static void kvm_riscv_read_vlenb(RISCVCPU *cpu, KVMScratchCPU *kvmcpu,
                                  struct kvm_reg_list *reglist)
 {
@@ -1365,6 +1384,7 @@ static void kvm_riscv_init_cfg(RISCVCPU *cpu, KVMScratchCPU *kvmcpu)
     }
 
     kvm_riscv_check_sbi_dbcn_support(cpu, reglist);
+    kvm_riscv_check_sbi_sta_support(cpu, reglist);
     kvm_riscv_read_csr_cfg(reglist);
 }
 
Signature · 1 line
2.27.0
#2 lore raw

PATCH v2 2/3 target/riscv/kvm: Sync SBI STA shmem registers with KVM

In reply to Wang Yechao

Now that SBI STA support is detected, synchronize the shared memory address (shmem_lo and shmem_hi) between KVM and QEMU using the KVM_REG_RISCV_SBI_STA one-reg interface.

The shmem address is configured by the guest, so QEMU does not need to perform put reg operations during reset.

---
 target/riscv/cpu.h         |  6 +++
 target/riscv/kvm/kvm-cpu.c | 97 ++++++++++++++++++++++++++++++++++++++
 2 files changed, 103 insertions(+)
target/riscv/cpu.h +6 -0
index b65d631994..4da7963d3d 100644
@@ -34,6 +34,9 @@
 #include "cpu_cfg.h"
 #include "qapi/qapi-types-common.h"
 #include "cpu-qom.h"
+#ifdef CONFIG_KVM
+#include <linux/kvm.h>
+#endif
 
 typedef struct CPUArchState CPURISCVState;
 
@@ -550,6 +553,9 @@ struct CPUArchState {
     /* KVM multiprocessor state */
     uint32_t kvm_mp_state;
     bool kvm_mp_state_loaded;
+
+    /* kvm sbi state */
+    struct kvm_riscv_sbi_sta kvm_sbi_sta;
 #endif /* CONFIG_KVM */
 };
 
target/riscv/kvm/kvm-cpu.c +97 -0

121 lines not on this page · raw message

Signature · 1 line
2.27.0
#3 lore raw

PATCH v2 3/3 target/riscv: Add SBI STA state to vmstate

In reply to Wang Yechao

Save and restore the KVM SBI state as a vmstate subsection, so that a guest using SBI STA keeps working after live migration. Only the STA shmem address (shmem_lo and shmem_hi) is saved for now; other SBI state can be appended to kvm_sbi_state as it is added.

---
 target/riscv/kvm/kvm-cpu.c   |  5 +++++
 target/riscv/kvm/kvm_riscv.h |  1 +
 target/riscv/machine.c       | 18 ++++++++++++++++++
 3 files changed, 24 insertions(+)
target/riscv/kvm/kvm-cpu.c +5 -0
index ba5ba63854..0586e290dd 100644
@@ -1015,6 +1015,11 @@ static int kvm_riscv_put_regs_vector(CPUState *cs)
     return ret;
 }
 
+bool kvm_riscv_has_sbi_sta_state(void)
+{
+     return kvm_sbi_sta.supported;
+}
+
 static int kvm_riscv_get_regs_sbi_sta(CPUState *cs)
 {
     RISCVCPU *cpu = RISCV_CPU(cs);
target/riscv/kvm/kvm_riscv.h +1 -0
index aef681f0a2..5e17bacad1 100644
@@ -35,6 +35,7 @@ void kvm_riscv_aia_create(MachineState *machine, uint64_t group_shift,
                           uint64_t guest_num);
 void riscv_kvm_aplic_request(void *opaque, int irq, int level);
 bool kvm_riscv_has_mp_state(void);
+bool kvm_riscv_has_sbi_sta_state(void);
 int kvm_riscv_check_timer_frequency(RISCVCPU *cpu);
 void riscv_kvm_cpu_finalize_features(RISCVCPU *cpu, Error **errp);
 uint64_t kvm_riscv_get_timebase_frequency(RISCVCPU *cpu);
target/riscv/machine.c +18 -0
index 0de06e9588..9fc699a482 100644
@@ -318,6 +318,23 @@ static const VMStateDescription vmstate_kvm_mp_state = {
         VMSTATE_END_OF_LIST()
     }
 };
+
+static bool kvm_sbi_state_needed(void *opaque)
+{
+    return kvm_enabled() && kvm_riscv_has_sbi_sta_state();
+}
+
+static const VMStateDescription vmstate_kvm_sbi_state = {
+    .name = "cpu/kvm-sbi-state",
+    .version_id = 1,
+    .minimum_version_id = 1,
+    .needed = kvm_sbi_state_needed,
+    .fields = (const VMStateField[]) {
+        VMSTATE_UINT64(env.kvm_sbi_sta.shmem_lo, RISCVCPU),
+        VMSTATE_UINT64(env.kvm_sbi_sta.shmem_hi, RISCVCPU),
+        VMSTATE_END_OF_LIST()
+    }
+};
 #endif
 
 static bool debug_needed(void *opaque)
@@ -645,6 +662,7 @@ const VMStateDescription vmstate_riscv_cpu = {
         &vmstate_kvm_timer_frequency,
         &vmstate_kvmtimer,
         &vmstate_kvm_mp_state,
+        &vmstate_kvm_sbi_state,
 #endif
         &vmstate_envcfg,
         &vmstate_debug,
Signature · 1 line
2.27.0
Reviewed-by on v2 3/3
#4 lore raw

Re: [PATCH v2 3/3] target/riscv: Add SBI STA state to vmstate

Quoted 7 lines · Wang Yechao

Save and restore the KVM SBI state as a vmstate subsection, so that a guest using SBI STA keeps working after live migration. Only the STA shmem address (shmem_lo and shmem_hi) is saved for now; other SBI state can be appended to kvm_sbi_state as it is added.

---

Quoted 69 lines
  target/riscv/kvm/kvm-cpu.c   |  5 +++++
  target/riscv/kvm/kvm_riscv.h |  1 +
  target/riscv/machine.c       | 18 ++++++++++++++++++
  3 files changed, 24 insertions(+)
target/riscv/kvm/kvm-cpu.c +5 -0
index ba5ba63854..0586e290dd 100644
@@ -1015,6 +1015,11 @@ static int kvm_riscv_put_regs_vector(CPUState *cs)
      return ret;
  }
 
+bool kvm_riscv_has_sbi_sta_state(void)
+{
+     return kvm_sbi_sta.supported;
+}
+
  static int kvm_riscv_get_regs_sbi_sta(CPUState *cs)
  {
      RISCVCPU *cpu = RISCV_CPU(cs);
target/riscv/kvm/kvm_riscv.h +1 -0
index aef681f0a2..5e17bacad1 100644
@@ -35,6 +35,7 @@ void kvm_riscv_aia_create(MachineState *machine, uint64_t group_shift,
                            uint64_t guest_num);
  void riscv_kvm_aplic_request(void *opaque, int irq, int level);
  bool kvm_riscv_has_mp_state(void);
+bool kvm_riscv_has_sbi_sta_state(void);
  int kvm_riscv_check_timer_frequency(RISCVCPU *cpu);
  void riscv_kvm_cpu_finalize_features(RISCVCPU *cpu, Error **errp);
  uint64_t kvm_riscv_get_timebase_frequency(RISCVCPU *cpu);
target/riscv/machine.c +18 -0
index 0de06e9588..9fc699a482 100644
@@ -318,6 +318,23 @@ static const VMStateDescription vmstate_kvm_mp_state = {
          VMSTATE_END_OF_LIST()
      }
  };
+
+static bool kvm_sbi_state_needed(void *opaque)
+{
+    return kvm_enabled() && kvm_riscv_has_sbi_sta_state();
+}
+
+static const VMStateDescription vmstate_kvm_sbi_state = {
+    .name = "cpu/kvm-sbi-state",
+    .version_id = 1,
+    .minimum_version_id = 1,
+    .needed = kvm_sbi_state_needed,
+    .fields = (const VMStateField[]) {
+        VMSTATE_UINT64(env.kvm_sbi_sta.shmem_lo, RISCVCPU),
+        VMSTATE_UINT64(env.kvm_sbi_sta.shmem_hi, RISCVCPU),
+        VMSTATE_END_OF_LIST()
+    }
+};
  #endif
 
  static bool debug_needed(void *opaque)
@@ -645,6 +662,7 @@ const VMStateDescription vmstate_riscv_cpu = {
          &vmstate_kvm_timer_frequency,
          &vmstate_kvmtimer,
          &vmstate_kvm_mp_state,
+        &vmstate_kvm_sbi_state,
  #endif
          &vmstate_envcfg,
          &vmstate_debug,
#5 lore raw
In reply to Wang Yechao
Quoted 28 lines · Wang Yechao

KVM already exposes the SBI STA extension and its shmem address through
the one-reg interface, but QEMU does not consume it. As a result, the guest-configured shmem address is not kept in sync between KVM and QEMU,
and is lost on migration, breaking STA for the guest after live migration.

This series probes for SBI STA support via get-reg-list, synchronizes the shmem address (shmem_lo/shmem_hi) between KVM and QEMU (skipping the
put at reset, since the address is configured by the guest), and saves
the address in vmstate so STA keeps working after live migration. Only
the STA shmem address is saved for now; other SBI state can be appended
to kvm_sbi_state later.

Changes in v2:
 - patch03, only save the sbi sta state if kvm sbi sta supported.
 - rebase on riscv-to-apply.next.

 - Link to v1:

https://lore.kernel.org/qemu-devel/[email protected]
/

Quoted 4 lines

Wang Yechao (3):
  target/riscv/kvm: Detect SBI STA extension support target/riscv/kvm: Sync SBI STA shmem registers with KVM target/riscv: Add SBI STA state to vmstate

Thanks!

Applied to riscv-to-apply.next

Alistair

Quoted 7 lines

 target/riscv/cpu.h           |   6 ++
 target/riscv/kvm/kvm-cpu.c   | 122
+++++++++++++++++++++++++++++++++++
 target/riscv/kvm/kvm_riscv.h |   1 +
 target/riscv/machine.c       |  18 ++++++

 4 files changed, 147 insertions(+)
#6 lore raw
In reply to Wang Yechao
Quoted 28 lines · Wang Yechao

KVM already exposes the SBI STA extension and its shmem address through
the one-reg interface, but QEMU does not consume it. As a result, the guest-configured shmem address is not kept in sync between KVM and QEMU,
and is lost on migration, breaking STA for the guest after live migration.

This series probes for SBI STA support via get-reg-list, synchronizes the shmem address (shmem_lo/shmem_hi) between KVM and QEMU (skipping the
put at reset, since the address is configured by the guest), and saves
the address in vmstate so STA keeps working after live migration. Only
the STA shmem address is saved for now; other SBI state can be appended
to kvm_sbi_state later.

Changes in v2:
 - patch03, only save the sbi sta state if kvm sbi sta supported.
 - rebase on riscv-to-apply.next.

 - Link to v1:

https://lore.kernel.org/qemu-devel/[email protected]
/

Quoted 4 lines

Wang Yechao (3):
  target/riscv/kvm: Detect SBI STA extension support target/riscv/kvm: Sync SBI STA shmem registers with KVM target/riscv: Add SBI STA state to vmstate

Thanks!

Applied to riscv-to-apply.next

Alistair

Quoted 7 lines

 target/riscv/cpu.h           |   6 ++
 target/riscv/kvm/kvm-cpu.c   | 122
+++++++++++++++++++++++++++++++++++
 target/riscv/kvm/kvm_riscv.h |   1 +
 target/riscv/machine.c       |  18 ++++++

 4 files changed, 147 insertions(+)