8 #include <linux/errno.h>
9 #include <linux/types.h>
10 #include <linux/sched.h>
14 #include <linux/sem.h>
15 #include <linux/msg.h>
16 #include <linux/shm.h>
17 #include <linux/stat.h>
18 #include <linux/mman.h>
19 #include <linux/utsname.h>
21 #include <linux/slab.h>
23 #include <linux/ipc.h>
24 #include <linux/personality.h>
25 #include <linux/random.h>
26 #include <linux/export.h>
28 #include <asm/uaccess.h>
30 #include <asm/unistd.h>
42 #define VA_EXCLUDE_START (0x0000080000000000UL - (1UL << 32UL))
43 #define VA_EXCLUDE_END (0xfffff80000000000UL + (1UL << 32UL))
48 static inline int invalid_64bit_range(
unsigned long addr,
unsigned long len)
50 unsigned long va_exclude_start, va_exclude_end;
55 if (
unlikely(len >= va_exclude_start))
61 if (
unlikely((addr >= va_exclude_start && addr < va_exclude_end) ||
62 ((addr + len) >= va_exclude_start &&
63 (addr + len) < va_exclude_end)))
87 static inline unsigned long COLOUR_ALIGN_DOWN(
unsigned long addr,
90 unsigned long base = addr & ~(
SHMLBA-1);
93 if (base + off <= addr)
116 if (test_thread_flag(TIF_32BIT))
117 task_size = STACK_TOP32;
132 if (task_size - len >= addr &&
133 (!vma || addr + len <= vma->
vm_start))
185 const unsigned long len,
const unsigned long pgoff,
186 const unsigned long flags)
191 unsigned long addr = addr0;
195 BUG_ON(!test_thread_flag(TIF_32BIT));
222 if (task_size - len >= addr &&
223 (!vma || addr + len <= vma->vm_start))
235 if (do_color_align) {
236 unsigned long base = COLOUR_ALIGN_DOWN(addr-len, pgoff);
244 if (!vma || addr <= vma->vm_start) {
255 addr = COLOUR_ALIGN_DOWN(addr, pgoff);
264 if (
likely(!vma || addr+len <= vma->vm_start)) {
276 addr = COLOUR_ALIGN_DOWN(addr, pgoff);
277 }
while (
likely(len < vma->vm_start));
301 unsigned long align_goal, addr = -
ENOMEM;
305 get_area =
current->mm->get_unmapped_area;
309 return get_area(
NULL, orig_addr, len, pgoff, flags);
314 if (len >= (4
UL * 1024 * 1024))
315 align_goal = (4
UL * 1024 * 1024);
316 else if (len >= (512
UL * 1024))
317 align_goal = (512
UL * 1024);
318 else if (len >= (64
UL * 1024))
319 align_goal = (64
UL * 1024);
322 addr = get_area(
NULL, orig_addr, len + (align_goal -
PAGE_SIZE), pgoff, flags);
324 addr = (addr + (align_goal - 1
UL)) & ~(align_goal - 1
UL);
328 if (align_goal == (4
UL * 1024 * 1024))
329 align_goal = (512
UL * 1024);
330 else if (align_goal == (512
UL * 1024))
331 align_goal = (64
UL * 1024);
340 addr = get_area(
NULL, orig_addr, len, pgoff, flags);
347 static unsigned long mmap_rnd(
void)
349 unsigned long rnd = 0
UL;
353 if (test_thread_flag(TIF_32BIT))
363 unsigned long random_factor = mmap_rnd();
371 if (!test_thread_flag(TIF_32BIT) ||
382 if (gap < 128 * 1024 * 1024)
383 gap = 128 * 1024 * 1024;
384 if (gap > (task_size / 6 * 5))
385 gap = (task_size / 6 * 5);
418 unsigned long, third,
void __user *,
ptr,
long, fifth)
432 (
unsigned long) fifth);
476 (
ulong __user *) third))
517 if (test_thread_flag(TIF_32BIT)) {
518 if (len >= STACK_TOP32)
521 if (addr > STACK_TOP32 - len)
527 if (invalid_64bit_range(addr, len))
536 unsigned long, prot,
unsigned long,
flags,
unsigned long,
fd,
552 if (invalid_64bit_range(addr,
len))
558 extern unsigned long do_mremap(
unsigned long addr,
559 unsigned long old_len,
unsigned long new_len,
560 unsigned long flags,
unsigned long new_addr);
563 unsigned long, new_len,
unsigned long,
flags,
564 unsigned long, new_addr)
566 if (test_thread_flag(TIF_32BIT))
580 printk (
"Unimplemented SPARC system call %ld\n",regs->
u_regs[1]);
581 #ifdef DEBUG_UNIMP_SYSCALL
594 if (test_thread_flag(TIF_32BIT)) {
595 regs->tpc &= 0xffffffff;
596 regs->tnpc &= 0xffffffff;
598 #ifdef DEBUG_SPARC_BREAKPOINT
599 printk (
"TRAP: Entering kernel PC=%lx, nPC=%lx\n", regs->tpc, regs->tnpc);
604 info.si_addr = (
void __user *)regs->tpc;
607 #ifdef DEBUG_SPARC_BREAKPOINT
608 printk (
"TRAP: Returning to space: PC=%lx nPC=%lx\n", regs->tpc, regs->tnpc);
623 nlen =
strlen(utsname()->domainname) + 1;
662 kzalloc((UT_TRAP_INSTRUCTION_31+1)*
sizeof(
long),
GFP_KERNEL);
672 kmalloc((UT_TRAP_INSTRUCTION_31+1)*
sizeof(
long),
681 UT_TRAP_INSTRUCTION_31*
sizeof(
long));
702 regs->tstate = (regs->tstate & ~
TSTATE_MM) | (model << 14);
707 struct sigaction __user *, oact,
void __user *, restorer,
738 const char *
const argv[],
739 const char *
const envp[])
743 register long __o0
__asm__ (
"o0") = (
long)(filename);
746 asm volatile (
"t 0x6d\n\t"
747 "sub %%g0, %%o0, %0\n\t"
748 "movcc %%xcc, %%o0, %0\n\t"
749 :
"=r" (__res),
"=&r" (__o0)
750 :
"1" (__o0),
"r" (__o1),
"r" (__o2),
"r" (__g1)