kvm: x86: Add cr3 to struct kvm_debug_exit_arch
PATCH v2 1/1 kvm: x86: Add cr3 to struct kvm_debug_exit_arch
From: Ken Hofsass <[email protected]>
A userspace agent can use cr3 to quickly determine whether a KVM_EXIT_DEBUG is associated with a guest process of interest.
KVM_CAP_DEBUG_EVENT_PDBR indicates support for the extension.
---
v1 -> v2: Changed KVM_CAP_DEBUG_EVENT_PG_BASE_ADDR to KVM_CAP_DEBUG_EVENT_PDBR
Set debug.arch.cr3 in kvm_vcpu_do_singlestep and
kvm_vcpu_check_breakpoint
Added svm support
arch/x86/include/uapi/asm/kvm.h | 1 + arch/x86/kvm/svm.c | 3 +++ arch/x86/kvm/vmx/vmx.c | 2 ++ arch/x86/kvm/x86.c | 3 +++ include/uapi/linux/kvm.h | 1 + 5 files changed, 10 insertions(+)
arch/x86/include/uapi/asm/kvm.h +1 -0
@@ -254,6 +254,7 @@ struct kvm_debug_exit_arch {__u64 pc;__u64 dr6;__u64 dr7; +__u64 cr3;/* Depends on KVM_CAP_DEBUG_EVENT_PDBR */ };#define KVM_GUESTDBG_USE_SW_BP 0x00010000
arch/x86/kvm/svm.c +3 -0
@@ -2738,6 +2738,7 @@ static int db_interception(struct vcpu_svm *svm) kvm_run->exit_reason =KVM_EXIT_DEBUG ; kvm_run->debug.arch.pc = svm->vmcb->save.cs.base + svm->vmcb->save.rip; + kvm_run->debug.arch.cr3 =kvm_read_cr3 (vcpu); kvm_run->debug.arch.exception =DB_VECTOR ;return 0 ; }
@@ -2748,9 +2749,11 @@ static int db_interception(struct vcpu_svm *svm)static int bp_interception (struct vcpu_svm *svm) {struct kvm_run *kvm_run = svm->vcpu.run; +struct kvm_vcpu *vcpu = &svm->vcpu; kvm_run->exit_reason =KVM_EXIT_DEBUG ; kvm_run->debug.arch.pc = svm->vmcb->save.cs.base + svm->vmcb->save.rip; + kvm_run->debug.arch.cr3 =kvm_read_cr3 (vcpu); kvm_run->debug.arch.exception =BP_VECTOR ;return 0 ; }
arch/x86/kvm/vmx/vmx.c +2 -0
@@ -4690,6 +4690,7 @@ static int handle_exception_nmi(struct kvm_vcpu *vcpu) kvm_run->exit_reason =KVM_EXIT_DEBUG ; rip =kvm_rip_read (vcpu); kvm_run->debug.arch.pc =vmcs_readl (GUEST_CS_BASE ) + rip; + kvm_run->debug.arch.cr3 =kvm_read_cr3 (vcpu); kvm_run->debug.arch.exception = ex_no;break ;default :
@@ -4909,6 +4910,7 @@ static int handle_dr(struct kvm_vcpu *vcpu) vcpu->run->debug.arch.dr6 = vcpu->arch.dr6; vcpu->run->debug.arch.dr7 = dr7; vcpu->run->debug.arch.pc =kvm_get_linear_rip (vcpu); + vcpu->run->debug.arch.cr3 =kvm_read_cr3 (vcpu); vcpu->run->debug.arch.exception =DB_VECTOR ; vcpu->run->exit_reason =KVM_EXIT_DEBUG ;return 0 ;
arch/x86/kvm/x86.c +3 -0
@@ -3222,6 +3222,7 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)case KVM_CAP_GET_MSR_FEATURES :case KVM_CAP_MSR_PLATFORM_INFO :case KVM_CAP_EXCEPTION_PAYLOAD : +case KVM_CAP_DEBUG_EVENT_PDBR : r =1 ;break ;case KVM_CAP_SYNC_REGS :
@@ -6490,6 +6491,7 @@ static int kvm_vcpu_do_singlestep(struct kvm_vcpu *vcpu)if (vcpu->guest_debug &KVM_GUESTDBG_SINGLESTEP ) { kvm_run->debug.arch.dr6 =DR6_BS |DR6_FIXED_1 |DR6_RTM ; kvm_run->debug.arch.pc = vcpu->arch.singlestep_rip; + kvm_run->debug.arch.cr3 =kvm_read_cr3 (vcpu); kvm_run->debug.arch.exception =DB_VECTOR ; kvm_run->exit_reason =KVM_EXIT_DEBUG ;return 0 ;
@@ -6534,6 +6536,7 @@ static bool kvm_vcpu_check_breakpoint(struct kvm_vcpu *vcpu, int *r)if (dr6 !=0 ) { kvm_run->debug.arch.dr6 = dr6 |DR6_FIXED_1 |DR6_RTM ; kvm_run->debug.arch.pc = eip; + kvm_run->debug.arch.cr3 =kvm_read_cr3 (vcpu); kvm_run->debug.arch.exception =DB_VECTOR ; kvm_run->exit_reason =KVM_EXIT_DEBUG ; *r =0 ;
include/uapi/linux/kvm.h +1 -0
@@ -1000,6 +1000,7 @@ struct kvm_ppc_resize_hpt {#define KVM_CAP_PMU_EVENT_FILTER 173#define KVM_CAP_ARM_IRQ_LINE_LAYOUT_2 174#define KVM_CAP_HYPERV_DIRECT_TLBFLUSH 175 +#define KVM_CAP_DEBUG_EVENT_PDBR 176#ifdef KVM_CAP_IRQ_ROUTING
Signature · 1 line
2.24.0.rc0.303.g954a862665-goog
Quoted 6 lines · Jim Mattson
From: Ken Hofsass <[email protected]>
A userspace agent can use cr3 to quickly determine whether a
KVM_EXIT_DEBUGis associated with a guest process of interest.
KVM_CAP_DEBUG_EVENT_PDBRindicates support for the extension.
Isn't PDBR x86-specific terminology? If we're going to use something that is x86-specific then just call it GUEST_CR3. If there's a chance that this is useful on other architectures then it'd probably be better to go with Linux's own terminology, e.g. KVM_CAP_DEBUG_EVENT_GUEST_PGD.
Quoted 8 lines
Signed-off-by Ken Hofsass <[email protected]>Signed-off-by Jim Mattson <[email protected]>Cc Peter Shier <[email protected]>---
v1 -> v2: ChangedKVM_CAP_DEBUG_EVENT_PG_BASE_ADDRtoKVM_CAP_DEBUG_EVENT_PDBR
Set debug.arch.cr3 inkvm_vcpu_do_singlestepand
kvm_vcpu_check_breakpoint
Added svm support
Heh, I wonder what the record is for longest time between legitimate versions of a single patch.
Paolo Bonzini
maintainerQuoted 7 lines · Jim Mattson
From: Ken Hofsass <[email protected]>
A userspace agent can use cr3 to quickly determine whether a
KVM_EXIT_DEBUGis associated with a guest process of interest.
KVM_CAP_DEBUG_EVENT_PDBRindicates support for the extension.
Quoted 8 lines
Signed-off-by Ken Hofsass <[email protected]>Signed-off-by Jim Mattson <[email protected]>Cc Peter Shier <[email protected]>---
v1 -> v2: ChangedKVM_CAP_DEBUG_EVENT_PG_BASE_ADDRtoKVM_CAP_DEBUG_EVENT_PDBR
Set debug.arch.cr3 inkvm_vcpu_do_singlestepand
kvm_vcpu_check_breakpoint
Added svm support
Perhaps you have already considered using KVM_CAP_SYNC_REGS instead, since Google contributed it in the first place, but anyway... would it be enough for userspace to request KVM_SYNC_X86_SREGS when it enables breakpoints or singlestep?
Thanks,
Paolo
Quoted 17 lines · Paolo Bonzini
Quoted 7 lines · Jim Mattson
From: Ken Hofsass <[email protected]>
A userspace agent can use cr3 to quickly determine whether a
KVM_EXIT_DEBUGis associated with a guest process of interest.
KVM_CAP_DEBUG_EVENT_PDBRindicates support for the extension.Quoted 8 lines
Signed-off-by Ken Hofsass <[email protected]>Signed-off-by Jim Mattson <[email protected]>Cc Peter Shier <[email protected]>---
v1 -> v2: ChangedKVM_CAP_DEBUG_EVENT_PG_BASE_ADDRtoKVM_CAP_DEBUG_EVENT_PDBR
Set debug.arch.cr3 inkvm_vcpu_do_singlestepand
kvm_vcpu_check_breakpoint
Added svm support
Quoted 4 lines
Perhaps you have already considered using
KVM_CAP_SYNC_REGSinstead, since Google contributed it in the first place, but anyway... would it be enough for userspace to requestKVM_SYNC_X86_SREGSwhen it enables breakpoints or singlestep?
Hi Paolo, from a functional perspective, using KVM_SYNC_X86_SREGS is totally reasonable. But it currently introduces a non-trivial amount of overhead because it affects all exits.
This change is a targeted optimization for use in instrumentation scenarios. Specifically where debug breakpoint exits are a small percentage of total exits and only a small percentage of the debug exits are from processes of interest.
thanks,
Ken
Quoted 28 lines · Ken Hofsass
Quoted 17 lines · Paolo Bonzini
Quoted 7 lines · Jim Mattson
From: Ken Hofsass <[email protected]>
A userspace agent can use cr3 to quickly determine whether a
KVM_EXIT_DEBUGis associated with a guest process of interest.
KVM_CAP_DEBUG_EVENT_PDBRindicates support for the extension.Quoted 8 lines
Signed-off-by Ken Hofsass <[email protected]>Signed-off-by Jim Mattson <[email protected]>Cc Peter Shier <[email protected]>---
v1 -> v2: ChangedKVM_CAP_DEBUG_EVENT_PG_BASE_ADDRtoKVM_CAP_DEBUG_EVENT_PDBR
Set debug.arch.cr3 inkvm_vcpu_do_singlestepand
kvm_vcpu_check_breakpoint
Added svm supportQuoted 4 lines
Perhaps you have already considered using
KVM_CAP_SYNC_REGSinstead, since Google contributed it in the first place, but anyway... would it be enough for userspace to requestKVM_SYNC_X86_SREGSwhen it enables breakpoints or singlestep?Hi Paolo, from a functional perspective, using
KVM_SYNC_X86_SREGSis totally reasonable. But it currently introduces a non-trivial amount of overhead because it affects all exits.
Quoted 7 lines
This change is a targeted optimization for use in instrumentation scenarios. Specifically where debug breakpoint exits are a small percentage of total exits and only a small percentage of the debug exits are from processes of interest.
thanks,
Ken
Another possibility would be to add flags to KVM_SET_GET_DEBUG that request a SYNC_REGS on a breakpoint or single step.
Paolo Bonzini
maintainerQuoted 23 lines · Ken Hofsass
Quoted 17 lines · Paolo Bonzini
Quoted 7 lines · Jim Mattson
From: Ken Hofsass <[email protected]>
A userspace agent can use cr3 to quickly determine whether a
KVM_EXIT_DEBUGis associated with a guest process of interest.
KVM_CAP_DEBUG_EVENT_PDBRindicates support for the extension.Quoted 8 lines
Signed-off-by Ken Hofsass <[email protected]>Signed-off-by Jim Mattson <[email protected]>Cc Peter Shier <[email protected]>---
v1 -> v2: ChangedKVM_CAP_DEBUG_EVENT_PG_BASE_ADDRtoKVM_CAP_DEBUG_EVENT_PDBR
Set debug.arch.cr3 inkvm_vcpu_do_singlestepand
kvm_vcpu_check_breakpoint
Added svm supportQuoted 4 lines
Perhaps you have already considered using
KVM_CAP_SYNC_REGSinstead, since Google contributed it in the first place, but anyway... would it be enough for userspace to requestKVM_SYNC_X86_SREGSwhen it enables breakpoints or singlestep?
Quoted 8 lines
Hi Paolo, from a functional perspective, using
KVM_SYNC_X86_SREGSis totally reasonable. But it currently introduces a non-trivial amount of overhead because it affects all exits.This change is a targeted optimization for use in instrumentation scenarios. Specifically where debug breakpoint exits are a small percentage of total exits and only a small percentage of the debug exits are from processes of interest.
Sorry for the delayed response, mostly due to KVM Forum.
Is this due to Google's non-upstream userspace emulation patches? With a properly configured guest and in-kernel emulation, userspace exits should be so few as to make KVM_CAP_SYNC_REGS's overhead low.
But in any case, what about adding a new KVM_SYNC_X86_CR3 that is a subset of SREGS?
Thanks,
Paolo