root/arch/mips/mm/fault.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. do_page_fault

   1 /*
   2  *  arch/mips/mm/fault.c
   3  *
   4  *  Copyright (C) 1995 by Ralf Baechle
   5  */
   6 #include <linux/signal.h>
   7 #include <linux/sched.h>
   8 #include <linux/head.h>
   9 #include <linux/kernel.h>
  10 #include <linux/errno.h>
  11 #include <linux/string.h>
  12 #include <linux/types.h>
  13 #include <linux/ptrace.h>
  14 #include <linux/mman.h>
  15 #include <linux/mm.h>
  16 
  17 #include <asm/system.h>
  18 #include <asm/segment.h>
  19 #include <asm/pgtable.h>
  20 
  21 extern void die_if_kernel(char *, struct pt_regs *, long);
  22 
  23 /*
  24  * This routine handles page faults.  It determines the address,
  25  * and the problem, and then passes it off to one of the appropriate
  26  * routines.
  27  */
  28 asmlinkage void
  29 do_page_fault(struct pt_regs *regs, unsigned long writeaccess, unsigned long address)
     /* [previous][next][first][last][top][bottom][index][help] */
  30 {
  31         struct vm_area_struct * vma;
  32 
  33 #if 0
  34         printk("do_page_fault() #1: %s %08lx (epc == %08lx, ra == %08lx)\n",
  35                writeaccess ? "writeaccess to" : "readaccess from",
  36                address, regs->cp0_epc, regs->reg31);
  37 #endif
  38         vma = find_vma(current, address);
  39         if (!vma)
  40                 goto bad_area;
  41         if (vma->vm_start <= address)
  42                 goto good_area;
  43         if (!(vma->vm_flags & VM_GROWSDOWN))
  44                 goto bad_area;
  45         if (expand_stack(vma, address))
  46                 goto bad_area;
  47 /*
  48  * Ok, we have a good vm_area for this memory access, so
  49  * we can handle it..
  50  */
  51 good_area:
  52         if (writeaccess) {
  53                 if (!(vma->vm_flags & VM_WRITE))
  54                         goto bad_area;
  55         } else {
  56                 if (!(vma->vm_flags & (VM_READ | VM_EXEC)))
  57                         goto bad_area;
  58         }
  59         handle_mm_fault(vma, address, writeaccess);
  60         /* FIXME: This flushes the cache far to often */
  61         sys_cacheflush(address, PAGE_SIZE, BCACHE);
  62 
  63         return;
  64 
  65 /*
  66  * Something tried to access memory that isn't in our memory map..
  67  * Fix it, but check if it's kernel or user first..
  68  */
  69 bad_area:
  70         if (user_mode(regs)) {
  71                 current->tss.cp0_badvaddr = address;
  72                 current->tss.error_code = writeaccess;
  73                 send_sig(SIGSEGV, current, 1);
  74                 return;
  75         }
  76         /*
  77          * Oops. The kernel tried to access some bad page. We'll have to
  78          * terminate things with extreme prejudice.
  79          */
  80         printk(KERN_ALERT "Unable to handle kernel paging request at virtual "
  81                "address %08lx\n", address);
  82         die_if_kernel("Oops", regs, writeaccess);
  83         do_exit(SIGKILL);
  84 }

/* [previous][next][first][last][top][bottom][index][help] */