All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 0/4] target/loongarch/kvm: cpucfg and device attr fixes
@ 2026-06-26  5:27 Tao Cui
  2026-06-26  5:27 ` [PATCH v2 1/4] target/loongarch/kvm: fix uninitialized val and unchecked GET in cpucfg2 check Tao Cui
                   ` (3 more replies)
  0 siblings, 4 replies; 5+ messages in thread
From: Tao Cui @ 2026-06-26  5:27 UTC (permalink / raw)
  To: qemu-devel
  Cc: Song Gao, Bibo Mao, Paolo Bonzini, Philippe Mathieu-Daudé,
	Qiang Ma, Tao Cui

From: Tao Cui <cuitao@kylinos.cn>

A few small robustness fixes around cpucfg register sync and kvm device
attribute handling in the LoongArch KVM target.

  1/4: kvm_check_cpucfg2() discarded the return value of
       KVM_GET_DEVICE_ATTR and used an uninitialized val to mask
       cpucfg[2]; check the return value, warn and skip the mask on a GET
       failure (best-effort negotiation), and initialize val.

  2/4: kvm_get_stealtime(), kvm_set_stealtime() and kvm_set_pv_features()
       pass a struct kvm_device_attr by value to the variadic
       kvm_vcpu_ioctl(), which expects a pointer. Pass &attr.

  3/4: drop the redundant trace_kvm_failed_get/put_cpucfg() calls and
       their now-unused trace events; kvm_get/set_one_reg() already trace
       on failure.

  4/4: kvm_loongarch_get/put_cpucfg() overwrite ret on each iteration, so
       only the last register's result is returned and earlier failures
       are lost; on a failed read, get_cpucfg() also stores a stale val.
       Accumulate errors with ret |= and only store on a successful read.

Compiled and boot-tested on a loongarch64 KVM host.

Tao Cui (4):
  target/loongarch/kvm: fix uninitialized val and unchecked GET in
    cpucfg2 check
  target/loongarch/kvm: pass device attr by reference to kvm_vcpu_ioctl
  target/loongarch/kvm: remove redundant cpucfg failure traces
  target/loongarch/kvm: fix cpucfg sync error handling

 target/loongarch/kvm/kvm.c    | 46 ++++++++++++++++++++---------------
 target/loongarch/trace-events |  2 --
 2 files changed, 26 insertions(+), 22 deletions(-)

---
Changes in v2:
  - 1/4: on KVM_GET_DEVICE_ATTR failure, warn and skip the cpucfg2 mask
    instead of failing the register sync; the &= mask is best-effort, and a
    GET failure after a successful HAS is most likely a copy_{from,to}_user
    issue. Switched the report from error_report() to warn_report().

-- 
2.43.0



^ permalink raw reply	[flat|nested] 5+ messages in thread

* [PATCH v2 1/4] target/loongarch/kvm: fix uninitialized val and unchecked GET in cpucfg2 check
  2026-06-26  5:27 [PATCH v2 0/4] target/loongarch/kvm: cpucfg and device attr fixes Tao Cui
