When invoked by compat mode, mode_64bit() will be false at the start of
emulation. The logic after complete_insn, however, needs to consider the
mode switched into, in particular to avoid truncating RIP.
Inspired by / paralleling and extending Linux commit
943dea8af21b ("KVM:
x86: Update emulator context mode if SYSENTER xfers to 64-bit mode").
While there, tighten a related assertion in x86_emulate_wrapper() - we
want to be sure to not switch into an impossible mode when the code gets
built for 32-bit only (as is possible for the test harness).
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Andrew Cooper <andrew.cooper3@citirix.com>
(rc = ops->write_segment(x86_seg_ss, &sreg, ctxt)) )
goto done;
+ if ( ctxt->lma )
+ /* In particular mode_64bit() needs to return true from here on. */
+ ctxt->addr_size = ctxt->sp_size = 64;
+
/*
* SYSCALL (unlike most instructions) evaluates its singlestep action
* based on the resulting EFLAGS.TF, not the starting EFLAGS.TF.
ctxt)) != X86EMUL_OKAY )
goto done;
+ if ( ctxt->lma )
+ /* In particular mode_64bit() needs to return true from here on. */
+ ctxt->addr_size = ctxt->sp_size = 64;
+
singlestep = _regs.eflags & X86_EFLAGS_TF;
break;
unsigned long orig_ip = ctxt->regs->r(ip);
int rc;
+#ifdef __x86_64__
if ( mode_64bit() )
ASSERT(ctxt->lma);
+#else
+ ASSERT(!ctxt->lma && !mode_64bit());
+#endif
rc = x86_emulate(ctxt, ops);