diff options
Diffstat (limited to 'arch/um/kernel/skas')
-rw-r--r-- | arch/um/kernel/skas/Makefile | 4 | ||||
-rw-r--r-- | arch/um/kernel/skas/clone.c | 6 | ||||
-rw-r--r-- | arch/um/kernel/skas/exec.c | 40 | ||||
-rw-r--r-- | arch/um/kernel/skas/mem.c | 22 | ||||
-rw-r--r-- | arch/um/kernel/skas/mmu.c | 81 | ||||
-rw-r--r-- | arch/um/kernel/skas/process.c | 187 | ||||
-rw-r--r-- | arch/um/kernel/skas/syscall.c | 21 | ||||
-rw-r--r-- | arch/um/kernel/skas/tlb.c | 164 | ||||
-rw-r--r-- | arch/um/kernel/skas/uaccess.c | 146 |
9 files changed, 135 insertions, 536 deletions
diff --git a/arch/um/kernel/skas/Makefile b/arch/um/kernel/skas/Makefile index 3e3fa7e7e3c..0b76d8869c9 100644 --- a/arch/um/kernel/skas/Makefile +++ b/arch/um/kernel/skas/Makefile @@ -1,9 +1,9 @@ # -# Copyright (C) 2002 - 2004 Jeff Dike (jdike@addtoit.com) +# Copyright (C) 2002 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com) # Licensed under the GPL # -obj-y := clone.o exec.o mem.o mmu.o process.o syscall.o tlb.o uaccess.o +obj-y := clone.o mmu.o process.o syscall.o uaccess.o # clone.o is in the stub, so it can't be built with profiling # GCC hardened also auto-enables -fpic, but we need %ebx so it can't work -> diff --git a/arch/um/kernel/skas/clone.c b/arch/um/kernel/skas/clone.c index 47b812b3bca..d119f4f7d89 100644 --- a/arch/um/kernel/skas/clone.c +++ b/arch/um/kernel/skas/clone.c @@ -4,6 +4,7 @@ #include <sys/time.h> #include <asm/unistd.h> #include <asm/page.h> +#include "as-layout.h" #include "ptrace_user.h" #include "skas.h" #include "stub-data.h" @@ -21,12 +22,11 @@ void __attribute__ ((__section__ (".__syscall_stub"))) stub_clone_handler(void) { - struct stub_data *data = (struct stub_data *) UML_CONFIG_STUB_DATA; + struct stub_data *data = (struct stub_data *) STUB_DATA; long err; err = stub_syscall2(__NR_clone, CLONE_PARENT | CLONE_FILES | SIGCHLD, - UML_CONFIG_STUB_DATA + UM_KERN_PAGE_SIZE / 2 - - sizeof(void *)); + STUB_DATA + UM_KERN_PAGE_SIZE / 2 - sizeof(void *)); if(err != 0) goto out; diff --git a/arch/um/kernel/skas/exec.c b/arch/um/kernel/skas/exec.c deleted file mode 100644 index 580eb646894..00000000000 --- a/arch/um/kernel/skas/exec.c +++ /dev/null @@ -1,40 +0,0 @@ -/* - * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) - * Licensed under the GPL - */ - -#include "linux/kernel.h" -#include "asm/current.h" -#include "asm/page.h" -#include "asm/signal.h" -#include "asm/ptrace.h" -#include "asm/uaccess.h" -#include "asm/mmu_context.h" -#include "tlb.h" -#include "skas.h" -#include "um_mmu.h" -#include "os.h" - -void flush_thread_skas(void) -{ - void *data = NULL; - unsigned long end = proc_mm ? task_size : CONFIG_STUB_START; - int ret; - - ret = unmap(¤t->mm->context.skas.id, 0, end, 1, &data); - if(ret){ - printk("flush_thread_skas - clearing address space failed, " - "err = %d\n", ret); - force_sig(SIGKILL, current); - } - - switch_mm_skas(¤t->mm->context.skas.id); -} - -void start_thread_skas(struct pt_regs *regs, unsigned long eip, - unsigned long esp) -{ - set_fs(USER_DS); - PT_REGS_IP(regs) = eip; - PT_REGS_SP(regs) = esp; -} diff --git a/arch/um/kernel/skas/mem.c b/arch/um/kernel/skas/mem.c deleted file mode 100644 index 7c18dfcd7d8..00000000000 --- a/arch/um/kernel/skas/mem.c +++ /dev/null @@ -1,22 +0,0 @@ -/* - * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) - * Licensed under the GPL - */ - -#include "linux/mm.h" -#include "asm/pgtable.h" -#include "mem_user.h" -#include "skas.h" - -unsigned long set_task_sizes_skas(unsigned long *task_size_out) -{ - /* Round up to the nearest 4M */ - unsigned long host_task_size = ROUND_4M((unsigned long) - &host_task_size); - - if (!skas_needs_stub) - *task_size_out = host_task_size; - else *task_size_out = CONFIG_STUB_START & PGDIR_MASK; - - return host_task_size; -} diff --git a/arch/um/kernel/skas/mmu.c b/arch/um/kernel/skas/mmu.c index 2c6d090a2e8..f859ec306cd 100644 --- a/arch/um/kernel/skas/mmu.c +++ b/arch/um/kernel/skas/mmu.c @@ -1,20 +1,13 @@ -/* - * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) +/* + * Copyright (C) 2002 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com) * Licensed under the GPL */ -#include "linux/sched.h" -#include "linux/list.h" -#include "linux/spinlock.h" -#include "linux/slab.h" -#include "linux/errno.h" #include "linux/mm.h" -#include "asm/current.h" -#include "asm/segment.h" -#include "asm/mmu.h" +#include "linux/sched.h" #include "asm/pgalloc.h" #include "asm/pgtable.h" -#include "asm/ldt.h" +#include "as-layout.h" #include "os.h" #include "skas.h" @@ -41,10 +34,11 @@ static int init_stub_pte(struct mm_struct *mm, unsigned long proc, if (!pte) goto out_pte; - /* There's an interaction between the skas0 stub pages, stack + /* + * There's an interaction between the skas0 stub pages, stack * randomization, and the BUG at the end of exit_mmap. exit_mmap - * checks that the number of page tables freed is the same as had - * been allocated. If the stack is on the last page table page, + * checks that the number of page tables freed is the same as had + * been allocated. If the stack is on the last page table page, * then the stack pte page will be freed, and if not, it won't. To * avoid having to know where the stack is, or if the process mapped * something at the top of its address space for some other reason, @@ -54,76 +48,77 @@ static int init_stub_pte(struct mm_struct *mm, unsigned long proc, * destroy_context_skas. */ - mm->context.skas.last_page_table = pmd_page_vaddr(*pmd); + mm->context.last_page_table = pmd_page_vaddr(*pmd); #ifdef CONFIG_3_LEVEL_PGTABLES - mm->context.skas.last_pmd = (unsigned long) __va(pud_val(*pud)); + mm->context.last_pmd = (unsigned long) __va(pud_val(*pud)); #endif *pte = mk_pte(virt_to_page(kernel), __pgprot(_PAGE_PRESENT)); *pte = pte_mkread(*pte); - return(0); + return 0; out_pmd: pud_free(pud); out_pte: pmd_free(pmd); out: - return(-ENOMEM); + return -ENOMEM; } -int init_new_context_skas(struct task_struct *task, struct mm_struct *mm) +int init_new_context(struct task_struct *task, struct mm_struct *mm) { - struct mmu_context_skas *from_mm = NULL; - struct mmu_context_skas *to_mm = &mm->context.skas; + struct mm_context *from_mm = NULL; + struct mm_context *to_mm = &mm->context; unsigned long stack = 0; int ret = -ENOMEM; - if(skas_needs_stub){ + if (skas_needs_stub) { stack = get_zeroed_page(GFP_KERNEL); - if(stack == 0) + if (stack == 0) goto out; - /* This zeros the entry that pgd_alloc didn't, needed since + /* + * This zeros the entry that pgd_alloc didn't, needed since * we are about to reinitialize it, and want mm.nr_ptes to * be accurate. */ mm->pgd[USER_PTRS_PER_PGD] = __pgd(0); - ret = init_stub_pte(mm, CONFIG_STUB_CODE, + ret = init_stub_pte(mm, STUB_CODE, (unsigned long) &__syscall_stub_start); - if(ret) + if (ret) goto out_free; - ret = init_stub_pte(mm, CONFIG_STUB_DATA, stack); - if(ret) + ret = init_stub_pte(mm, STUB_DATA, stack); + if (ret) goto out_free; mm->nr_ptes--; } to_mm->id.stack = stack; - if(current->mm != NULL && current->mm != &init_mm) - from_mm = ¤t->mm->context.skas; + if (current->mm != NULL && current->mm != &init_mm) + from_mm = ¤t->mm->context; - if(proc_mm){ + if (proc_mm) { ret = new_mm(stack); - if(ret < 0){ - printk("init_new_context_skas - new_mm failed, " - "errno = %d\n", ret); + if (ret < 0) { + printk(KERN_ERR "init_new_context_skas - " + "new_mm failed, errno = %d\n", ret); goto out_free; } to_mm->id.u.mm_fd = ret; } else { - if(from_mm) + if (from_mm) to_mm->id.u.pid = copy_context_skas0(stack, from_mm->id.u.pid); else to_mm->id.u.pid = start_userspace(stack); } ret = init_new_ldt(to_mm, from_mm); - if(ret < 0){ - printk("init_new_context_skas - init_ldt" + if (ret < 0) { + printk(KERN_ERR "init_new_context_skas - init_ldt" " failed, errno = %d\n", ret); goto out_free; } @@ -131,22 +126,22 @@ int init_new_context_skas(struct task_struct *task, struct mm_struct *mm) return 0; out_free: - if(to_mm->id.stack != 0) + if (to_mm->id.stack != 0) free_page(to_mm->id.stack); out: return ret; } -void destroy_context_skas(struct mm_struct *mm) +void destroy_context(struct mm_struct *mm) { - struct mmu_context_skas *mmu = &mm->context.skas; + struct mm_context *mmu = &mm->context; - if(proc_mm) + if (proc_mm) os_close_file(mmu->id.u.mm_fd); else os_kill_ptraced_process(mmu->id.u.pid, 1); - if(!proc_mm || !ptrace_faultinfo){ + if (!proc_mm || !ptrace_faultinfo) { free_page(mmu->id.stack); pte_lock_deinit(virt_to_page(mmu->last_page_table)); pte_free_kernel((pte_t *) mmu->last_page_table); @@ -155,4 +150,6 @@ void destroy_context_skas(struct mm_struct *mm) pmd_free((pmd_t *) mmu->last_pmd); #endif } + + free_ldt(mmu); } diff --git a/arch/um/kernel/skas/process.c b/arch/um/kernel/skas/process.c index 48051a98525..fce389c2342 100644 --- a/arch/um/kernel/skas/process.c +++ b/arch/um/kernel/skas/process.c @@ -1,146 +1,26 @@ /* - * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) + * Copyright (C) 2002 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com) * Licensed under the GPL */ -#include "linux/sched.h" -#include "linux/slab.h" -#include "linux/ptrace.h" -#include "linux/proc_fs.h" -#include "linux/file.h" -#include "linux/errno.h" #include "linux/init.h" -#include "asm/uaccess.h" -#include "asm/atomic.h" -#include "kern_util.h" +#include "linux/sched.h" #include "as-layout.h" -#include "skas.h" #include "os.h" -#include "tlb.h" -#include "kern.h" -#include "mode.h" -#include "registers.h" - -void switch_to_skas(void *prev, void *next) -{ - struct task_struct *from, *to; - - from = prev; - to = next; - - /* XXX need to check runqueues[cpu].idle */ - if(current->pid == 0) - switch_timers(0); - - switch_threads(&from->thread.mode.skas.switch_buf, - &to->thread.mode.skas.switch_buf); - - arch_switch_to_skas(current->thread.prev_sched, current); - - if(current->pid == 0) - switch_timers(1); -} - -extern void schedule_tail(struct task_struct *prev); - -/* This is called magically, by its address being stuffed in a jmp_buf - * and being longjmp-d to. - */ -void new_thread_handler(void) -{ - int (*fn)(void *), n; - void *arg; - - if(current->thread.prev_sched != NULL) - schedule_tail(current->thread.prev_sched); - current->thread.prev_sched = NULL; - - fn = current->thread.request.u.thread.proc; - arg = current->thread.request.u.thread.arg; - - /* The return value is 1 if the kernel thread execs a process, - * 0 if it just exits - */ - n = run_kernel_thread(fn, arg, ¤t->thread.exec_buf); - if(n == 1){ - /* Handle any immediate reschedules or signals */ - interrupt_end(); - userspace(¤t->thread.regs.regs); - } - else do_exit(0); -} - -void release_thread_skas(struct task_struct *task) -{ -} - -/* Called magically, see new_thread_handler above */ -void fork_handler(void) -{ - force_flush_all(); - if(current->thread.prev_sched == NULL) - panic("blech"); - - schedule_tail(current->thread.prev_sched); - - /* XXX: if interrupt_end() calls schedule, this call to - * arch_switch_to_skas isn't needed. We could want to apply this to - * improve performance. -bb */ - arch_switch_to_skas(current->thread.prev_sched, current); - - current->thread.prev_sched = NULL; - -/* Handle any immediate reschedules or signals */ - interrupt_end(); - - userspace(¤t->thread.regs.regs); -} - -int copy_thread_skas(int nr, unsigned long clone_flags, unsigned long sp, - unsigned long stack_top, struct task_struct * p, - struct pt_regs *regs) -{ - void (*handler)(void); - - if(current->thread.forking){ - memcpy(&p->thread.regs.regs.skas, ®s->regs.skas, - sizeof(p->thread.regs.regs.skas)); - REGS_SET_SYSCALL_RETURN(p->thread.regs.regs.skas.regs, 0); - if(sp != 0) REGS_SP(p->thread.regs.regs.skas.regs) = sp; - - handler = fork_handler; - - arch_copy_thread(¤t->thread.arch, &p->thread.arch); - } - else { - init_thread_registers(&p->thread.regs.regs); - p->thread.request.u.thread = current->thread.request.u.thread; - handler = new_thread_handler; - } - - new_thread(task_stack_page(p), &p->thread.mode.skas.switch_buf, - handler); - return(0); -} +#include "skas.h" int new_mm(unsigned long stack) { int fd; fd = os_open_file("/proc/mm", of_cloexec(of_write(OPENFLAGS())), 0); - if(fd < 0) - return(fd); + if (fd < 0) + return fd; - if(skas_needs_stub) - map_stub_pages(fd, CONFIG_STUB_CODE, CONFIG_STUB_DATA, stack); + if (skas_needs_stub) + map_stub_pages(fd, STUB_CODE, STUB_DATA, stack); - return(fd); -} - -void init_idle_skas(void) -{ - cpu_tasks[current_thread->cpu].pid = os_getpid(); - default_idle(); + return fd; } extern void start_kernel(void); @@ -158,67 +38,32 @@ static int __init start_kernel_proc(void *unused) cpu_online_map = cpumask_of_cpu(0); #endif start_kernel(); - return(0); + return 0; } extern int userspace_pid[]; extern char cpu0_irqstack[]; -int __init start_uml_skas(void) +int __init start_uml(void) { stack_protections((unsigned long) &cpu0_irqstack); set_sigstack(cpu0_irqstack, THREAD_SIZE); - if(proc_mm) + if (proc_mm) userspace_pid[0] = start_userspace(0); init_new_thread_signals(); init_task.thread.request.u.thread.proc = start_kernel_proc; init_task.thread.request.u.thread.arg = NULL; - return(start_idle_thread(task_stack_page(&init_task), - &init_task.thread.mode.skas.switch_buf)); -} - -int external_pid_skas(struct task_struct *task) -{ - /* FIXME: Need to look up userspace_pid by cpu */ - return(userspace_pid[0]); -} - -int thread_pid_skas(struct task_struct *task) -{ - /* FIXME: Need to look up userspace_pid by cpu */ - return(userspace_pid[0]); -} - -void kill_off_processes_skas(void) -{ - if(proc_mm) - /* - * FIXME: need to loop over userspace_pids in - * kill_off_processes_skas - */ - os_kill_ptraced_process(userspace_pid[0], 1); - else { - struct task_struct *p; - int pid, me; - - me = os_getpid(); - for_each_process(p){ - if(p->mm == NULL) - continue; - - pid = p->mm->context.skas.id.u.pid; - os_kill_ptraced_process(pid, 1); - } - } + return start_idle_thread(task_stack_page(&init_task), + &init_task.thread.switch_buf); } unsigned long current_stub_stack(void) { - if(current->mm == NULL) - return(0); + if (current->mm == NULL) + return 0; - return(current->mm->context.skas.id.stack); + return current->mm->context.id.stack; } diff --git a/arch/um/kernel/skas/syscall.c b/arch/um/kernel/skas/syscall.c index 0ae4eea21be..50b476f2b38 100644 --- a/arch/um/kernel/skas/syscall.c +++ b/arch/um/kernel/skas/syscall.c @@ -1,19 +1,15 @@ /* - * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) + * Copyright (C) 2002 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com) * Licensed under the GPL */ -#include "linux/sys.h" +#include "linux/kernel.h" #include "linux/ptrace.h" -#include "asm/errno.h" -#include "asm/unistd.h" -#include "asm/ptrace.h" -#include "asm/current.h" -#include "sysdep/syscalls.h" #include "kern_util.h" -#include "syscall.h" +#include "sysdep/ptrace.h" +#include "sysdep/syscalls.h" -void handle_syscall(union uml_pt_regs *r) +void handle_syscall(struct uml_pt_regs *r) { struct pt_regs *regs = container_of(r, struct pt_regs, regs); long result; @@ -24,7 +20,8 @@ void handle_syscall(union uml_pt_regs *r) current->thread.nsyscalls++; nsyscalls++; - /* This should go in the declaration of syscall, but when I do that, + /* + * This should go in the declaration of syscall, but when I do that, * strace -f -c bash -c 'ls ; ls' breaks, sometimes not tracing * children at all, sometimes hanging when bash doesn't see the first * ls exit. @@ -33,11 +30,11 @@ void handle_syscall(union uml_pt_regs *r) * in case it's a compiler bug. */ syscall = UPT_SYSCALL_NR(r); - if((syscall >= NR_syscalls) || (syscall < 0)) + if ((syscall >= NR_syscalls) || (syscall < 0)) result = -ENOSYS; else result = EXECUTE_SYSCALL(syscall, regs); - REGS_SET_SYSCALL_RETURN(r->skas.regs, result); + REGS_SET_SYSCALL_RETURN(r->gp, result); syscall_trace(r, 1); } diff --git a/arch/um/kernel/skas/tlb.c b/arch/um/kernel/skas/tlb.c deleted file mode 100644 index c0f0693743b..00000000000 --- a/arch/um/kernel/skas/tlb.c +++ /dev/null @@ -1,164 +0,0 @@ -/* - * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) - * Copyright 2003 PathScale, Inc. - * Licensed under the GPL - */ - -#include "linux/stddef.h" -#include "linux/sched.h" -#include "linux/mm.h" -#include "asm/page.h" -#include "asm/pgtable.h" -#include "asm/mmu.h" -#include "mem_user.h" -#include "mem.h" -#include "skas.h" -#include "os.h" -#include "tlb.h" - -static int do_ops(union mm_context *mmu, struct host_vm_op *ops, int last, - int finished, void **flush) -{ - struct host_vm_op *op; - int i, ret = 0; - - for(i = 0; i <= last && !ret; i++){ - op = &ops[i]; - switch(op->type){ - case MMAP: - ret = map(&mmu->skas.id, op->u.mmap.addr, - op->u.mmap.len, op->u.mmap.prot, - op->u.mmap.fd, op->u.mmap.offset, finished, - flush); - break; - case MUNMAP: - ret = unmap(&mmu->skas.id, op->u.munmap.addr, - op->u.munmap.len, finished, flush); - break; - case MPROTECT: - ret = protect(&mmu->skas.id, op->u.mprotect.addr, - op->u.mprotect.len, op->u.mprotect.prot, - finished, flush); - break; - default: - printk("Unknown op type %d in do_ops\n", op->type); - break; - } - } - - return ret; -} - -extern int proc_mm; - -static void fix_range(struct mm_struct *mm, unsigned long start_addr, - unsigned long end_addr, int force) -{ - if(!proc_mm && (end_addr > CONFIG_STUB_START)) - end_addr = CONFIG_STUB_START; - - fix_range_common(mm, start_addr, end_addr, force, do_ops); -} - -void __flush_tlb_one_skas(unsigned long addr) -{ - flush_tlb_kernel_range_common(addr, addr + PAGE_SIZE); -} - -void flush_tlb_range_skas(struct vm_area_struct *vma, unsigned long start, - unsigned long end) -{ - if(vma->vm_mm == NULL) - flush_tlb_kernel_range_common(start, end); - else fix_range(vma->vm_mm, start, end, 0); -} - -void flush_tlb_mm_skas(struct mm_struct *mm) -{ - unsigned long end; - - /* Don't bother flushing if this address space is about to be - * destroyed. - */ - if(atomic_read(&mm->mm_users) == 0) - return; - - end = proc_mm ? task_size : CONFIG_STUB_START; - fix_range(mm, 0, end, 0); -} - -void force_flush_all_skas(void) -{ - struct mm_struct *mm = current->mm; - struct vm_area_struct *vma = mm->mmap; - - while(vma != NULL) { - fix_range(mm, vma->vm_start, vma->vm_end, 1); - vma = vma->vm_next; - } -} - -void flush_tlb_page_skas(struct vm_area_struct *vma, unsigned long address) -{ - pgd_t *pgd; - pud_t *pud; - pmd_t *pmd; - pte_t *pte; - struct mm_struct *mm = vma->vm_mm; - void *flush = NULL; - int r, w, x, prot, err = 0; - struct mm_id *mm_id; - - pgd = pgd_offset(mm, address); - if(!pgd_present(*pgd)) - goto kill; - - pud = pud_offset(pgd, address); - if(!pud_present(*pud)) - goto kill; - - pmd = pmd_offset(pud, address); - if(!pmd_present(*pmd)) - goto kill; - - pte = pte_offset_kernel(pmd, address); - - r = pte_read(*pte); - w = pte_write(*pte); - x = pte_exec(*pte); - if (!pte_young(*pte)) { - r = 0; - w = 0; - } else if (!pte_dirty(*pte)) { - w = 0; - } - - mm_id = &mm->context.skas.id; - prot = ((r ? UM_PROT_READ : 0) | (w ? UM_PROT_WRITE : 0) | - (x ? UM_PROT_EXEC : 0)); - if(pte_newpage(*pte)){ - if(pte_present(*pte)){ - unsigned long long offset; - int fd; - - fd = phys_mapping(pte_val(*pte) & PAGE_MASK, &offset); - err = map(mm_id, address, PAGE_SIZE, prot, fd, offset, - 1, &flush); - } - else err = unmap(mm_id, address, PAGE_SIZE, 1, &flush); - } - else if(pte_newprot(*pte)) - err = protect(mm_id, address, PAGE_SIZE, prot, 1, &flush); - - if(err) - goto kill; - - *pte = pte_mkuptodate(*pte); - - return; - -kill: - printk("Failed to flush page for address 0x%lx\n", address); - force_sig(SIGKILL, current); -} - diff --git a/arch/um/kernel/skas/uaccess.c b/arch/um/kernel/skas/uaccess.c index 8912cec0fe4..1d8b119f2d0 100644 --- a/arch/um/kernel/skas/uaccess.c +++ b/arch/um/kernel/skas/uaccess.c @@ -1,18 +1,14 @@ /* - * Copyright (C) 2002 - 2003 Jeff Dike (jdike@addtoit.com) + * Copyright (C) 2002 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com) * Licensed under the GPL */ -#include "linux/compiler.h" -#include "linux/stddef.h" -#include "linux/kernel.h" -#include "linux/string.h" -#include "linux/fs.h" -#include "linux/hardirq.h" +#include "linux/err.h" #include "linux/highmem.h" +#include "linux/mm.h" +#include "asm/current.h" #include "asm/page.h" #include "asm/pgtable.h" -#include "asm/uaccess.h" #include "kern_util.h" #include "os.h" @@ -27,16 +23,16 @@ static unsigned long maybe_map(unsigned long virt, int is_write) void *phys = um_virt_to_phys(current, virt, &pte); int dummy_code; - if(IS_ERR(phys) || (is_write && !pte_write(pte))){ + if (IS_ERR(phys) || (is_write && !pte_write(pte))) { err = handle_page_fault(virt, 0, is_write, 1, &dummy_code); - if(err) - return(-1UL); + if (err) + return -1UL; phys = um_virt_to_phys(current, virt, NULL); } - if(IS_ERR(phys)) - phys = (void *) -1; + if (IS_ERR(phys)) + phys = (void *) -1; - return((unsigned long) phys); + return (unsigned long) phys; } static int do_op_one_page(unsigned long addr, int len, int is_write, @@ -46,17 +42,18 @@ static int do_op_one_page(unsigned long addr, int len, int is_write, int n; addr = maybe_map(addr, is_write); - if(addr == -1UL) - return(-1); + if (addr == -1UL) + return -1; page = phys_to_page(addr); - addr = (unsigned long) kmap_atomic(page, KM_UML_USERCOPY) + (addr & ~PAGE_MASK); + addr = (unsigned long) kmap_atomic(page, KM_UML_USERCOPY) + + (addr & ~PAGE_MASK); n = (*op)(addr, len, arg); kunmap_atomic(page, KM_UML_USERCOPY); - return(n); + return n; } static void do_buffer_op(void *jmpbuf, void *arg_ptr) @@ -81,21 +78,21 @@ static void do_buffer_op(void *jmpbuf, void *arg_ptr) current->thread.fault_catcher = jmpbuf; n = do_op_one_page(addr, size, is_write, op, arg); - if(n != 0){ + if (n != 0) { *res = (n < 0 ? remain : 0); goto out; } addr += size; remain -= size; - if(remain == 0){ + if (remain == 0) { *res = 0; goto out; } - while(addr < ((addr + remain) & PAGE_MASK)){ + while(addr < ((addr + remain) & PAGE_MASK)) { n = do_op_one_page(addr, PAGE_SIZE, is_write, op, arg); - if(n != 0){ + if (n != 0) { *res = (n < 0 ? remain : 0); goto out; } @@ -103,13 +100,13 @@ static void do_buffer_op(void *jmpbuf, void *arg_ptr) addr += PAGE_SIZE; remain -= PAGE_SIZE; } - if(remain == 0){ + if (remain == 0) { *res = 0; goto out; } n = do_op_one_page(addr, remain, is_write, op, arg); - if(n != 0) + if (n != 0) *res = (n < 0 ? remain : 0); else *res = 0; out: @@ -124,10 +121,10 @@ static int buffer_op(unsigned long addr, int len, int is_write, faulted = setjmp_wrapper(do_buffer_op, addr, len, is_write, op, arg, &res); - if(!faulted) - return(res); + if (!faulted) + return res; - return(addr + len - (unsigned long) current->thread.fault_addr); + return addr + len - (unsigned long) current->thread.fault_addr; } static int copy_chunk_from_user(unsigned long from, int len, void *arg) @@ -136,19 +133,19 @@ static int copy_chunk_from_user(unsigned long from, int len, void *arg) memcpy((void *) to, (void *) from, len); *to_ptr += len; - return(0); + return 0; } -int copy_from_user_skas(void *to, const void __user *from, int n) +int copy_from_user(void *to, const void __user *from, int n) { - if(segment_eq(get_fs(), KERNEL_DS)){ + if (segment_eq(get_fs(), KERNEL_DS)) { memcpy(to, (__force void*)from, n); - return(0); + return 0; } - return(access_ok(VERIFY_READ, from, n) ? + return access_ok(VERIFY_READ, from, n) ? buffer_op((unsigned long) from, n, 0, copy_chunk_from_user, &to): - n); + n; } static int copy_chunk_to_user(unsigned long to, int len, void *arg) @@ -157,19 +154,19 @@ static int copy_chunk_to_user(unsigned long to, int len, void *arg) memcpy((void *) to, (void *) from, len); *from_ptr += len; - return(0); + return 0; } -int copy_to_user_skas(void __user *to, const void *from, int n) +int copy_to_user(void __user *to, const void *from, int n) { - if(segment_eq(get_fs(), KERNEL_DS)){ - memcpy((__force void*)to, from, n); - return(0); + if (segment_eq(get_fs(), KERNEL_DS)) { + memcpy((__force void *) to, from, n); + return 0; } - return(access_ok(VERIFY_WRITE, to, n) ? + return access_ok(VERIFY_WRITE, to, n) ? buffer_op((unsigned long) to, n, 1, copy_chunk_to_user, &from) : - n); + n; } static int strncpy_chunk_from_user(unsigned long from, int len, void *arg) @@ -181,51 +178,51 @@ static int strncpy_chunk_from_user(unsigned long from, int len, void *arg) n = strnlen(to, len); *to_ptr += n; - if(n < len) - return(1); - return(0); + if (n < len) + return 1; + return 0; } -int strncpy_from_user_skas(char *dst, const char __user *src, int count) +int strncpy_from_user(char *dst, const char __user *src, int count) { int n; char *ptr = dst; - if(segment_eq(get_fs(), KERNEL_DS)){ - strncpy(dst, (__force void*)src, count); - return(strnlen(dst, count)); + if (segment_eq(get_fs(), KERNEL_DS)) { + strncpy(dst, (__force void *) src, count); + return strnlen(dst, count); } - if(!access_ok(VERIFY_READ, src, 1)) - return(-EFAULT); + if (!access_ok(VERIFY_READ, src, 1)) + return -EFAULT; n = buffer_op((unsigned long) src, count, 0, strncpy_chunk_from_user, &ptr); - if(n != 0) - return(-EFAULT); - return(strnlen(dst, count)); + if (n != 0) + return -EFAULT; + return strnlen(dst, count); } static int clear_chunk(unsigned long addr, int len, void *unused) { memset((void *) addr, 0, len); - return(0); + return 0; } -int __clear_user_skas(void __user *mem, int len) +int __clear_user(void __user *mem, int len) { - return(buffer_op((unsigned long) mem, len, 1, clear_chunk, NULL)); + return buffer_op((unsigned long) mem, len, 1, clear_chunk, NULL); } -int clear_user_skas(void __user *mem, int len) +int clear_user(void __user *mem, int len) { - if(segment_eq(get_fs(), KERNEL_DS)){ + if (segment_eq(get_fs(), KERNEL_DS)) { memset((__force void*)mem, 0, len); - return(0); + return 0; } - return(access_ok(VERIFY_WRITE, mem, len) ? - buffer_op((unsigned long) mem, len, 1, clear_chunk, NULL) : len); + return access_ok(VERIFY_WRITE, mem, len) ? + buffer_op((unsigned long) mem, len, 1, clear_chunk, NULL) : len; } static int strnlen_chunk(unsigned long str, int len, void *arg) @@ -235,31 +232,20 @@ static int strnlen_chunk(unsigned long str, int len, void *arg) n = strnlen((void *) str, len); *len_ptr += n; - if(n < len) - return(1); - return(0); + if (n < len) + return 1; + return 0; } -int strnlen_user_skas(const void __user *str, int len) +int strnlen_user(const void __user *str, int len) { int count = 0, n; - if(segment_eq(get_fs(), KERNEL_DS)) - return(strnlen((__force char*)str, len) + 1); + if (segment_eq(get_fs(), KERNEL_DS)) + return strnlen((__force char*)str, len) + 1; n = buffer_op((unsigned long) str, len, 0, strnlen_chunk, &count); - if(n == 0) - return(count + 1); - return(-EFAULT); + if (n == 0) + return count + 1; + return -EFAULT; } - -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ |