From 83efc5ae38c99bc261f1edecee8d29b23fa25c0e Mon Sep 17 00:00:00 2001 From: Sean Christopherson Date: Mon, 31 Aug 2026 22:26:40 +0100 Subject: KVM: x86/xen: Use atomic*() APIs instead of open coded equivalents Replace the open coded atomic asm blobs in the Xen event injection code with equivalent atomic{,64}_xxx() operations. Casting the event channel to atomic types is ugly, but not as ugly as asm blobs. No functional change intended. Signed-off-by: Sean Christopherson Signed-off-by: David Woodhouse Reviewed-by: Paul Durrant Link: https://patch.msgid.link/20260831213632.81023-10-dwmw2@infradead.org Signed-off-by: Paolo Bonzini --- arch/x86/kvm/xen.c | 35 ++++++++++++----------------------- 1 file changed, 12 insertions(+), 23 deletions(-) diff --git a/arch/x86/kvm/xen.c b/arch/x86/kvm/xen.c index 780eec2fb528..a4befaaa39af 100644 --- a/arch/x86/kvm/xen.c +++ b/arch/x86/kvm/xen.c @@ -678,12 +678,12 @@ void kvm_xen_inject_pending_events(struct kvm_vcpu *v) /* Now gpc->khva is a valid kernel address for the vcpu_info */ if (kvm_xen_has_64bit_shinfo(v->kvm)) { struct vcpu_info *vi = gpc->khva; + void *vi_pending_sel = &vi->evtchn_pending_sel; - if (IS_ALIGNED((unsigned long)&vi->evtchn_pending_sel, sizeof(u64))) - asm volatile(LOCK_PREFIX "orq %[src], %[dst]\n" - : [dst] "+m" (vi->evtchn_pending_sel) - : [src] "r" (evtchn_pending_sel)); - else + if (IS_ALIGNED((unsigned long)vi_pending_sel, sizeof(u64))) { + atomic64_or(evtchn_pending_sel, vi_pending_sel); + } else { + atomic_or(evtchn_pending_sel, vi_pending_sel); /* * The cast keeps the shift well-defined on 32-bit, * where evtchn_pending_sel is 32 bits wide and this @@ -691,28 +691,17 @@ void kvm_xen_inject_pending_events(struct kvm_vcpu *v) * kvm_xen_has_64bit_shinfo(), which is gated on * IS_ENABLED(CONFIG_64BIT)). */ - asm volatile(LOCK_PREFIX "orl %[src_lo], %[dst_lo]\n" - LOCK_PREFIX "orl %[src_hi], %[dst_hi]\n" - : [dst_lo] "+m" (vi->evtchn_pending_sel), - [dst_hi] "+m" (*(((u32 *)&vi->evtchn_pending_sel) + 1)) - : [src_lo] "r" ((u32)evtchn_pending_sel), - [src_hi] "r" ((u32)((u64)evtchn_pending_sel >> 32))); - - asm volatile(LOCK_PREFIX "andq %1, %0\n" - : "+m" (v->arch.xen.evtchn_pending_sel) - : "r" (~evtchn_pending_sel)); + atomic_or((u64)evtchn_pending_sel >> 32, + vi_pending_sel + 4); + } + + atomic64_andnot(evtchn_pending_sel, (void *)&v->arch.xen.evtchn_pending_sel); WRITE_ONCE(vi->evtchn_upcall_pending, 1); } else { - u32 evtchn_pending_sel32 = evtchn_pending_sel; struct compat_vcpu_info *vi = gpc->khva; - asm volatile(LOCK_PREFIX "orl %0, %1\n" - "notl %0\n" - LOCK_PREFIX "andl %0, %2\n" - : "=r" (evtchn_pending_sel32), - "+m" (vi->evtchn_pending_sel), - "+m" (v->arch.xen.evtchn_pending_sel) - : "0" (evtchn_pending_sel32)); + atomic_or(evtchn_pending_sel, (void *)&vi->evtchn_pending_sel); + atomic_andnot(evtchn_pending_sel, (void *)&v->arch.xen.evtchn_pending_sel); WRITE_ONCE(vi->evtchn_upcall_pending, 1); } -- cgit v1.2.3