@ 2026-06-26  5:27 ` Tao Cui
  2026-06-26  5:27 ` [PATCH v2 2/4] target/loongarch/kvm: pass device attr by reference to kvm_vcpu_ioctl Tao Cui
                   ` (2 subsequent siblings)
  3 siblings, 0 replies; 5+ messages in thread
From: Tao Cui @ 2026-06-26  5:27 UTC (permalink / raw)
  To: qemu-devel
  Cc: Song Gao, Bibo Mao, Paolo Bonzini, Philippe Mathieu-Daudé,
	Qiang Ma, Tao Cui

From: Tao Cui <cuitao@kylinos.cn>

kvm_check_cpucfg2() discards the return value of KVM_GET_DEVICE_ATTR and
uses the local val (the host cpucfg2 mask) without checking whether the
read succeeded. val is also declared without an initializer, so on a GET
failure env->cpucfg[2] &= val reads an uninitialized value.

The &= mask is best-effort feature negotiation: if KVM_HAS_DEVICE_ATTR
succeeds, a GET failure is most likely a copy_{from,to}_user issue, not a
reason to fail the whole register sync. Check the GET return value, warn and
skip the mask on failure (the guest keeps the cpucfg2 it already has), and
initialize val to 0.

Signed-off-by: Tao Cui <cuitao@kylinos.cn>
---
 target/loongarch/kvm/kvm.c | 15 ++++++++++++---
 1 file changed, 12 insertions(+), 3 deletions(-)

diff --git a/target/loongarch/kvm/kvm.c b/target/loongarch/kvm/kvm.c
index d6539c12ac..5bd5e268b9 100644
--- a/target/loongarch/kvm/kvm.c
+++ b/target/loongarch/kvm/kvm.c
@@ -725,7 +725,7 @@ static int kvm_loongarch_get_cpucfg(CPUState *cs)
 static int kvm_check_cpucfg2(CPUState *cs)
 {
     int ret;
-    uint64_t val;
+    uint64_t val = 0;
     struct kvm_device_attr attr = {
         .group = KVM_LOONGARCH_VCPU_CPUCFG,
         .attr = 2,
@@ -736,8 +736,17 @@ static int kvm_check_cpucfg2(CPUState *cs)
     ret = kvm_vcpu_ioctl(cs, KVM_HAS_DEVICE_ATTR, &attr);
 
     if (!ret) {
-        kvm_vcpu_ioctl(cs, KVM_GET_DEVICE_ATTR, &attr);
-        env->cpucfg[2] &= val;
+        /*
+         * The &= mask is best-effort feature negotiation. If HAS succeeded,
+         * a GET failure is most likely a copy_{from,to}_user issue; warn and
+         * keep the cpucfg2 the guest already has rather than failing the sync.
+         */
+        int r = kvm_vcpu_ioctl(cs, KVM_GET_DEVICE_ATTR, &attr);
+        if (r) {
+            warn_report("CPUCFG2: KVM_GET_DEVICE_ATTR: %s", strerror(errno));
+        } else {
+            env->cpucfg[2] &= val;
+        }
 
         if (FIELD_EX32(env->cpucfg[2], CPUCFG2, FP)) {
             /* The FP minimal version is 1. */
-- 
2.43.0



^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH v2 2/4] target/loongarch/kvm: pass device attr by reference to kvm_vcpu_ioctl
  2026-06-26  5:27 [PATCH v2 0/4] target/loongarch/kvm: cpucfg and device attr fixes Tao Cui
  2026-06-26  5:27 ` [PATCH v2 1/4] target/loongarch/kvm: fix uninitialized val and unchecked GET in cpucfg2 check Tao Cui
