mm: fault feedback #2
[safe/jmp/linux-2.6] / arch / arm / mm / fault.c
index 75d4914..c04124a 100644 (file)
@@ -183,20 +183,20 @@ good_area:
         */
 survive:
        fault = handle_mm_fault(mm, vma, addr & PAGE_MASK, fsr & (1 << 11));
-
-       /*
-        * Handle the "normal" cases first - successful and sigbus
-        */
-       switch (fault) {
-       case VM_FAULT_MAJOR:
+       if (unlikely(fault & VM_FAULT_ERROR)) {
+               if (fault & VM_FAULT_OOM)
+                       goto out_of_memory;
+               else if (fault & VM_FAULT_SIGBUS)
+                       return fault;
+               BUG();
+       }
+       if (fault & VM_FAULT_MAJOR)
                tsk->maj_flt++;
-               return fault;
-       case VM_FAULT_MINOR:
+       else
                tsk->min_flt++;
-       case VM_FAULT_SIGBUS:
-               return fault;
-       }
+       return fault;
 
+out_of_memory:
        if (!is_init(tsk))
                goto out;
 
@@ -249,7 +249,7 @@ do_page_fault(unsigned long addr, unsigned int fsr, struct pt_regs *regs)
        /*
         * Handle the "normal" case first - VM_FAULT_MAJOR / VM_FAULT_MINOR
         */
-       if (fault >= VM_FAULT_MINOR)
+       if (likely(!(fault & VM_FAULT_ERROR)))
                return 0;
 
        /*
@@ -259,8 +259,7 @@ do_page_fault(unsigned long addr, unsigned int fsr, struct pt_regs *regs)
        if (!user_mode(regs))
                goto no_context;
 
-       switch (fault) {
-       case VM_FAULT_OOM:
+       if (fault & VM_FAULT_OOM) {
                /*
                 * We ran out of memory, or some other thing
                 * happened to us that made us unable to handle
@@ -269,17 +268,15 @@ do_page_fault(unsigned long addr, unsigned int fsr, struct pt_regs *regs)
                printk("VM: killing process %s\n", tsk->comm);
                do_exit(SIGKILL);
                return 0;
-
-       case VM_FAULT_SIGBUS:
+       }
+       if (fault & VM_FAULT_SIGBUS) {
                /*
                 * We had some memory, but were unable to
                 * successfully fix up this page fault.
                 */
                sig = SIGBUS;
                code = BUS_ADRERR;
-               break;
-
-       default:
+       } else {
                /*
                 * Something tried to access memory that
                 * isn't in our memory map..
@@ -287,7 +284,6 @@ do_page_fault(unsigned long addr, unsigned int fsr, struct pt_regs *regs)
                sig = SIGSEGV;
                code = fault == VM_FAULT_BADACCESS ?
                        SEGV_ACCERR : SEGV_MAPERR;
-               break;
        }
 
        __do_user_fault(tsk, addr, fsr, sig, code, regs);