File 58343ec2-x86emul-fix-huge-bit-offset-handling.patch of Package xen.6117
Subject: x86emul: fix huge bit offset handling
From: Jan Beulich jbeulich@suse.com Tue Nov 22 14:29:03 2016 +0100
Date: Tue Nov 22 14:29:03 2016 +0100:
Git: 1530da267edf0799b7cc754c9e68ede5d4cc9a09
We must never chop off the high 32 bits.
This is CVE-2016-9383 / XSA-195.
Reported-by: George Dunlap <george.dunlap@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
master commit: 1c6c2d60d205f71ede0fbbd9047e459112f576db
master date: 2016-11-22 13:49:06 +0100
Index: xen-4.5.5-testing/xen/arch/x86/x86_emulate/x86_emulate.c
===================================================================
--- xen-4.5.5-testing.orig/xen/arch/x86/x86_emulate/x86_emulate.c
+++ xen-4.5.5-testing/xen/arch/x86/x86_emulate/x86_emulate.c
@@ -1976,6 +1976,12 @@ x86_emulate(
else
{
/*
+ * Instructions such as bt can reference an arbitrary offset from
+ * their memory operand, but the instruction doing the actual
+ * emulation needs the appropriate op_bytes read from memory.
+ * Adjust both the source register and memory operand to make an
+ * equivalent instruction.
+ *
* EA += BitOffset DIV op_bytes*8
* BitOffset = BitOffset MOD op_bytes*8
* DIV truncates towards negative infinity.
@@ -1987,14 +1993,15 @@ x86_emulate(
src.val = (int32_t)src.val;
if ( (long)src.val < 0 )
{
- unsigned long byte_offset;
- byte_offset = op_bytes + (((-src.val-1) >> 3) & ~(op_bytes-1));
+ unsigned long byte_offset =
+ op_bytes + (((-src.val - 1) >> 3) & ~(op_bytes - 1L));
+
ea.mem.off -= byte_offset;
src.val = (byte_offset << 3) + src.val;
}
else
{
- ea.mem.off += (src.val >> 3) & ~(op_bytes - 1);
+ ea.mem.off += (src.val >> 3) & ~(op_bytes - 1L);
src.val &= (op_bytes << 3) - 1;
}
}