@ 2026-06-26  5:27 ` Tao Cui
  2026-06-26  5:27 ` [PATCH v2 3/4] target/loongarch/kvm: remove redundant cpucfg failure traces Tao Cui
  2026-06-26  5:27 ` [PATCH v2 4/4] target/loongarch/kvm: fix cpucfg sync error handling Tao Cui
  3 siblings, 0 replies; 5+ messages in thread
From: Tao Cui @ 2026-06-26  5:27 UTC (permalink / raw)
  To: qemu-devel
  Cc: Song Gao, Bibo Mao, Paolo Bonzini, Philippe Mathieu-Daudé,
	Qiang Ma, Tao Cui

From: Tao Cui <cuitao@kylinos.cn>

kvm_vcpu_ioctl() is variadic and reads its argument as a pointer, but
kvm_get_stealtime(), kvm_set_stealtime() and kvm_set_pv_features() pass
the local struct kvm_device_attr by value. It currently works because of
how the calling convention passes large structs; pass &attr so the
argument is passed as intended.

Reviewed-by: Bibo Mao <maobibo@loongson.cn>
Signed-off-by: Tao Cui <cuitao@kylinos.cn>
---
 target/loongarch/kvm/kvm.c | 12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)

diff --git a/target/loongarch/kvm/kvm.c b/target/loongarch/kvm/kvm.c
index 5bd5e268b9..4bb5be6864 100644
--- a/target/loongarch/kvm/kvm.c
+++ b/target/loongarch/kvm/kvm.c
@@ -46,12 +46,12 @@ static int kvm_get_stealtime(CPUState *cs)
         .addr = (uint64_t)&env->stealtime.guest_addr,
     };
 
-    err = kvm_vcpu_ioctl(cs, KVM_HAS_DEVICE_ATTR, attr);
+    err = kvm_vcpu_ioctl(cs, KVM_HAS_DEVICE_ATTR, &attr);
     if (err) {
         return 0;
     }
 
-    err = kvm_vcpu_ioctl(cs, KVM_GET_DEVICE_ATTR, attr);
+    err = kvm_vcpu_ioctl(cs, KVM_GET_DEVICE_ATTR, &attr);
     if (err) {
         error_report("PVTIME: KVM_GET_DEVICE_ATTR: %s", strerror(errno));
         return err;
@@ -70,12 +70,12 @@ static int kvm_set_stealtime(CPUState *cs)
         .addr = (uint64_t)&env->stealtime.guest_addr,
     };
 
-    err = kvm_vcpu_ioctl(cs, KVM_HAS_DEVICE_ATTR, attr);
+    err = kvm_vcpu_ioctl(cs, KVM_HAS_DEVICE_ATTR, &attr);
     if (err) {
         return 0;
     }
 
-    err = kvm_vcpu_ioctl(cs, KVM_SET_DEVICE_ATTR, attr);
+    err = kvm_vcpu_ioctl(cs, KVM_SET_DEVICE_ATTR, &attr);
     if (err) {
         error_report("PVTIME: KVM_SET_DEVICE_ATTR %s with gpa "TARGET_FMT_lx,
                       strerror(errno), env->stealtime.guest_addr);
@@ -96,13 +96,13 @@ static int kvm_set_pv_features(CPUState *cs)
         .addr = (uint64_t)&val,
     };
 
-    err = kvm_vcpu_ioctl(cs, KVM_HAS_DEVICE_ATTR, attr);
+    err = kvm_vcpu_ioctl(cs, KVM_HAS_DEVICE_ATTR, &attr);
     if (err) {
         return 0;
     }
 
     val = env->pv_features;
-    err = kvm_vcpu_ioctl(cs, KVM_SET_DEVICE_ATTR, attr);
+    err = kvm_vcpu_ioctl(cs, KVM_SET_DEVICE_ATTR, &attr);
     if (err) {
         error_report("Fail to set pv feature "TARGET_FMT_lx " with error %s",
                       val, strerror(errno));
-- 
2.43.0



^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH v2 3/4] target/loongarch/kvm: remove redundant cpucfg failure traces
  2026-06-26  5:27 [PATCH v2 0/4] target/loongarch/kvm: cpucfg and device attr fixes Tao Cui
  2026-06-26  5:27 ` [PATCH v2 1/4] target/loongarch/kvm: fix uninitialized val and unchecked GET in cpucfg2 check Tao Cui
  2026-06-26  5:27 ` [PATCH v2 2/4] target/loongarch/kvm: pass device attr by reference to kvm_vcpu_ioctl Tao Cui
@ 2026-06-26  5:27 ` Tao Cui
  2026-06-26  5:27 ` [PATCH v2 4/4] target/loongarch/kvm: fix cpucfg sync error handling Tao Cui
  3 siblings, 0 replies; 5+ messages in thread
From: Tao Cui @ 2026-06-26  5:27 UTC (permalink / raw)
  To: qemu-devel
  Cc: Song Gao, Bibo Mao, Paolo Bonzini, Philippe Mathieu-Daudé,
	Qiang Ma, Tao Cui

From: Tao Cui <cuitao@kylinos.cn>

kvm_get_one_reg() and kvm_set_one_reg() already trace on failure, so the
trace_kvm_failed_get_cpucfg()/trace_kvm_failed_put_cpucfg() calls in
kvm_loongarch_get_cpucfg() and kvm_loongarch_put_cpucfg() duplicate that.
Remove the calls and the now-unused trace events.

Signed-off-by: Tao Cui <cuitao@kylinos.cn>
---
 target/loongarch/kvm/kvm.c    | 6 ------
 target/loongarch/trace-events | 2 --
 2 files changed, 8 deletions(-)

diff --git a/target/loongarch/kvm/kvm.c b/target/loongarch/kvm/kvm.c
index 4bb5be6864..a504cfaaf7 100644
--- a/target/loongarch/kvm/kvm.c
+++ b/target/loongarch/kvm/kvm.c
@@ -714,9 +714,6 @@ static int kvm_loongarch_get_cpucfg(CPUState *cs)
 
     for (i = 0; i < 21; i++) {
         ret = kvm_get_one_reg(cs, KVM_IOC_CPUCFG(i), &val);
-        if (ret < 0) {
-            trace_kvm_failed_get_cpucfg(strerror(errno));
-        }
         env->cpucfg[i] = (uint32_t)val;
     }
     return ret;
@@ -777,9 +774,6 @@ static int kvm_loongarch_put_cpucfg(CPUState *cs)
 	}
         val = env->cpucfg[i];
         ret = kvm_set_one_reg(cs, KVM_IOC_CPUCFG(i), &val);
-        if (ret < 0) {
-            trace_kvm_failed_put_cpucfg(strerror(errno));
-        }
     }
     return ret;
 }
diff --git a/target/loongarch/trace-events b/target/loongarch/trace-events
index dea11edc0f..829d8e0f53 100644
--- a/target/loongarch/trace-events
+++ b/target/loongarch/trace-events
@@ -9,7 +9,5 @@ kvm_failed_get_mpstate(const char *msg) "Failed to get mp_state from KVM: %s"
 kvm_failed_put_mpstate(const char *msg) "Failed to put mp_state into KVM: %s"
 kvm_failed_get_counter(const char *msg) "Failed to get counter from KVM: %s"
 kvm_failed_put_counter(const char *msg) "Failed to put counter into KVM: %s"
-kvm_failed_get_cpucfg(const char *msg) "Failed to get cpucfg from KVM: %s"
-kvm_failed_put_cpucfg(const char *msg) "Failed to put cpucfg into KVM: %s"
 kvm_arch_handle_exit(int num) "kvm arch handle exit, the reason number: %d"
 kvm_set_intr(int irq, int level) "kvm set interrupt, irq num: %d, level: %d"
-- 
2.43.0



^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH v2 4/4] target/loongarch/kvm: fix cpucfg sync error handling
  2026-06-26  5:27 [PATCH v2 0/4] target/loongarch/kvm: cpucfg and device attr fixes Tao Cui
                   ` (2 preceding siblings ...)
  2026-06-26  5:27 ` [PATCH v2 3/4] target/loongarch/kvm: remove redundant cpucfg failure traces Tao Cui
@ 2026-06-26  5:27 ` Tao Cui
  3 siblings, 0 replies; 5+ messages in thread
From: Tao Cui @ 2026-06-26  5:27 UTC (permalink / raw)
  To: qemu-devel
  Cc: Song Gao, Bibo Mao, Paolo Bonzini, Philippe Mathieu-Daudé,
	Qiang Ma, Tao Cui

From: Tao Cui <cuitao@kylinos.cn>

In kvm_loongarch_get_cpucfg() and kvm_loongarch_put_cpucfg(), ret is
overwritten on each iteration, so only the last register's result is
returned and earlier failures are lost. On a failed read, env->cpucfg[i]
is stored from a stale or uninitialized val.

Accumulate errors with ret |=, matching kvm_loongarch_get_csr()/put_csr(),
and only update env->cpucfg[i] on a successful read. Keep the cpucfg2
negotiation check in put_cpucfg() on a separate variable so its early
return does not overwrite the accumulated result.

Signed-off-by: Tao Cui <cuitao@kylinos.cn>
---
 target/loongarch/kvm/kvm.c | 15 +++++++++------
 1 file changed, 9 insertions(+), 6 deletions(-)

diff --git a/target/loongarch/kvm/kvm.c b/target/loongarch/kvm/kvm.c
index a504cfaaf7..9f1ee41ef6 100644
--- a/target/loongarch/kvm/kvm.c
+++ b/target/loongarch/kvm/kvm.c
@@ -713,8 +713,11 @@ static int kvm_loongarch_get_cpucfg(CPUState *cs)
     CPULoongArchState *env = cpu_env(cs);
 
     for (i = 0; i < 21; i++) {
-        ret = kvm_get_one_reg(cs, KVM_IOC_CPUCFG(i), &val);
-        env->cpucfg[i] = (uint32_t)val;
+        int r = kvm_get_one_reg(cs, KVM_IOC_CPUCFG(i), &val);
+        ret |= r;
+        if (!r) {
+            env->cpucfg[i] = (uint32_t)val;
+        }
     }
     return ret;
 }
@@ -767,13 +770,13 @@ static int kvm_loongarch_put_cpucfg(CPUState *cs)
 
     for (i = 0; i < 21; i++) {
 	if (i == 2) {
-            ret = kvm_check_cpucfg2(cs);
-            if (ret) {
-                return ret;
+            int r = kvm_check_cpucfg2(cs);
+            if (r) {
+                return r;
             }
 	}
         val = env->cpucfg[i];
-        ret = kvm_set_one_reg(cs, KVM_IOC_CPUCFG(i), &val);
+        ret |= kvm_set_one_reg(cs, KVM_IOC_CPUCFG(i), &val);
     }
     return ret;
 }
-- 
2.43.0



^ permalink raw reply related	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2026-06-26  5:28 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-06-26  5:27 [PATCH v2 0/4] target/loongarch/kvm: cpucfg and device attr fixes Tao Cui
2026-06-26  5:27 ` [PATCH v2 1/4] target/loongarch/kvm: fix uninitialized val and unchecked GET in cpucfg2 check Tao Cui
2026-06-26  5:27 ` [PATCH v2 2/4] target/loongarch/kvm: pass device attr by reference to kvm_vcpu_ioctl Tao Cui
2026-06-26  5:27 ` [PATCH v2 3/4] target/loongarch/kvm: remove redundant cpucfg failure traces Tao Cui
2026-06-26  5:27 ` [PATCH v2 4/4] target/loongarch/kvm: fix cpucfg sync error handling Tao Cui

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.