Re: [2.6.22.y] {06/17} - handle-bogus-%cs-selector-in-single-step-instruction-decoding - series for stable kernel #2
From: Roland McGrath <[EMAIL PROTECTED]> Date: Mon, 16 Jul 2007 08:03:16 + (-0700) Subject: Handle bogus %cs selector in single-step instruction decoding Patch-mainline: 2.6.23-rc1 References: 326270, CVE-2007-3731 Handle bogus %cs selector in single-step instruction decoding The code for LDT segment selectors was not robust in the face of a bogus selector set in %cs via ptrace before the single-step was done. Signed-off-by: Roland McGrath <[EMAIL PROTECTED]> Signed-off-by: Linus Torvalds <[EMAIL PROTECTED]> Acked-by: Jeff Mahoney <[EMAIL PROTECTED]> --- arch/i386/kernel/ptrace.c | 22 +++--- arch/x86_64/kernel/ptrace.c | 23 --- 2 files changed, 31 insertions(+), 14 deletions(-) diff --git a/arch/i386/kernel/ptrace.c b/arch/i386/kernel/ptrace.c index 1c075f5..0c8f00e 100644 --- a/arch/i386/kernel/ptrace.c +++ b/arch/i386/kernel/ptrace.c @@ -164,14 +164,22 @@ static unsigned long convert_eip_to_linear(struct task_struct *child, struct pt_ u32 *desc; unsigned long base; - down(>mm->context.sem); - desc = child->mm->context.ldt + (seg & ~7); - base = (desc[0] >> 16) | ((desc[1] & 0xff) << 16) | (desc[1] & 0xff00); + seg &= ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] >> 22) & 1)) - addr &= 0x; - addr += base; + down(>mm->context.sem); + if (unlikely((seg >> 3) >= child->mm->context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child->mm->context.ldt + seg; + base = ((desc[0] >> 16) | + ((desc[1] & 0xff) << 16) | + (desc[1] & 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] >> 22) & 1)) + addr &= 0x; + addr += base; + } up(>mm->context.sem); } return addr; diff --git a/arch/x86_64/kernel/ptrace.c b/arch/x86_64/kernel/ptrace.c index fa6775e..e83cc67 100644 --- a/arch/x86_64/kernel/ptrace.c +++ b/arch/x86_64/kernel/ptrace.c @@ -102,16 +102,25 @@ unsigned long convert_rip_to_linear(struct task_struct *child, struct pt_regs *r u32 *desc; unsigned long base; - down(>mm->context.sem); - desc = child->mm->context.ldt + (seg & ~7); - base = (desc[0] >> 16) | ((desc[1] & 0xff) << 16) | (desc[1] & 0xff00); + seg &= ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] >> 22) & 1)) - addr &= 0x; - addr += base; + down(>mm->context.sem); + if (unlikely((seg >> 3) >= child->mm->context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child->mm->context.ldt + seg; + base = ((desc[0] >> 16) | + ((desc[1] & 0xff) << 16) | + (desc[1] & 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] >> 22) & 1)) + addr &= 0x; + addr += base; + } up(>mm->context.sem); } + return addr; } On 2/2/08, Oliver Pinter (Pintér Olivér) <[EMAIL PROTECTED]> wrote: > mainline: 29eb51101c02df517ca64ec472d7501127ad1da8 > > > -- > Thanks, > Oliver > -- Thanks, Oliver -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
Re: [2.6.22.y] {06/17} - handle-bogus-%cs-selector-in-single-step-instruction-decoding - series for stable kernel #2
From: Roland McGrath [EMAIL PROTECTED] Date: Mon, 16 Jul 2007 08:03:16 + (-0700) Subject: Handle bogus %cs selector in single-step instruction decoding Patch-mainline: 2.6.23-rc1 References: 326270, CVE-2007-3731 Handle bogus %cs selector in single-step instruction decoding The code for LDT segment selectors was not robust in the face of a bogus selector set in %cs via ptrace before the single-step was done. Signed-off-by: Roland McGrath [EMAIL PROTECTED] Signed-off-by: Linus Torvalds [EMAIL PROTECTED] Acked-by: Jeff Mahoney [EMAIL PROTECTED] --- arch/i386/kernel/ptrace.c | 22 +++--- arch/x86_64/kernel/ptrace.c | 23 --- 2 files changed, 31 insertions(+), 14 deletions(-) diff --git a/arch/i386/kernel/ptrace.c b/arch/i386/kernel/ptrace.c index 1c075f5..0c8f00e 100644 --- a/arch/i386/kernel/ptrace.c +++ b/arch/i386/kernel/ptrace.c @@ -164,14 +164,22 @@ static unsigned long convert_eip_to_linear(struct task_struct *child, struct pt_ u32 *desc; unsigned long base; - down(child-mm-context.sem); - desc = child-mm-context.ldt + (seg ~7); - base = (desc[0] 16) | ((desc[1] 0xff) 16) | (desc[1] 0xff00); + seg = ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] 22) 1)) - addr = 0x; - addr += base; + down(child-mm-context.sem); + if (unlikely((seg 3) = child-mm-context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child-mm-context.ldt + seg; + base = ((desc[0] 16) | + ((desc[1] 0xff) 16) | + (desc[1] 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] 22) 1)) + addr = 0x; + addr += base; + } up(child-mm-context.sem); } return addr; diff --git a/arch/x86_64/kernel/ptrace.c b/arch/x86_64/kernel/ptrace.c index fa6775e..e83cc67 100644 --- a/arch/x86_64/kernel/ptrace.c +++ b/arch/x86_64/kernel/ptrace.c @@ -102,16 +102,25 @@ unsigned long convert_rip_to_linear(struct task_struct *child, struct pt_regs *r u32 *desc; unsigned long base; - down(child-mm-context.sem); - desc = child-mm-context.ldt + (seg ~7); - base = (desc[0] 16) | ((desc[1] 0xff) 16) | (desc[1] 0xff00); + seg = ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] 22) 1)) - addr = 0x; - addr += base; + down(child-mm-context.sem); + if (unlikely((seg 3) = child-mm-context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child-mm-context.ldt + seg; + base = ((desc[0] 16) | + ((desc[1] 0xff) 16) | + (desc[1] 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] 22) 1)) + addr = 0x; + addr += base; + } up(child-mm-context.sem); } + return addr; } On 2/2/08, Oliver Pinter (Pintér Olivér) [EMAIL PROTECTED] wrote: mainline: 29eb51101c02df517ca64ec472d7501127ad1da8 -- Thanks, Oliver -- Thanks, Oliver -- To unsubscribe from this list: send the line unsubscribe linux-kernel in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[2.6.22.y] {06/17} - handle-bogus-%cs-selector-in-single-step-instruction-decoding - series for stable kernel #2
mainline: 29eb51101c02df517ca64ec472d7501127ad1da8 -- Thanks, Oliver --- Begin Message --- Handle bogus %cs selector in single-step instruction decoding The code for LDT segment selectors was not robust in the face of a bogus selector set in %cs via ptrace before the single-step was done. Signed-off-by: Roland McGrath <[EMAIL PROTECTED]> Signed-off-by: Linus Torvalds <[EMAIL PROTECTED]> Acked-by: Jeff Mahoney <[EMAIL PROTECTED]> --- arch/i386/kernel/ptrace.c | 22 +++--- arch/x86_64/kernel/ptrace.c | 23 --- 2 files changed, 31 insertions(+), 14 deletions(-) diff --git a/arch/i386/kernel/ptrace.c b/arch/i386/kernel/ptrace.c index 1c075f5..0c8f00e 100644 --- a/arch/i386/kernel/ptrace.c +++ b/arch/i386/kernel/ptrace.c @@ -164,14 +164,22 @@ static unsigned long convert_eip_to_linear(struct task_struct *child, struct pt_ u32 *desc; unsigned long base; - down(>mm->context.sem); - desc = child->mm->context.ldt + (seg & ~7); - base = (desc[0] >> 16) | ((desc[1] & 0xff) << 16) | (desc[1] & 0xff00); + seg &= ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] >> 22) & 1)) - addr &= 0x; - addr += base; + down(>mm->context.sem); + if (unlikely((seg >> 3) >= child->mm->context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child->mm->context.ldt + seg; + base = ((desc[0] >> 16) | + ((desc[1] & 0xff) << 16) | + (desc[1] & 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] >> 22) & 1)) + addr &= 0x; + addr += base; + } up(>mm->context.sem); } return addr; diff --git a/arch/x86_64/kernel/ptrace.c b/arch/x86_64/kernel/ptrace.c index fa6775e..e83cc67 100644 --- a/arch/x86_64/kernel/ptrace.c +++ b/arch/x86_64/kernel/ptrace.c @@ -102,16 +102,25 @@ unsigned long convert_rip_to_linear(struct task_struct *child, struct pt_regs *r u32 *desc; unsigned long base; - down(>mm->context.sem); - desc = child->mm->context.ldt + (seg & ~7); - base = (desc[0] >> 16) | ((desc[1] & 0xff) << 16) | (desc[1] & 0xff00); + seg &= ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] >> 22) & 1)) - addr &= 0x; - addr += base; + down(>mm->context.sem); + if (unlikely((seg >> 3) >= child->mm->context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child->mm->context.ldt + seg; + base = ((desc[0] >> 16) | + ((desc[1] & 0xff) << 16) | + (desc[1] & 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] >> 22) & 1)) + addr &= 0x; + addr += base; + } up(>mm->context.sem); } + return addr; } --- End Message ---
[2.6.22.y] {06/17} - handle-bogus-%cs-selector-in-single-step-instruction-decoding - series for stable kernel #2
mainline: 29eb51101c02df517ca64ec472d7501127ad1da8 -- Thanks, Oliver ---BeginMessage--- Handle bogus %cs selector in single-step instruction decoding The code for LDT segment selectors was not robust in the face of a bogus selector set in %cs via ptrace before the single-step was done. Signed-off-by: Roland McGrath [EMAIL PROTECTED] Signed-off-by: Linus Torvalds [EMAIL PROTECTED] Acked-by: Jeff Mahoney [EMAIL PROTECTED] --- arch/i386/kernel/ptrace.c | 22 +++--- arch/x86_64/kernel/ptrace.c | 23 --- 2 files changed, 31 insertions(+), 14 deletions(-) diff --git a/arch/i386/kernel/ptrace.c b/arch/i386/kernel/ptrace.c index 1c075f5..0c8f00e 100644 --- a/arch/i386/kernel/ptrace.c +++ b/arch/i386/kernel/ptrace.c @@ -164,14 +164,22 @@ static unsigned long convert_eip_to_linear(struct task_struct *child, struct pt_ u32 *desc; unsigned long base; - down(child-mm-context.sem); - desc = child-mm-context.ldt + (seg ~7); - base = (desc[0] 16) | ((desc[1] 0xff) 16) | (desc[1] 0xff00); + seg = ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] 22) 1)) - addr = 0x; - addr += base; + down(child-mm-context.sem); + if (unlikely((seg 3) = child-mm-context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child-mm-context.ldt + seg; + base = ((desc[0] 16) | + ((desc[1] 0xff) 16) | + (desc[1] 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] 22) 1)) + addr = 0x; + addr += base; + } up(child-mm-context.sem); } return addr; diff --git a/arch/x86_64/kernel/ptrace.c b/arch/x86_64/kernel/ptrace.c index fa6775e..e83cc67 100644 --- a/arch/x86_64/kernel/ptrace.c +++ b/arch/x86_64/kernel/ptrace.c @@ -102,16 +102,25 @@ unsigned long convert_rip_to_linear(struct task_struct *child, struct pt_regs *r u32 *desc; unsigned long base; - down(child-mm-context.sem); - desc = child-mm-context.ldt + (seg ~7); - base = (desc[0] 16) | ((desc[1] 0xff) 16) | (desc[1] 0xff00); + seg = ~7UL; - /* 16-bit code segment? */ - if (!((desc[1] 22) 1)) - addr = 0x; - addr += base; + down(child-mm-context.sem); + if (unlikely((seg 3) = child-mm-context.size)) + addr = -1L; /* bogus selector, access would fault */ + else { + desc = child-mm-context.ldt + seg; + base = ((desc[0] 16) | + ((desc[1] 0xff) 16) | + (desc[1] 0xff00)); + + /* 16-bit code segment? */ + if (!((desc[1] 22) 1)) + addr = 0x; + addr += base; + } up(child-mm-context.sem); } + return addr; } ---End Message---