OSDN Git Service

powerpc/modules: Create module_trampoline_target()
authorAnton Blanchard <anton@samba.org>
Fri, 4 Apr 2014 04:58:42 +0000 (15:58 +1100)
committerAnton Blanchard <anton@samba.org>
Wed, 23 Apr 2014 00:05:34 +0000 (10:05 +1000)
ftrace has way too much knowledge of our kernel module trampoline
layout hidden inside it. Create module_trampoline_target() that gives
the target address of a kernel module trampoline.

Signed-off-by: Anton Blanchard <anton@samba.org>
arch/powerpc/include/asm/module.h
arch/powerpc/kernel/module_64.c

index f2711f0..dcfcad1 100644 (file)
@@ -79,6 +79,8 @@ struct mod_arch_specific {
 #endif
 
 bool is_module_trampoline(u32 *insns);
+int module_trampoline_target(struct module *mod, u32 *trampoline,
+                            unsigned long *target);
 
 struct exception_table_entry;
 void sort_ex_table(struct exception_table_entry *start,
index 4db5ecd..ef349d0 100644 (file)
@@ -176,6 +176,35 @@ bool is_module_trampoline(u32 *p)
        return true;
 }
 
+int module_trampoline_target(struct module *mod, u32 *trampoline,
+                            unsigned long *target)
+{
+       u32 buf[2];
+       u16 upper, lower;
+       long offset;
+       void *toc_entry;
+
+       if (probe_kernel_read(buf, trampoline, sizeof(buf)))
+               return -EFAULT;
+
+       upper = buf[0] & 0xffff;
+       lower = buf[1] & 0xffff;
+
+       /* perform the addis/addi, both signed */
+       offset = ((short)upper << 16) + (short)lower;
+
+       /*
+        * Now get the address this trampoline jumps to. This
+        * is always 32 bytes into our trampoline stub.
+        */
+       toc_entry = (void *)mod->arch.toc + offset + 32;
+
+       if (probe_kernel_read(target, toc_entry, sizeof(*target)))
+               return -EFAULT;
+
+       return 0;
+}
+
 #endif
 
 /* Count how many different 24-bit relocations (different symbol,