Skip to content

Commit

Permalink
[PATCH] i386: fix get_segment_eip() with vm86 segments
Browse files Browse the repository at this point in the history
We need to check for vm86 mode first before looking at selector privilege
bits.

Segment limit is always base + 64k and only the low 16 bits of EIP are
significant in vm86 mode.

Signed-off-by: Chuck Ebbert <76306.1226@compuserve.com>
Cc: Andi Kleen <ak@muc.de>
Cc: Zachary Amsden <zach@vmware.com>
Cc: Rohit Seth <rohitseth@google.com>
Acked-by: Ananth N Mavinakayanahalli <ananth@in.ibm.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
  • Loading branch information
Chuck Ebbert authored and Linus Torvalds committed Jun 23, 2006
1 parent 110cb1d commit 19964fe
Showing 1 changed file with 7 additions and 4 deletions.
11 changes: 7 additions & 4 deletions arch/i386/mm/fault.c
Original file line number Diff line number Diff line change
Expand Up @@ -77,12 +77,15 @@ static inline unsigned long get_segment_eip(struct pt_regs *regs,
unsigned seg = regs->xcs & 0xffff;
u32 seg_ar, seg_limit, base, *desc;

/* Unlikely, but must come before segment checks. */
if (unlikely(regs->eflags & VM_MASK)) {
base = seg << 4;
*eip_limit = base + 0xffff;
return base + (eip & 0xffff);
}

/* The standard kernel/user address space limit. */
*eip_limit = (seg & 3) ? USER_DS.seg : KERNEL_DS.seg;

/* Unlikely, but must come before segment checks. */
if (unlikely((regs->eflags & VM_MASK) != 0))
return eip + (seg << 4);

/* By far the most common cases. */
if (likely(seg == __USER_CS || seg == __KERNEL_CS))
Expand Down

0 comments on commit 19964fe

Please sign in to comment.