Commit 6fd1e396 authored by Julian Stecklina's avatar Julian Stecklina Committed by Sean Christopherson

KVM: x86: Clean up partially uninitialized integer in emulate_pop()

Explicitly zero out variables passed to emulate_pop() as output params
to harden against consuming uninitialized data, and to make sanitizers
happy.  Many flows that use emulate_pop() pass an "unsigned long" so as
to be able to hold the largest possible operand, but the actual number
of bytes written is usually the word with of the vCPU.  E.g. if the vCPU
is in 16-bit or 32-bit mode (on a 64-bit host), the upper portion of the
output param will be uninitialized.

Passing around the uninitialized data is benign, as actual KVM usage of
the output is also tied to the word width, but passing around
uninitialized data makes some sanitizers rightly complain.

Note, initializing the data in emulate_pop() is not a safe alternative,
e.g. it would result in em_leave() clobbering RBP[31:16] if LEAVE were
emulated with a 16-bit stack.
Signed-off-by: default avatarJulian Stecklina <julian.stecklina@cyberus-technology.de>
Link: https://lore.kernel.org/r/20231009092054.556935-1-julian.stecklina@cyberus-technology.de
[sean: massage changelog, drop em_popa() variable size change]]
Signed-off-by: default avatarSean Christopherson <seanjc@google.com>
parent 03f6298c
...@@ -1863,7 +1863,8 @@ static int emulate_popf(struct x86_emulate_ctxt *ctxt, ...@@ -1863,7 +1863,8 @@ static int emulate_popf(struct x86_emulate_ctxt *ctxt,
void *dest, int len) void *dest, int len)
{ {
int rc; int rc;
unsigned long val, change_mask; unsigned long val = 0;
unsigned long change_mask;
int iopl = (ctxt->eflags & X86_EFLAGS_IOPL) >> X86_EFLAGS_IOPL_BIT; int iopl = (ctxt->eflags & X86_EFLAGS_IOPL) >> X86_EFLAGS_IOPL_BIT;
int cpl = ctxt->ops->cpl(ctxt); int cpl = ctxt->ops->cpl(ctxt);
...@@ -1954,7 +1955,7 @@ static int em_push_sreg(struct x86_emulate_ctxt *ctxt) ...@@ -1954,7 +1955,7 @@ static int em_push_sreg(struct x86_emulate_ctxt *ctxt)
static int em_pop_sreg(struct x86_emulate_ctxt *ctxt) static int em_pop_sreg(struct x86_emulate_ctxt *ctxt)
{ {
int seg = ctxt->src2.val; int seg = ctxt->src2.val;
unsigned long selector; unsigned long selector = 0;
int rc; int rc;
rc = emulate_pop(ctxt, &selector, 2); rc = emulate_pop(ctxt, &selector, 2);
...@@ -2000,7 +2001,7 @@ static int em_popa(struct x86_emulate_ctxt *ctxt) ...@@ -2000,7 +2001,7 @@ static int em_popa(struct x86_emulate_ctxt *ctxt)
{ {
int rc = X86EMUL_CONTINUE; int rc = X86EMUL_CONTINUE;
int reg = VCPU_REGS_RDI; int reg = VCPU_REGS_RDI;
u32 val; u32 val = 0;
while (reg >= VCPU_REGS_RAX) { while (reg >= VCPU_REGS_RAX) {
if (reg == VCPU_REGS_RSP) { if (reg == VCPU_REGS_RSP) {
...@@ -2229,7 +2230,7 @@ static int em_cmpxchg8b(struct x86_emulate_ctxt *ctxt) ...@@ -2229,7 +2230,7 @@ static int em_cmpxchg8b(struct x86_emulate_ctxt *ctxt)
static int em_ret(struct x86_emulate_ctxt *ctxt) static int em_ret(struct x86_emulate_ctxt *ctxt)
{ {
int rc; int rc;
unsigned long eip; unsigned long eip = 0;
rc = emulate_pop(ctxt, &eip, ctxt->op_bytes); rc = emulate_pop(ctxt, &eip, ctxt->op_bytes);
if (rc != X86EMUL_CONTINUE) if (rc != X86EMUL_CONTINUE)
...@@ -2241,7 +2242,8 @@ static int em_ret(struct x86_emulate_ctxt *ctxt) ...@@ -2241,7 +2242,8 @@ static int em_ret(struct x86_emulate_ctxt *ctxt)
static int em_ret_far(struct x86_emulate_ctxt *ctxt) static int em_ret_far(struct x86_emulate_ctxt *ctxt)
{ {
int rc; int rc;
unsigned long eip, cs; unsigned long eip = 0;
unsigned long cs = 0;
int cpl = ctxt->ops->cpl(ctxt); int cpl = ctxt->ops->cpl(ctxt);
struct desc_struct new_desc; struct desc_struct new_desc;
...@@ -3184,7 +3186,7 @@ static int em_call_far(struct x86_emulate_ctxt *ctxt) ...@@ -3184,7 +3186,7 @@ static int em_call_far(struct x86_emulate_ctxt *ctxt)
static int em_ret_near_imm(struct x86_emulate_ctxt *ctxt) static int em_ret_near_imm(struct x86_emulate_ctxt *ctxt)
{ {
int rc; int rc;
unsigned long eip; unsigned long eip = 0;
rc = emulate_pop(ctxt, &eip, ctxt->op_bytes); rc = emulate_pop(ctxt, &eip, ctxt->op_bytes);
if (rc != X86EMUL_CONTINUE) if (rc != X86EMUL_CONTINUE)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment