diff options
Diffstat (limited to 'arch/i386/mm')
-rw-r--r-- | arch/i386/mm/fault.c | 21 | ||||
-rw-r--r-- | arch/i386/mm/init.c | 3 | ||||
-rw-r--r-- | arch/i386/mm/pageattr.c | 8 |
3 files changed, 18 insertions, 14 deletions
diff --git a/arch/i386/mm/fault.c b/arch/i386/mm/fault.c index 7f0fcf219a26..bd6fe96cc16d 100644 --- a/arch/i386/mm/fault.c +++ b/arch/i386/mm/fault.c | |||
@@ -77,12 +77,15 @@ static inline unsigned long get_segment_eip(struct pt_regs *regs, | |||
77 | unsigned seg = regs->xcs & 0xffff; | 77 | unsigned seg = regs->xcs & 0xffff; |
78 | u32 seg_ar, seg_limit, base, *desc; | 78 | u32 seg_ar, seg_limit, base, *desc; |
79 | 79 | ||
80 | /* Unlikely, but must come before segment checks. */ | ||
81 | if (unlikely(regs->eflags & VM_MASK)) { | ||
82 | base = seg << 4; | ||
83 | *eip_limit = base + 0xffff; | ||
84 | return base + (eip & 0xffff); | ||
85 | } | ||
86 | |||
80 | /* The standard kernel/user address space limit. */ | 87 | /* The standard kernel/user address space limit. */ |
81 | *eip_limit = (seg & 3) ? USER_DS.seg : KERNEL_DS.seg; | 88 | *eip_limit = (seg & 3) ? USER_DS.seg : KERNEL_DS.seg; |
82 | |||
83 | /* Unlikely, but must come before segment checks. */ | ||
84 | if (unlikely((regs->eflags & VM_MASK) != 0)) | ||
85 | return eip + (seg << 4); | ||
86 | 89 | ||
87 | /* By far the most common cases. */ | 90 | /* By far the most common cases. */ |
88 | if (likely(seg == __USER_CS || seg == __KERNEL_CS)) | 91 | if (likely(seg == __USER_CS || seg == __KERNEL_CS)) |
@@ -380,12 +383,12 @@ fastcall void __kprobes do_page_fault(struct pt_regs *regs, | |||
380 | goto bad_area; | 383 | goto bad_area; |
381 | if (error_code & 4) { | 384 | if (error_code & 4) { |
382 | /* | 385 | /* |
383 | * accessing the stack below %esp is always a bug. | 386 | * Accessing the stack below %esp is always a bug. |
384 | * The "+ 32" is there due to some instructions (like | 387 | * The large cushion allows instructions like enter |
385 | * pusha) doing post-decrement on the stack and that | 388 | * and pusha to work. ("enter $65535,$31" pushes |
386 | * doesn't show up until later.. | 389 | * 32 pointers and then decrements %esp by 65535.) |
387 | */ | 390 | */ |
388 | if (address + 32 < regs->esp) | 391 | if (address + 65536 + 32 * sizeof(unsigned long) < regs->esp) |
389 | goto bad_area; | 392 | goto bad_area; |
390 | } | 393 | } |
391 | if (expand_stack(vma, address)) | 394 | if (expand_stack(vma, address)) |
diff --git a/arch/i386/mm/init.c b/arch/i386/mm/init.c index 3df1371d4520..bf19513f0cea 100644 --- a/arch/i386/mm/init.c +++ b/arch/i386/mm/init.c | |||
@@ -29,6 +29,7 @@ | |||
29 | #include <linux/efi.h> | 29 | #include <linux/efi.h> |
30 | #include <linux/memory_hotplug.h> | 30 | #include <linux/memory_hotplug.h> |
31 | #include <linux/initrd.h> | 31 | #include <linux/initrd.h> |
32 | #include <linux/cpumask.h> | ||
32 | 33 | ||
33 | #include <asm/processor.h> | 34 | #include <asm/processor.h> |
34 | #include <asm/system.h> | 35 | #include <asm/system.h> |
@@ -384,7 +385,7 @@ static void __init pagetable_init (void) | |||
384 | #endif | 385 | #endif |
385 | } | 386 | } |
386 | 387 | ||
387 | #ifdef CONFIG_SOFTWARE_SUSPEND | 388 | #if defined(CONFIG_SOFTWARE_SUSPEND) || defined(CONFIG_ACPI_SLEEP) |
388 | /* | 389 | /* |
389 | * Swap suspend & friends need this for resume because things like the intel-agp | 390 | * Swap suspend & friends need this for resume because things like the intel-agp |
390 | * driver might have split up a kernel 4MB mapping. | 391 | * driver might have split up a kernel 4MB mapping. |
diff --git a/arch/i386/mm/pageattr.c b/arch/i386/mm/pageattr.c index 92c3d9f0e731..0887b34bc59b 100644 --- a/arch/i386/mm/pageattr.c +++ b/arch/i386/mm/pageattr.c | |||
@@ -209,19 +209,19 @@ int change_page_attr(struct page *page, int numpages, pgprot_t prot) | |||
209 | } | 209 | } |
210 | 210 | ||
211 | void global_flush_tlb(void) | 211 | void global_flush_tlb(void) |
212 | { | 212 | { |
213 | LIST_HEAD(l); | 213 | struct list_head l; |
214 | struct page *pg, *next; | 214 | struct page *pg, *next; |
215 | 215 | ||
216 | BUG_ON(irqs_disabled()); | 216 | BUG_ON(irqs_disabled()); |
217 | 217 | ||
218 | spin_lock_irq(&cpa_lock); | 218 | spin_lock_irq(&cpa_lock); |
219 | list_splice_init(&df_list, &l); | 219 | list_replace_init(&df_list, &l); |
220 | spin_unlock_irq(&cpa_lock); | 220 | spin_unlock_irq(&cpa_lock); |
221 | flush_map(); | 221 | flush_map(); |
222 | list_for_each_entry_safe(pg, next, &l, lru) | 222 | list_for_each_entry_safe(pg, next, &l, lru) |
223 | __free_page(pg); | 223 | __free_page(pg); |
224 | } | 224 | } |
225 | 225 | ||
226 | #ifdef CONFIG_DEBUG_PAGEALLOC | 226 | #ifdef CONFIG_DEBUG_PAGEALLOC |
227 | void kernel_map_pages(struct page *page, int numpages, int enable) | 227 | void kernel_map_pages(struct page *page, int numpages, int enable) |