* [PATCH v4 09/24] x86/emul: Provide a wrapper to x86_emulate() to ASSERT() certain behaviour
2016-12-01 16:55 [PATCH v4 for-4.9 00/24] [SUBSET] XSA-191 followup Andrew Cooper
@ 2016-12-01 16:55 ` Andrew Cooper
2016-12-02 11:26 ` Jan Beulich
2016-12-01 16:55 ` [PATCH v4 10/24] x86/emul: Always use fault semantics for software events Andrew Cooper
` (3 subsequent siblings)
4 siblings, 1 reply; 12+ messages in thread
From: Andrew Cooper @ 2016-12-01 16:55 UTC (permalink / raw)
To: Xen-devel; +Cc: Andrew Cooper, Jan Beulich
In debug builds, confirm that some properties of x86_emulate()'s behaviour
actually hold. The first property, fixed in a previous change, is that retire
flags are only ever set in the X86EMUL_OKAY case.
While adjusting the userspace test harness to cope with ASSERT() in
x86_emulate.h, fix a build problem introduced in c/s 122dd9575c7 "x86emul:
in_longmode() should not ignore ->read_msr() errors" by providing an
implementation of likely()/unlikely().
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
---
CC: Jan Beulich <JBeulich@suse.com>
v4:
* Shuffle #ifdefary
* Correct the documentation for x86_emulate()
* Use true/false in likely/unlikely definitions
v3:
* New
---
tools/tests/x86_emulator/test_x86_emulator.c | 1 +
tools/tests/x86_emulator/x86_emulate.c | 4 +++-
xen/arch/x86/x86_emulate/x86_emulate.c | 3 +++
xen/arch/x86/x86_emulate/x86_emulate.h | 27 ++++++++++++++++++++++++++-
4 files changed, 33 insertions(+), 2 deletions(-)
diff --git a/tools/tests/x86_emulator/test_x86_emulator.c b/tools/tests/x86_emulator/test_x86_emulator.c
index f255fef..b54fd11 100644
--- a/tools/tests/x86_emulator/test_x86_emulator.c
+++ b/tools/tests/x86_emulator/test_x86_emulator.c
@@ -1,3 +1,4 @@
+#include <assert.h>
#include <errno.h>
#include <limits.h>
#include <stdbool.h>
diff --git a/tools/tests/x86_emulator/x86_emulate.c b/tools/tests/x86_emulator/x86_emulate.c
index c46b7fc..897b9ab 100644
--- a/tools/tests/x86_emulator/x86_emulate.c
+++ b/tools/tests/x86_emulator/x86_emulate.c
@@ -16,7 +16,6 @@ typedef bool bool_t;
#define EFER_LMA (1 << 10)
#define BUG() abort()
-#define ASSERT assert
#define ASSERT_UNREACHABLE() assert(!__LINE__)
#if __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)
@@ -50,4 +49,7 @@ typedef bool bool_t;
#define __init
#define __maybe_unused __attribute__((__unused__))
+#define likely(x) __builtin_expect(!!(x), true)
+#define unlikely(x) __builtin_expect(!!(x), false)
+
#include "x86_emulate/x86_emulate.c"
diff --git a/xen/arch/x86/x86_emulate/x86_emulate.c b/xen/arch/x86/x86_emulate/x86_emulate.c
index bfcc05d..3e602da 100644
--- a/xen/arch/x86/x86_emulate/x86_emulate.c
+++ b/xen/arch/x86/x86_emulate/x86_emulate.c
@@ -2404,6 +2404,9 @@ x86_decode(
#undef insn_fetch_bytes
#undef insn_fetch_type
+/* Undo DEBUG wrapper. */
+#undef x86_emulate
+
int
x86_emulate(
struct x86_emulate_ctxt *ctxt,
diff --git a/xen/arch/x86/x86_emulate/x86_emulate.h b/xen/arch/x86/x86_emulate/x86_emulate.h
index ef39601..60f9105 100644
--- a/xen/arch/x86/x86_emulate/x86_emulate.h
+++ b/xen/arch/x86/x86_emulate/x86_emulate.h
@@ -23,6 +23,10 @@
#ifndef __X86_EMULATE_H__
#define __X86_EMULATE_H__
+#if !defined(__XEN__) && !defined(ASSERT)
+#define ASSERT assert
+#endif
+
#define MAX_INST_LEN 15
struct x86_emulate_ctxt;
@@ -546,13 +550,34 @@ struct x86_emulate_stub {
/*
* x86_emulate: Emulate an instruction.
- * Returns -1 on failure, 0 on success.
+ * Returns X86EMUL_* constants.
*/
int
x86_emulate(
struct x86_emulate_ctxt *ctxt,
const struct x86_emulate_ops *ops);
+#ifndef NDEBUG
+/*
+ * In debug builds, wrap x86_emulate() with some assertions about its expected
+ * behaviour.
+ */
+static inline int x86_emulate_wrapper(
+ struct x86_emulate_ctxt *ctxt,
+ const struct x86_emulate_ops *ops)
+{
+ int rc = x86_emulate(ctxt, ops);
+
+ /* Retire flags should only be set for successful instruction emulation. */
+ if ( rc != X86EMUL_OKAY )
+ ASSERT(ctxt->retire.raw == 0);
+
+ return rc;
+}
+
+#define x86_emulate x86_emulate_wrapper
+#endif
+
/*
* Given the 'reg' portion of a ModRM byte, and a register block, return a
* pointer into the block that addresses the relevant register.
--
2.1.4
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply related [flat|nested] 12+ messages in thread* Re: [PATCH v4 09/24] x86/emul: Provide a wrapper to x86_emulate() to ASSERT() certain behaviour
2016-12-01 16:55 ` [PATCH v4 09/24] x86/emul: Provide a wrapper to x86_emulate() to ASSERT() certain behaviour Andrew Cooper
@ 2016-12-02 11:26 ` Jan Beulich
0 siblings, 0 replies; 12+ messages in thread
From: Jan Beulich @ 2016-12-02 11:26 UTC (permalink / raw)
To: Andrew Cooper; +Cc: Xen-devel
>>> On 01.12.16 at 17:55, <andrew.cooper3@citrix.com> wrote:
> In debug builds, confirm that some properties of x86_emulate()'s behaviour
> actually hold. The first property, fixed in a previous change, is that retire
> flags are only ever set in the X86EMUL_OKAY case.
>
> While adjusting the userspace test harness to cope with ASSERT() in
> x86_emulate.h, fix a build problem introduced in c/s 122dd9575c7 "x86emul:
> in_longmode() should not ignore ->read_msr() errors" by providing an
> implementation of likely()/unlikely().
>
> Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Some of the #define-ary will be able to go away again with a patch
of mine splitting out common definitions of the test harness into a
private header (which I decided to create due to the increasing
amount of things needed/wanted in both of its source files).
Jan
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply [flat|nested] 12+ messages in thread
* [PATCH v4 10/24] x86/emul: Always use fault semantics for software events
2016-12-01 16:55 [PATCH v4 for-4.9 00/24] [SUBSET] XSA-191 followup Andrew Cooper
2016-12-01 16:55 ` [PATCH v4 09/24] x86/emul: Provide a wrapper to x86_emulate() to ASSERT() certain behaviour Andrew Cooper
@ 2016-12-01 16:55 ` Andrew Cooper
2016-12-01 19:07 ` Boris Ostrovsky
2016-12-02 11:28 ` Jan Beulich
2016-12-01 16:55 ` [PATCH v4 11/24] x86/emul: Implement singlestep as a retire flag Andrew Cooper
` (2 subsequent siblings)
4 siblings, 2 replies; 12+ messages in thread
From: Andrew Cooper @ 2016-12-01 16:55 UTC (permalink / raw)
To: Xen-devel
Cc: Andrew Cooper, Boris Ostrovsky, Tim Deegan, Suravee Suthikulpanit,
Jan Beulich
The common case is already using fault semantics out of x86_emulate(), as that
is how VT-x/SVM expects to inject the event (given suitable hardware support).
However, x86_emulate() returning X86EMUL_EXCEPTION and also completing a
register writeback is problematic for callers.
Switch the logic to always using fault semantics, and leave svm_inject_trap()
to fix up %eip if necessary.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
---
CC: Jan Beulich <JBeulich@suse.com>
CC: Tim Deegan <tim@xen.org>
CC: Boris Ostrovsky <boris.ostrovsky@oracle.com>
CC: Suravee Suthikulpanit <suravee.suthikulpanit@amd.com>
v4:
* s/eip/rip/
* Zero the high bits of regs->rip and vmcb->nextrip outside of 64bit mode.
* Spelling fixes
v3:
* New
---
xen/arch/x86/hvm/svm/svm.c | 60 ++++++++++++++++++++++------------
xen/arch/x86/x86_emulate/x86_emulate.c | 2 --
xen/arch/x86/x86_emulate/x86_emulate.h | 8 ++++-
3 files changed, 46 insertions(+), 24 deletions(-)
diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c
index 912d871..8c4f3c7 100644
--- a/xen/arch/x86/hvm/svm/svm.c
+++ b/xen/arch/x86/hvm/svm/svm.c
@@ -1209,7 +1209,7 @@ static void svm_inject_event(const struct x86_event *event)
struct vmcb_struct *vmcb = curr->arch.hvm_svm.vmcb;
eventinj_t eventinj = vmcb->eventinj;
struct x86_event _event = *event;
- const struct cpu_user_regs *regs = guest_cpu_user_regs();
+ struct cpu_user_regs *regs = guest_cpu_user_regs();
switch ( _event.vector )
{
@@ -1242,44 +1242,52 @@ static void svm_inject_event(const struct x86_event *event)
eventinj.fields.v = 1;
eventinj.fields.vector = _event.vector;
- /* Refer to AMD Vol 2: System Programming, 15.20 Event Injection. */
+ /*
+ * Refer to AMD Vol 2: System Programming, 15.20 Event Injection.
+ *
+ * On hardware lacking NextRIP support, and all hardware in the case of
+ * icebp, software events with trap semantics need emulating, so %rip in
+ * the trap frame points after the instruction.
+ *
+ * The x86 emulator (if requested by the x86_swint_emulate_* choice) will
+ * have performed checks such as presence/dpl/etc and believes that the
+ * event injection will succeed without faulting.
+ *
+ * The x86 emulator will always provide fault semantics for software
+ * events, with _trap.insn_len set appropriately. If the injection
+ * requires emulation, move %rip forwards at this point.
+ */
switch ( _event.type )
{
case X86_EVENTTYPE_SW_INTERRUPT: /* int $n */
- /*
- * Software interrupts (type 4) cannot be properly injected if the
- * processor doesn't support NextRIP. Without NextRIP, the emulator
- * will have performed DPL and presence checks for us, and will have
- * moved eip forward if appropriate.
- */
if ( cpu_has_svm_nrips )
- vmcb->nextrip = regs->eip + _event.insn_len;
+ vmcb->nextrip = regs->rip + _event.insn_len;
+ else
+ regs->rip += _event.insn_len;
eventinj.fields.type = X86_EVENTTYPE_SW_INTERRUPT;
break;
case X86_EVENTTYPE_PRI_SW_EXCEPTION: /* icebp */
/*
- * icebp's injection must always be emulated. Software injection help
- * in x86_emulate has moved eip forward, but NextRIP (if used) still
- * needs setting or execution will resume from 0.
+ * icebp's injection must always be emulated, as hardware does not
+ * special case HW_EXCEPTION with vector 1 (#DB) as having trap
+ * semantics.
*/
+ regs->rip += _event.insn_len;
if ( cpu_has_svm_nrips )
- vmcb->nextrip = regs->eip;
+ vmcb->nextrip = regs->rip;
eventinj.fields.type = X86_EVENTTYPE_HW_EXCEPTION;
break;
case X86_EVENTTYPE_SW_EXCEPTION: /* int3, into */
/*
- * The AMD manual states that .type=3 (HW exception), .vector=3 or 4,
- * will perform DPL checks. Experimentally, DPL and presence checks
- * are indeed performed, even without NextRIP support.
- *
- * However without NextRIP support, the event injection still needs
- * fully emulating to get the correct eip in the trap frame, yet get
- * the correct faulting eip should a fault occur.
+ * Hardware special cases HW_EXCEPTION with vectors 3 and 4 as having
+ * trap semantics, and will perform DPL checks.
*/
if ( cpu_has_svm_nrips )
- vmcb->nextrip = regs->eip + _event.insn_len;
+ vmcb->nextrip = regs->rip + _event.insn_len;
+ else
+ regs->rip += _event.insn_len;
eventinj.fields.type = X86_EVENTTYPE_HW_EXCEPTION;
break;
@@ -1290,6 +1298,16 @@ static void svm_inject_event(const struct x86_event *event)
break;
}
+ /*
+ * If injecting an event outside of 64bit mode, zero the upper bits of the
+ * %eip and nextrip after the adjustments above.
+ */
+ if ( !((vmcb->_efer & EFER_LMA) && vmcb->cs.attr.fields.l) )
+ {
+ regs->rip = regs->_eip;
+ vmcb->nextrip = (uint32_t)vmcb->nextrip;
+ }
+
vmcb->eventinj = eventinj;
if ( _event.vector == TRAP_page_fault )
diff --git a/xen/arch/x86/x86_emulate/x86_emulate.c b/xen/arch/x86/x86_emulate/x86_emulate.c
index 3e602da..fa8d98f 100644
--- a/xen/arch/x86/x86_emulate/x86_emulate.c
+++ b/xen/arch/x86/x86_emulate/x86_emulate.c
@@ -1694,8 +1694,6 @@ static int inject_swint(enum x86_swint_type type,
goto raise_exn;
}
}
-
- ctxt->regs->eip += insn_len;
}
rc = ops->inject_sw_interrupt(type, vector, insn_len, ctxt);
diff --git a/xen/arch/x86/x86_emulate/x86_emulate.h b/xen/arch/x86/x86_emulate/x86_emulate.h
index 60f9105..f4bcf36 100644
--- a/xen/arch/x86/x86_emulate/x86_emulate.h
+++ b/xen/arch/x86/x86_emulate/x86_emulate.h
@@ -64,7 +64,13 @@ enum x86_swint_type {
x86_swint_int, /* 0xcd $n */
};
-/* How much help is required with software event injection? */
+/*
+ * How much help is required with software event injection?
+ *
+ * All software events return from x86_emulate() with X86EMUL_EXCEPTION and
+ * fault-like semantics. This just controls whether the emulator performs
+ * presence/dpl/etc checks and possibly raises exceptions instead.
+ */
enum x86_swint_emulation {
x86_swint_emulate_none, /* Hardware supports all software injection properly */
x86_swint_emulate_icebp,/* Help needed with `icebp` (0xf1) */
--
2.1.4
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply related [flat|nested] 12+ messages in thread* Re: [PATCH v4 10/24] x86/emul: Always use fault semantics for software events
2016-12-01 16:55 ` [PATCH v4 10/24] x86/emul: Always use fault semantics for software events Andrew Cooper
@ 2016-12-01 19:07 ` Boris Ostrovsky
2016-12-02 11:28 ` Jan Beulich
1 sibling, 0 replies; 12+ messages in thread
From: Boris Ostrovsky @ 2016-12-01 19:07 UTC (permalink / raw)
To: Andrew Cooper, Xen-devel; +Cc: Tim Deegan, Suravee Suthikulpanit, Jan Beulich
On 12/01/2016 11:55 AM, Andrew Cooper wrote:
> The common case is already using fault semantics out of x86_emulate(), as that
> is how VT-x/SVM expects to inject the event (given suitable hardware support).
>
> However, x86_emulate() returning X86EMUL_EXCEPTION and also completing a
> register writeback is problematic for callers.
>
> Switch the logic to always using fault semantics, and leave svm_inject_trap()
> to fix up %eip if necessary.
>
> Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Boris Ostrovsky <boris.ostrovsky@oracle.com>
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH v4 10/24] x86/emul: Always use fault semantics for software events
2016-12-01 16:55 ` [PATCH v4 10/24] x86/emul: Always use fault semantics for software events Andrew Cooper
2016-12-01 19:07 ` Boris Ostrovsky
@ 2016-12-02 11:28 ` Jan Beulich
1 sibling, 0 replies; 12+ messages in thread
From: Jan Beulich @ 2016-12-02 11:28 UTC (permalink / raw)
To: Andrew Cooper
Cc: Boris Ostrovsky, Tim Deegan, Suravee Suthikulpanit, Xen-devel
>>> On 01.12.16 at 17:55, <andrew.cooper3@citrix.com> wrote:
> The common case is already using fault semantics out of x86_emulate(), as that
> is how VT-x/SVM expects to inject the event (given suitable hardware support).
>
> However, x86_emulate() returning X86EMUL_EXCEPTION and also completing a
> register writeback is problematic for callers.
>
> Switch the logic to always using fault semantics, and leave svm_inject_trap()
> to fix up %eip if necessary.
>
> Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply [flat|nested] 12+ messages in thread
* [PATCH v4 11/24] x86/emul: Implement singlestep as a retire flag
2016-12-01 16:55 [PATCH v4 for-4.9 00/24] [SUBSET] XSA-191 followup Andrew Cooper
2016-12-01 16:55 ` [PATCH v4 09/24] x86/emul: Provide a wrapper to x86_emulate() to ASSERT() certain behaviour Andrew Cooper
2016-12-01 16:55 ` [PATCH v4 10/24] x86/emul: Always use fault semantics for software events Andrew Cooper
@ 2016-12-01 16:55 ` Andrew Cooper
2016-12-02 11:32 ` Jan Beulich
2016-12-01 16:56 ` [PATCH v4 17/24] x86/pv: Avoid raising faults behind the emulators back Andrew Cooper
2016-12-01 16:56 ` [PATCH v4 18/24] x86/shadow: " Andrew Cooper
4 siblings, 1 reply; 12+ messages in thread
From: Andrew Cooper @ 2016-12-01 16:55 UTC (permalink / raw)
To: Xen-devel; +Cc: Andrew Cooper, Jan Beulich
The behaviour of singlestep is to raise #DB after the instruction has been
completed, but implementing it with inject_hw_exception() causes x86_emulate()
to return X86EMUL_EXCEPTION, despite succesfully completing execution of the
instruction, including register writeback.
Instead, use a retire flag to indicate singlestep, which causes x86_emulate()
to return X86EMUL_OKAY.
Update all callers of x86_emulate() to use the new retire flag. This fixes
the behaviour of singlestep for shadow pagetable updates and mmcfg/mmio_ro
intercepts, which previously discarded the exception.
With this change, all uses of X86EMUL_EXCEPTION from x86_emulate() are
believed to have strictly fault semantics.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Paul Durrant <paul.durrant@citrix.com>
Acked-by: Tim Deegan <tim@xen.org>
---
CC: Jan Beulich <JBeulich@suse.com>
v4:
* s/is_hvm_vcpu/has_hvm_container_domain/
* Adjust comments and entry condition into the PAE second-half case.
v3:
* New
---
xen/arch/x86/hvm/emulate.c | 3 +++
xen/arch/x86/mm.c | 11 ++++++++++-
xen/arch/x86/mm/shadow/multi.c | 35 ++++++++++++++++++++++++++++++----
xen/arch/x86/x86_emulate/x86_emulate.c | 9 ++++-----
xen/arch/x86/x86_emulate/x86_emulate.h | 6 ++++++
5 files changed, 54 insertions(+), 10 deletions(-)
diff --git a/xen/arch/x86/hvm/emulate.c b/xen/arch/x86/hvm/emulate.c
index fe62500..91c79fa 100644
--- a/xen/arch/x86/hvm/emulate.c
+++ b/xen/arch/x86/hvm/emulate.c
@@ -1788,6 +1788,9 @@ static int _hvm_emulate_one(struct hvm_emulate_ctxt *hvmemul_ctxt,
if ( rc != X86EMUL_OKAY )
return rc;
+ if ( hvmemul_ctxt->ctxt.retire.singlestep )
+ hvm_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+
new_intr_shadow = hvmemul_ctxt->intr_shadow;
/* MOV-SS instruction toggles MOV-SS shadow, else we just clear it. */
diff --git a/xen/arch/x86/mm.c b/xen/arch/x86/mm.c
index b7c7122..231c7bf 100644
--- a/xen/arch/x86/mm.c
+++ b/xen/arch/x86/mm.c
@@ -5382,6 +5382,9 @@ int ptwr_do_page_fault(struct vcpu *v, unsigned long addr,
if ( rc == X86EMUL_UNHANDLEABLE )
goto bail;
+ if ( ptwr_ctxt.ctxt.retire.singlestep )
+ pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+
perfc_incr(ptwr_emulations);
return EXCRET_fault_fixed;
@@ -5503,7 +5506,13 @@ int mmio_ro_do_page_fault(struct vcpu *v, unsigned long addr,
else
rc = x86_emulate(&ctxt, &mmio_ro_emulate_ops);
- return rc != X86EMUL_UNHANDLEABLE ? EXCRET_fault_fixed : 0;
+ if ( rc == X86EMUL_UNHANDLEABLE )
+ return 0;
+
+ if ( ctxt.retire.singlestep )
+ pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+
+ return EXCRET_fault_fixed;
}
void *alloc_xen_pagetable(void)
diff --git a/xen/arch/x86/mm/shadow/multi.c b/xen/arch/x86/mm/shadow/multi.c
index 9ee48a8..eac2330 100644
--- a/xen/arch/x86/mm/shadow/multi.c
+++ b/xen/arch/x86/mm/shadow/multi.c
@@ -3422,18 +3422,36 @@ static int sh_page_fault(struct vcpu *v,
v->arch.paging.last_write_emul_ok = 0;
#endif
+ if ( emul_ctxt.ctxt.retire.singlestep )
+ {
+ if ( has_hvm_container_domain(d) )
+ hvm_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+ else
+ pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+ }
+
#if GUEST_PAGING_LEVELS == 3 /* PAE guest */
- if ( r == X86EMUL_OKAY ) {
+ /*
+ * If there are no pending actions, emulate up to four extra instructions
+ * in the hope of catching the "second half" of a 64-bit pagetable write.
+ */
+ if ( r == X86EMUL_OKAY && !emul_ctxt.ctxt.retire.raw )
+ {
int i, emulation_count=0;
this_cpu(trace_emulate_initial_va) = va;
- /* Emulate up to four extra instructions in the hope of catching
- * the "second half" of a 64-bit pagetable write. */
+
for ( i = 0 ; i < 4 ; i++ )
{
shadow_continue_emulation(&emul_ctxt, regs);
v->arch.paging.last_write_was_pt = 0;
r = x86_emulate(&emul_ctxt.ctxt, emul_ops);
- if ( r == X86EMUL_OKAY )
+
+ /*
+ * Only continue the search for the second half if there are no
+ * exceptions or pending actions. Otherwise, give up and re-enter
+ * the guest.
+ */
+ if ( r == X86EMUL_OKAY && !emul_ctxt.ctxt.retire.raw )
{
emulation_count++;
if ( v->arch.paging.last_write_was_pt )
@@ -3449,6 +3467,15 @@ static int sh_page_fault(struct vcpu *v,
{
perfc_incr(shadow_em_ex_fail);
TRACE_SHADOW_PATH_FLAG(TRCE_SFLAG_EMULATION_LAST_FAILED);
+
+ if ( emul_ctxt.ctxt.retire.singlestep )
+ {
+ if ( has_hvm_container_domain(d) )
+ hvm_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+ else
+ pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+ }
+
break; /* Don't emulate again if we failed! */
}
}
diff --git a/xen/arch/x86/x86_emulate/x86_emulate.c b/xen/arch/x86/x86_emulate/x86_emulate.c
index fa8d98f..7bc1cd9 100644
--- a/xen/arch/x86/x86_emulate/x86_emulate.c
+++ b/xen/arch/x86/x86_emulate/x86_emulate.c
@@ -2415,7 +2415,6 @@ x86_emulate(
struct x86_emulate_state state;
int rc;
uint8_t b, d;
- bool tf = ctxt->regs->eflags & EFLG_TF;
struct operand src = { .reg = PTR_POISON };
struct operand dst = { .reg = PTR_POISON };
enum x86_swint_type swint_type;
@@ -5413,11 +5412,11 @@ x86_emulate(
if ( !mode_64bit() )
_regs.eip = (uint32_t)_regs.eip;
- *ctxt->regs = _regs;
+ /* Was singestepping active at the start of this instruction? */
+ if ( (rc == X86EMUL_OKAY) && (ctxt->regs->eflags & EFLG_TF) )
+ ctxt->retire.singlestep = true;
- /* Inject #DB if single-step tracing was enabled at instruction start. */
- if ( tf && (rc == X86EMUL_OKAY) && ops->inject_hw_exception )
- rc = ops->inject_hw_exception(EXC_DB, -1, ctxt) ? : X86EMUL_EXCEPTION;
+ *ctxt->regs = _regs;
done:
_put_fpu();
diff --git a/xen/arch/x86/x86_emulate/x86_emulate.h b/xen/arch/x86/x86_emulate/x86_emulate.h
index f4bcf36..5a4f9b7 100644
--- a/xen/arch/x86/x86_emulate/x86_emulate.h
+++ b/xen/arch/x86/x86_emulate/x86_emulate.h
@@ -483,6 +483,7 @@ struct x86_emulate_ctxt
bool hlt:1; /* Instruction HLTed. */
bool mov_ss:1; /* Instruction sets MOV-SS irq shadow. */
bool sti:1; /* Instruction sets STI irq shadow. */
+ bool singlestep:1; /* Singlestepping was active. */
};
} retire;
};
@@ -572,12 +573,17 @@ static inline int x86_emulate_wrapper(
struct x86_emulate_ctxt *ctxt,
const struct x86_emulate_ops *ops)
{
+ unsigned long orig_eip = ctxt->regs->eip;
int rc = x86_emulate(ctxt, ops);
/* Retire flags should only be set for successful instruction emulation. */
if ( rc != X86EMUL_OKAY )
ASSERT(ctxt->retire.raw == 0);
+ /* All cases returning X86EMUL_EXCEPTION should have fault semantics. */
+ if ( rc == X86EMUL_EXCEPTION )
+ ASSERT(ctxt->regs->eip == orig_eip);
+
return rc;
}
--
2.1.4
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply related [flat|nested] 12+ messages in thread* Re: [PATCH v4 11/24] x86/emul: Implement singlestep as a retire flag
2016-12-01 16:55 ` [PATCH v4 11/24] x86/emul: Implement singlestep as a retire flag Andrew Cooper
@ 2016-12-02 11:32 ` Jan Beulich
0 siblings, 0 replies; 12+ messages in thread
From: Jan Beulich @ 2016-12-02 11:32 UTC (permalink / raw)
To: Andrew Cooper; +Cc: Xen-devel
>>> On 01.12.16 at 17:55, <andrew.cooper3@citrix.com> wrote:
> The behaviour of singlestep is to raise #DB after the instruction has been
> completed, but implementing it with inject_hw_exception() causes x86_emulate()
> to return X86EMUL_EXCEPTION, despite succesfully completing execution of the
> instruction, including register writeback.
>
> Instead, use a retire flag to indicate singlestep, which causes x86_emulate()
> to return X86EMUL_OKAY.
>
> Update all callers of x86_emulate() to use the new retire flag. This fixes
> the behaviour of singlestep for shadow pagetable updates and mmcfg/mmio_ro
> intercepts, which previously discarded the exception.
>
> With this change, all uses of X86EMUL_EXCEPTION from x86_emulate() are
> believed to have strictly fault semantics.
>
> Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
> Reviewed-by: Paul Durrant <paul.durrant@citrix.com>
> Acked-by: Tim Deegan <tim@xen.org>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply [flat|nested] 12+ messages in thread
* [PATCH v4 17/24] x86/pv: Avoid raising faults behind the emulators back
2016-12-01 16:55 [PATCH v4 for-4.9 00/24] [SUBSET] XSA-191 followup Andrew Cooper
` (2 preceding siblings ...)
2016-12-01 16:55 ` [PATCH v4 11/24] x86/emul: Implement singlestep as a retire flag Andrew Cooper
@ 2016-12-01 16:56 ` Andrew Cooper
2016-12-01 16:56 ` [PATCH v4 18/24] x86/shadow: " Andrew Cooper
4 siblings, 0 replies; 12+ messages in thread
From: Andrew Cooper @ 2016-12-01 16:56 UTC (permalink / raw)
To: Xen-devel; +Cc: Andrew Cooper
Use x86_emul_pagefault() rather than pv_inject_page_fault() to cause raised
pagefaults to be known to the emulator. This requires altering the callers of
x86_emulate() to properly re-inject the event.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Acked-by: Tim Deegan <tim@xen.org>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
---
v4:
* Tweak comment wording.
* Drop default cases.
v3:
* Split out #DB handling to an earlier part of the series
* Don't raise #GP faults for unexpected events, but do return back to the
guest.
v2:
* New
---
xen/arch/x86/mm.c | 101 ++++++++++++++++++++++++++++++++++--------------------
1 file changed, 63 insertions(+), 38 deletions(-)
diff --git a/xen/arch/x86/mm.c b/xen/arch/x86/mm.c
index 5d59479..14552a1 100644
--- a/xen/arch/x86/mm.c
+++ b/xen/arch/x86/mm.c
@@ -5136,7 +5136,7 @@ static int ptwr_emulated_read(
if ( !__addr_ok(addr) ||
(rc = __copy_from_user(p_data, (void *)addr, bytes)) )
{
- pv_inject_page_fault(0, addr + bytes - rc); /* Read fault. */
+ x86_emul_pagefault(0, addr + bytes - rc, ctxt); /* Read fault. */
return X86EMUL_EXCEPTION;
}
@@ -5177,8 +5177,9 @@ static int ptwr_emulated_update(
addr &= ~(sizeof(paddr_t)-1);
if ( (rc = copy_from_user(&full, (void *)addr, sizeof(paddr_t))) != 0 )
{
- pv_inject_page_fault(0, /* Read fault. */
- addr + sizeof(paddr_t) - rc);
+ x86_emul_pagefault(0, /* Read fault. */
+ addr + sizeof(paddr_t) - rc,
+ &ptwr_ctxt->ctxt);
return X86EMUL_EXCEPTION;
}
/* Mask out bits provided by caller. */
@@ -5379,27 +5380,38 @@ int ptwr_do_page_fault(struct vcpu *v, unsigned long addr,
page_unlock(page);
put_page(page);
- /*
- * The previous lack of inject_{sw,hw}*() hooks caused exceptions raised
- * by the emulator itself to become X86EMUL_UNHANDLEABLE. Such exceptions
- * now set event_pending instead. Exceptions raised behind the back of
- * the emulator don't yet set event_pending.
- *
- * For now, cause such cases to return to the X86EMUL_UNHANDLEABLE path,
- * for no functional change from before. Future patches will fix this
- * properly.
- */
- if ( rc == X86EMUL_EXCEPTION && ptwr_ctxt.ctxt.event_pending )
- rc = X86EMUL_UNHANDLEABLE;
+ /* More strict than x86_emulate_wrapper(), as this is now true for PV. */
+ ASSERT(ptwr_ctxt.ctxt.event_pending == (rc == X86EMUL_EXCEPTION));
- if ( rc == X86EMUL_UNHANDLEABLE )
- goto bail;
+ switch ( rc )
+ {
+ case X86EMUL_EXCEPTION:
+ /*
+ * This emulation only covers writes to pagetables which are marked
+ * read-only by Xen. We tolerate #PF (in case a concurrent pagetable
+ * update has succeeded on a different vcpu). Anything else is an
+ * emulation bug, or a guest playing with the instruction stream under
+ * Xen's feet.
+ */
+ if ( ptwr_ctxt.ctxt.event.type == X86_EVENTTYPE_HW_EXCEPTION &&
+ ptwr_ctxt.ctxt.event.vector == TRAP_page_fault )
+ pv_inject_event(&ptwr_ctxt.ctxt.event);
+ else
+ gdprintk(XENLOG_WARNING,
+ "Unexpected event (type %u, vector %#x) from emulation\n",
+ ptwr_ctxt.ctxt.event.type, ptwr_ctxt.ctxt.event.vector);
- if ( ptwr_ctxt.ctxt.retire.singlestep )
- pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+ /* Fallthrough */
+ case X86EMUL_OKAY:
- perfc_incr(ptwr_emulations);
- return EXCRET_fault_fixed;
+ if ( ptwr_ctxt.ctxt.retire.singlestep )
+ pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+
+ /* Fallthrough */
+ case X86EMUL_RETRY:
+ perfc_incr(ptwr_emulations);
+ return EXCRET_fault_fixed;
+ }
bail:
return 0;
@@ -5519,26 +5531,39 @@ int mmio_ro_do_page_fault(struct vcpu *v, unsigned long addr,
else
rc = x86_emulate(&ctxt, &mmio_ro_emulate_ops);
- /*
- * The previous lack of inject_{sw,hw}*() hooks caused exceptions raised
- * by the emulator itself to become X86EMUL_UNHANDLEABLE. Such exceptions
- * now set event_pending instead. Exceptions raised behind the back of
- * the emulator don't yet set event_pending.
- *
- * For now, cause such cases to return to the X86EMUL_UNHANDLEABLE path,
- * for no functional change from before. Future patches will fix this
- * properly.
- */
- if ( rc == X86EMUL_EXCEPTION && ctxt.event_pending )
- rc = X86EMUL_UNHANDLEABLE;
+ /* More strict than x86_emulate_wrapper(), as this is now true for PV. */
+ ASSERT(ctxt.event_pending == (rc == X86EMUL_EXCEPTION));
- if ( rc == X86EMUL_UNHANDLEABLE )
- return 0;
+ switch ( rc )
+ {
+ case X86EMUL_EXCEPTION:
+ /*
+ * This emulation only covers writes to MMCFG space or read-only MFNs.
+ * We tolerate #PF (from hitting an adjacent page or a successful
+ * concurrent pagetable update). Anything else is an emulation bug,
+ * or a guest playing with the instruction stream under Xen's feet.
+ */
+ if ( ctxt.event.type == X86_EVENTTYPE_HW_EXCEPTION &&
+ ctxt.event.vector == TRAP_page_fault )
+ pv_inject_event(&ctxt.event);
+ else
+ gdprintk(XENLOG_WARNING,
+ "Unexpected event (type %u, vector %#x) from emulation\n",
+ ctxt.event.type, ctxt.event.vector);
+
+ /* Fallthrough */
+ case X86EMUL_OKAY:
- if ( ctxt.retire.singlestep )
- pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
+ if ( ctxt.retire.singlestep )
+ pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
- return EXCRET_fault_fixed;
+ /* Fallthrough */
+ case X86EMUL_RETRY:
+ perfc_incr(ptwr_emulations);
+ return EXCRET_fault_fixed;
+ }
+
+ return 0;
}
void *alloc_xen_pagetable(void)
--
2.1.4
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply related [flat|nested] 12+ messages in thread* [PATCH v4 18/24] x86/shadow: Avoid raising faults behind the emulators back
2016-12-01 16:55 [PATCH v4 for-4.9 00/24] [SUBSET] XSA-191 followup Andrew Cooper
` (3 preceding siblings ...)
2016-12-01 16:56 ` [PATCH v4 17/24] x86/pv: Avoid raising faults behind the emulators back Andrew Cooper
@ 2016-12-01 16:56 ` Andrew Cooper
2016-12-02 11:37 ` Jan Beulich
4 siblings, 1 reply; 12+ messages in thread
From: Andrew Cooper @ 2016-12-01 16:56 UTC (permalink / raw)
To: Xen-devel; +Cc: Andrew Cooper, Jan Beulich
Use x86_emul_{hw_exception,pagefault}() rather than
{pv,hvm}_inject_page_fault() and hvm_inject_hw_exception() to cause raised
faults to be known to the emulator. This requires altering the callers of
x86_emulate() to properly re-inject the event.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Acked-by: Tim Deegan <tim@xen.org>
---
CC: Jan Beulich <JBeulich@suse.com>
v4:
* Fix the commit message following v3's changes.
* s/is_hvm_vcpu/has_hvm_container_domain/
* Adjust description of permitted exceptions.
* Disallow #GP/#SS with non-zero error codes.
v3:
* Split out #DB handling to an earlier part of the series
* Don't inject #GP faults for unexpected events, but do reenter the guest.
v2:
* New
---
xen/arch/x86/mm/shadow/common.c | 13 ++++++-------
xen/arch/x86/mm/shadow/multi.c | 40 +++++++++++++++++++++++++++++-----------
2 files changed, 35 insertions(+), 18 deletions(-)
diff --git a/xen/arch/x86/mm/shadow/common.c b/xen/arch/x86/mm/shadow/common.c
index f07803b..e509cc1 100644
--- a/xen/arch/x86/mm/shadow/common.c
+++ b/xen/arch/x86/mm/shadow/common.c
@@ -162,8 +162,9 @@ static int hvm_translate_linear_addr(
if ( !okay )
{
- hvm_inject_hw_exception(
- (seg == x86_seg_ss) ? TRAP_stack_error : TRAP_gp_fault, 0);
+ x86_emul_hw_exception(
+ (seg == x86_seg_ss) ? TRAP_stack_error : TRAP_gp_fault,
+ 0, &sh_ctxt->ctxt);
return X86EMUL_EXCEPTION;
}
@@ -323,7 +324,7 @@ pv_emulate_read(enum x86_segment seg,
if ( (rc = copy_from_user(p_data, (void *)offset, bytes)) != 0 )
{
- pv_inject_page_fault(0, offset + bytes - rc); /* Read fault. */
+ x86_emul_pagefault(0, offset + bytes - rc, ctxt); /* Read fault. */
return X86EMUL_EXCEPTION;
}
@@ -1720,10 +1721,8 @@ static mfn_t emulate_gva_to_mfn(struct vcpu *v, unsigned long vaddr,
gfn = paging_get_hostmode(v)->gva_to_gfn(v, NULL, vaddr, &pfec);
if ( gfn == gfn_x(INVALID_GFN) )
{
- if ( is_hvm_vcpu(v) )
- hvm_inject_page_fault(pfec, vaddr);
- else
- pv_inject_page_fault(pfec, vaddr);
+ x86_emul_pagefault(pfec, vaddr, &sh_ctxt->ctxt);
+
return _mfn(BAD_GVA_TO_GFN);
}
diff --git a/xen/arch/x86/mm/shadow/multi.c b/xen/arch/x86/mm/shadow/multi.c
index 7d9081b..fc18d65 100644
--- a/xen/arch/x86/mm/shadow/multi.c
+++ b/xen/arch/x86/mm/shadow/multi.c
@@ -3373,18 +3373,36 @@ static int sh_page_fault(struct vcpu *v,
r = x86_emulate(&emul_ctxt.ctxt, emul_ops);
- /*
- * The previous lack of inject_{sw,hw}*() hooks caused exceptions raised
- * by the emulator itself to become X86EMUL_UNHANDLEABLE. Such exceptions
- * now set event_pending instead. Exceptions raised behind the back of
- * the emulator don't yet set event_pending.
- *
- * For now, cause such cases to return to the X86EMUL_UNHANDLEABLE path,
- * for no functional change from before. Future patches will fix this
- * properly.
- */
if ( r == X86EMUL_EXCEPTION && emul_ctxt.ctxt.event_pending )
- r = X86EMUL_UNHANDLEABLE;
+ {
+ /*
+ * This emulation covers writes to shadow pagetables. We tolerate #PF
+ * (from accesses spanning pages, concurrent paging updated from
+ * vcpus, etc) and #GP[0]/#SS[0] (from segmentation errors). Anything
+ * else is an emulation bug, or a guest playing with the instruction
+ * stream under Xen's feet.
+ */
+ if ( emul_ctxt.ctxt.event.type == X86_EVENTTYPE_HW_EXCEPTION &&
+ ((emul_ctxt.ctxt.event.vector == TRAP_page_fault) ||
+ (((emul_ctxt.ctxt.event.vector == TRAP_gp_fault) ||
+ (emul_ctxt.ctxt.event.vector == TRAP_stack_error)) &&
+ emul_ctxt.ctxt.event.error_code == 0)) )
+ {
+ if ( has_hvm_container_domain(d) )
+ hvm_inject_event(&emul_ctxt.ctxt.event);
+ else
+ pv_inject_event(&emul_ctxt.ctxt.event);
+
+ goto emulate_done;
+ }
+ else
+ {
+ SHADOW_PRINTK(
+ "Unexpected event (type %u, vector %#x) from emulation\n",
+ emul_ctxt.ctxt.event.type, emul_ctxt.ctxt.event.vector);
+ r = X86EMUL_UNHANDLEABLE;
+ }
+ }
/*
* NB. We do not unshadow on X86EMUL_EXCEPTION. It's not clear that it
--
2.1.4
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply related [flat|nested] 12+ messages in thread* Re: [PATCH v4 18/24] x86/shadow: Avoid raising faults behind the emulators back
2016-12-01 16:56 ` [PATCH v4 18/24] x86/shadow: " Andrew Cooper
@ 2016-12-02 11:37 ` Jan Beulich
2016-12-02 11:48 ` Andrew Cooper
0 siblings, 1 reply; 12+ messages in thread
From: Jan Beulich @ 2016-12-02 11:37 UTC (permalink / raw)
To: Andrew Cooper; +Cc: Xen-devel
>>> On 01.12.16 at 17:56, <andrew.cooper3@citrix.com> wrote:
> Use x86_emul_{hw_exception,pagefault}() rather than
> {pv,hvm}_inject_page_fault() and hvm_inject_hw_exception() to cause raised
> faults to be known to the emulator. This requires altering the callers of
> x86_emulate() to properly re-inject the event.
>
> Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
> Acked-by: Tim Deegan <tim@xen.org>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
albeit ...
> --- a/xen/arch/x86/mm/shadow/multi.c
> +++ b/xen/arch/x86/mm/shadow/multi.c
> @@ -3373,18 +3373,36 @@ static int sh_page_fault(struct vcpu *v,
>
> r = x86_emulate(&emul_ctxt.ctxt, emul_ops);
>
> - /*
> - * The previous lack of inject_{sw,hw}*() hooks caused exceptions raised
> - * by the emulator itself to become X86EMUL_UNHANDLEABLE. Such exceptions
> - * now set event_pending instead. Exceptions raised behind the back of
> - * the emulator don't yet set event_pending.
> - *
> - * For now, cause such cases to return to the X86EMUL_UNHANDLEABLE path,
> - * for no functional change from before. Future patches will fix this
> - * properly.
> - */
> if ( r == X86EMUL_EXCEPTION && emul_ctxt.ctxt.event_pending )
> - r = X86EMUL_UNHANDLEABLE;
> + {
> + /*
> + * This emulation covers writes to shadow pagetables. We tolerate #PF
> + * (from accesses spanning pages, concurrent paging updated from
> + * vcpus, etc) and #GP[0]/#SS[0] (from segmentation errors). Anything
> + * else is an emulation bug, or a guest playing with the instruction
> + * stream under Xen's feet.
> + */
> + if ( emul_ctxt.ctxt.event.type == X86_EVENTTYPE_HW_EXCEPTION &&
> + ((emul_ctxt.ctxt.event.vector == TRAP_page_fault) ||
> + (((emul_ctxt.ctxt.event.vector == TRAP_gp_fault) ||
> + (emul_ctxt.ctxt.event.vector == TRAP_stack_error)) &&
> + emul_ctxt.ctxt.event.error_code == 0)) )
> + {
> + if ( has_hvm_container_domain(d) )
> + hvm_inject_event(&emul_ctxt.ctxt.event);
> + else
> + pv_inject_event(&emul_ctxt.ctxt.event);
> +
> + goto emulate_done;
> + }
> + else
... the else following a goto is kind of pointless and imo makes the
code slightly harder to follow.
Jan
> + {
> + SHADOW_PRINTK(
> + "Unexpected event (type %u, vector %#x) from emulation\n",
> + emul_ctxt.ctxt.event.type, emul_ctxt.ctxt.event.vector);
> + r = X86EMUL_UNHANDLEABLE;
> + }
> + }
>
> /*
> * NB. We do not unshadow on X86EMUL_EXCEPTION. It's not clear that it
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply [flat|nested] 12+ messages in thread* Re: [PATCH v4 18/24] x86/shadow: Avoid raising faults behind the emulators back
2016-12-02 11:37 ` Jan Beulich
@ 2016-12-02 11:48 ` Andrew Cooper
0 siblings, 0 replies; 12+ messages in thread
From: Andrew Cooper @ 2016-12-02 11:48 UTC (permalink / raw)
To: Jan Beulich; +Cc: Xen-devel
On 02/12/16 11:37, Jan Beulich wrote:
>> --- a/xen/arch/x86/mm/shadow/multi.c
>> +++ b/xen/arch/x86/mm/shadow/multi.c
>> @@ -3373,18 +3373,36 @@ static int sh_page_fault(struct vcpu *v,
>>
>> r = x86_emulate(&emul_ctxt.ctxt, emul_ops);
>>
>> - /*
>> - * The previous lack of inject_{sw,hw}*() hooks caused exceptions raised
>> - * by the emulator itself to become X86EMUL_UNHANDLEABLE. Such exceptions
>> - * now set event_pending instead. Exceptions raised behind the back of
>> - * the emulator don't yet set event_pending.
>> - *
>> - * For now, cause such cases to return to the X86EMUL_UNHANDLEABLE path,
>> - * for no functional change from before. Future patches will fix this
>> - * properly.
>> - */
>> if ( r == X86EMUL_EXCEPTION && emul_ctxt.ctxt.event_pending )
>> - r = X86EMUL_UNHANDLEABLE;
>> + {
>> + /*
>> + * This emulation covers writes to shadow pagetables. We tolerate #PF
>> + * (from accesses spanning pages, concurrent paging updated from
>> + * vcpus, etc) and #GP[0]/#SS[0] (from segmentation errors). Anything
>> + * else is an emulation bug, or a guest playing with the instruction
>> + * stream under Xen's feet.
>> + */
>> + if ( emul_ctxt.ctxt.event.type == X86_EVENTTYPE_HW_EXCEPTION &&
>> + ((emul_ctxt.ctxt.event.vector == TRAP_page_fault) ||
>> + (((emul_ctxt.ctxt.event.vector == TRAP_gp_fault) ||
>> + (emul_ctxt.ctxt.event.vector == TRAP_stack_error)) &&
>> + emul_ctxt.ctxt.event.error_code == 0)) )
>> + {
>> + if ( has_hvm_container_domain(d) )
>> + hvm_inject_event(&emul_ctxt.ctxt.event);
>> + else
>> + pv_inject_event(&emul_ctxt.ctxt.event);
>> +
>> + goto emulate_done;
>> + }
>> + else
> ... the else following a goto is kind of pointless and imo makes the
> code slightly harder to follow.
Oh - good point. This is actually a slight behavioural change, as it
skips the trace. I will drop the goto.
~Andrew
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
https://lists.xen.org/xen-devel
^ permalink raw reply [flat|nested] 12+ messages in thread