[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-devel] [PATCH v3 2/4] hvm/svm: Enable Breakpoint events
This commit implements the breakpoint events for svm. At the moment, the Breakpoint vmexit is not forwarded to the monitor layer. This patch adds the hvm_monitor_debug call to the VMEXIT_EXCEPTION_BP. Also, the Software Breakpoint cap is moved from the Intel arch to the common part of the code. Signed-off-by: Alexandru Isaila <aisaila@xxxxxxxxxxxxxxx> --- Changes since V2: - Moved the comment from vmx_vmexit_handler to hvm_monitor_debug - Moved the AMD comment up. --- xen/arch/x86/hvm/monitor.c | 5 +++++ xen/arch/x86/hvm/svm/svm.c | 48 +++++++++++++++++++++++++++++++++++-------- xen/arch/x86/hvm/vmx/vmx.c | 5 ----- xen/include/asm-x86/monitor.h | 4 ++-- 4 files changed, 47 insertions(+), 15 deletions(-) diff --git a/xen/arch/x86/hvm/monitor.c b/xen/arch/x86/hvm/monitor.c index 131b852..60cb68d 100644 --- a/xen/arch/x86/hvm/monitor.c +++ b/xen/arch/x86/hvm/monitor.c @@ -133,6 +133,11 @@ static inline unsigned long gfn_of_rip(unsigned long rip) int hvm_monitor_debug(unsigned long rip, enum hvm_monitor_debug_type type, unsigned long trap_type, unsigned long insn_length) { + /* + * rc < 0 error in monitor/vm_event, crash + * !rc continue normally + * rc > 0 paused waiting for response, work here is done + */ struct vcpu *curr = current; struct arch_domain *ad = &curr->domain->arch; vm_event_request_t req = {}; diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c index dcbd550..0d9baf8 100644 --- a/xen/arch/x86/hvm/svm/svm.c +++ b/xen/arch/x86/hvm/svm/svm.c @@ -59,6 +59,7 @@ #include <asm/hap.h> #include <asm/apic.h> #include <asm/debugger.h> +#include <asm/hvm/monitor.h> #include <asm/xstate.h> void svm_asm_do_resume(void); @@ -1079,7 +1080,8 @@ static void svm_ctxt_switch_to(struct vcpu *v) static void noreturn svm_do_resume(struct vcpu *v) { struct vmcb_struct *vmcb = v->arch.hvm_svm.vmcb; - bool_t debug_state = v->domain->debugger_attached; + bool debug_state = v->domain->debugger_attached + || v->domain->arch.monitor.software_breakpoint_enabled; bool_t vcpu_guestmode = 0; struct vlapic *vlapic = vcpu_vlapic(v); @@ -2407,6 +2409,19 @@ static bool svm_get_pending_event(struct vcpu *v, struct x86_event *info) return true; } +static void svm_propagate_intr(struct vcpu *v, unsigned long insn_len) +{ + struct vmcb_struct *vmcb = v->arch.hvm_svm.vmcb; + struct x86_event event = { + .vector = vmcb->eventinj.fields.type, + .type = vmcb->eventinj.fields.type, + .error_code = vmcb->exitinfo1, + }; + + event.insn_len = insn_len; + hvm_inject_event(&event); +} + static struct hvm_function_table __initdata svm_function_table = { .name = "SVM", .cpu_up_prepare = svm_cpu_up_prepare, @@ -2619,14 +2634,31 @@ void svm_vmexit_handler(struct cpu_user_regs *regs) break; case VMEXIT_EXCEPTION_BP: - if ( !v->domain->debugger_attached ) - goto unexpected_exit_type; - /* AMD Vol2, 15.11: INT3, INTO, BOUND intercepts do not update RIP. */ - if ( (inst_len = __get_instruction_length(v, INSTR_INT3)) == 0 ) + inst_len = __get_instruction_length(v, INSTR_INT3); + + if ( inst_len == 0 ) break; - __update_guest_eip(regs, inst_len); - current->arch.gdbsx_vcpu_event = TRAP_int3; - domain_pause_for_debugger(); + + if ( v->domain->debugger_attached ) + { + /* AMD Vol2, 15.11: INT3, INTO, BOUND intercepts do not update RIP. */ + __update_guest_eip(regs, inst_len); + current->arch.gdbsx_vcpu_event = TRAP_int3; + domain_pause_for_debugger(); + } + else + { + int rc; + + rc = hvm_monitor_debug(regs->rip, + HVM_MONITOR_SOFTWARE_BREAKPOINT, + X86_EVENTTYPE_SW_EXCEPTION, + inst_len); + if ( rc < 0 ) + goto unexpected_exit_type; + if ( !rc ) + svm_propagate_intr(v, inst_len); + } break; case VMEXIT_EXCEPTION_NM: diff --git a/xen/arch/x86/hvm/vmx/vmx.c b/xen/arch/x86/hvm/vmx/vmx.c index 3dc6a6d..c89b4b6 100644 --- a/xen/arch/x86/hvm/vmx/vmx.c +++ b/xen/arch/x86/hvm/vmx/vmx.c @@ -3709,11 +3709,6 @@ void vmx_vmexit_handler(struct cpu_user_regs *regs) HVM_MONITOR_DEBUG_EXCEPTION, trap_type, insn_len); - /* - * rc < 0 error in monitor/vm_event, crash - * !rc continue normally - * rc > 0 paused waiting for response, work here is done - */ if ( rc < 0 ) goto exit_and_crash; if ( !rc ) diff --git a/xen/include/asm-x86/monitor.h b/xen/include/asm-x86/monitor.h index c339324..11a0cae 100644 --- a/xen/include/asm-x86/monitor.h +++ b/xen/include/asm-x86/monitor.h @@ -77,13 +77,13 @@ static inline uint32_t arch_monitor_get_capabilities(struct domain *d) if ( !is_hvm_domain(d) ) return capabilities; - capabilities = (1U << XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST); + capabilities = ((1U << XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST) | + (1U << XEN_DOMCTL_MONITOR_EVENT_SOFTWARE_BREAKPOINT)); if( cpu_has_vmx ) { capabilities |= (1U << XEN_DOMCTL_MONITOR_EVENT_WRITE_CTRLREG) | (1U << XEN_DOMCTL_MONITOR_EVENT_MOV_TO_MSR) | - (1U << XEN_DOMCTL_MONITOR_EVENT_SOFTWARE_BREAKPOINT) | (1U << XEN_DOMCTL_MONITOR_EVENT_DEBUG_EXCEPTION) | (1U << XEN_DOMCTL_MONITOR_EVENT_CPUID) | (1U << XEN_DOMCTL_MONITOR_EVENT_INTERRUPT) | -- 2.7.4 _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxxxxxxxxx https://lists.xenproject.org/mailman/listinfo/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |