diff options
author | Anton Blanchard <anton@samba.org> | 2009-02-22 01:50:04 +0000 |
---|---|---|
committer | Benjamin Herrenschmidt <benh@kernel.crashing.org> | 2009-02-23 15:53:20 +1100 |
commit | 912f9ee21c836081e3c96dfe61025841ebeb95da (patch) | |
tree | 289e0c461cb651d041a2f1df359d88f285b82b4d | |
parent | d839088caec6891a5070f0b1ce61031e458533a9 (diff) |
powerpc: Randomise the brk region
Randomize the heap.
before:
tundro2:~ # sleep 1 & cat /proc/${!}/maps | grep heap
10017000-10118000 rw-p 10017000 00:00 0 [heap]
10017000-10118000 rw-p 10017000 00:00 0 [heap]
10017000-10118000 rw-p 10017000 00:00 0 [heap]
10017000-10118000 rw-p 10017000 00:00 0 [heap]
10017000-10118000 rw-p 10017000 00:00 0 [heap]
after
tundro2:~ # sleep 1 & cat /proc/${!}/maps | grep heap
19419000-1951a000 rw-p 19419000 00:00 0 [heap]
325ff000-32700000 rw-p 325ff000 00:00 0 [heap]
1a97c000-1aa7d000 rw-p 1a97c000 00:00 0 [heap]
1cc60000-1cd61000 rw-p 1cc60000 00:00 0 [heap]
1afa9000-1b0aa000 rw-p 1afa9000 00:00 0 [heap]
Signed-off-by: Anton Blanchard <anton@samba.org>
Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
-rw-r--r-- | arch/powerpc/include/asm/elf.h | 3 | ||||
-rw-r--r-- | arch/powerpc/kernel/process.c | 23 |
2 files changed, 26 insertions, 0 deletions
diff --git a/arch/powerpc/include/asm/elf.h b/arch/powerpc/include/asm/elf.h index 3f94d8880e6..968b37f7a9f 100644 --- a/arch/powerpc/include/asm/elf.h +++ b/arch/powerpc/include/asm/elf.h @@ -276,6 +276,9 @@ extern int arch_setup_additional_pages(struct linux_binprm *bprm, (0x7ff >> (PAGE_SHIFT - 12)) : \ (0x3ffff >> (PAGE_SHIFT - 12))) +extern unsigned long arch_randomize_brk(struct mm_struct *mm); +#define arch_randomize_brk arch_randomize_brk + #endif /* __KERNEL__ */ /* diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c index 69b9d2d3cb8..30b149ce759 100644 --- a/arch/powerpc/kernel/process.c +++ b/arch/powerpc/kernel/process.c @@ -1147,3 +1147,26 @@ unsigned long arch_align_stack(unsigned long sp) sp -= get_random_int() & ~PAGE_MASK; return sp & ~0xf; } + +static inline unsigned long brk_rnd(void) +{ + unsigned long rnd = 0; + + /* 8MB for 32bit, 1GB for 64bit */ + if (is_32bit_task()) + rnd = (long)(get_random_int() % (1<<(23-PAGE_SHIFT))); + else + rnd = (long)(get_random_int() % (1<<(30-PAGE_SHIFT))); + + return rnd << PAGE_SHIFT; +} + +unsigned long arch_randomize_brk(struct mm_struct *mm) +{ + unsigned long ret = PAGE_ALIGN(mm->brk + brk_rnd()); + + if (ret < mm->brk) + return mm->brk; + + return ret; +} |