Merge branch 'i2c/for-mergewindow' of git://git.kernel.org/pub/scm/linux/kernel/git...
[linux-2.6-microblaze.git] / arch / arm / mm / fault.c
index bc8779d..a1cebe3 100644 (file)
@@ -17,6 +17,7 @@
 #include <linux/sched/debug.h>
 #include <linux/highmem.h>
 #include <linux/perf_event.h>
+#include <linux/kfence.h>
 
 #include <asm/system_misc.h>
 #include <asm/system_info.h>
@@ -99,6 +100,11 @@ void show_pte(const char *lvl, struct mm_struct *mm, unsigned long addr)
 { }
 #endif                                 /* CONFIG_MMU */
 
+static inline bool is_write_fault(unsigned int fsr)
+{
+       return (fsr & FSR_WRITE) && !(fsr & FSR_CM);
+}
+
 static void die_kernel_fault(const char *msg, struct mm_struct *mm,
                             unsigned long addr, unsigned int fsr,
                             struct pt_regs *regs)
@@ -131,10 +137,14 @@ __do_kernel_fault(struct mm_struct *mm, unsigned long addr, unsigned int fsr,
        /*
         * No handler, we'll have to terminate things with extreme prejudice.
         */
-       if (addr < PAGE_SIZE)
+       if (addr < PAGE_SIZE) {
                msg = "NULL pointer dereference";
-       else
+       } else {
+               if (kfence_handle_page_fault(addr, is_write_fault(fsr), regs))
+                       return;
+
                msg = "paging request";
+       }
 
        die_kernel_fault(msg, mm, addr, fsr, regs);
 }
@@ -191,8 +201,8 @@ void do_bad_area(unsigned long addr, unsigned int fsr, struct pt_regs *regs)
 }
 
 #ifdef CONFIG_MMU
-#define VM_FAULT_BADMAP                0x010000
-#define VM_FAULT_BADACCESS     0x020000
+#define VM_FAULT_BADMAP                ((__force vm_fault_t)0x010000)
+#define VM_FAULT_BADACCESS     ((__force vm_fault_t)0x020000)
 
 static inline bool is_permission_fault(unsigned int fsr)
 {
@@ -261,7 +271,7 @@ do_page_fault(unsigned long addr, unsigned int fsr, struct pt_regs *regs)
        if (user_mode(regs))
                flags |= FAULT_FLAG_USER;
 
-       if ((fsr & FSR_WRITE) && !(fsr & FSR_CM)) {
+       if (is_write_fault(fsr)) {
                flags |= FAULT_FLAG_WRITE;
                vm_flags = VM_WRITE;
        }