1/* 2 * Split from entry_32.S 3 * 4 * This program is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU General Public License 6 * as published by the Free Software Foundation; either version 7 * 2 of the License, or (at your option) any later version. 8 */ 9 10#include <linux/magic.h> 11#include <asm/reg.h> 12#include <asm/ppc_asm.h> 13#include <asm/asm-offsets.h> 14#include <asm/ftrace.h> 15#include <asm/export.h> 16 17_GLOBAL(mcount) 18_GLOBAL(_mcount) 19 /* 20 * It is required that _mcount on PPC32 must preserve the 21 * link register. But we have r0 to play with. We use r0 22 * to push the return address back to the caller of mcount 23 * into the ctr register, restore the link register and 24 * then jump back using the ctr register. 25 */ 26 mflr r0 27 mtctr r0 28 lwz r0, 4(r1) 29 mtlr r0 30 bctr 31 32_GLOBAL(ftrace_caller) 33 MCOUNT_SAVE_FRAME 34 /* r3 ends up with link register */ 35 subi r3, r3, MCOUNT_INSN_SIZE 36.globl ftrace_call 37ftrace_call: 38 bl ftrace_stub 39 nop 40#ifdef CONFIG_FUNCTION_GRAPH_TRACER 41.globl ftrace_graph_call 42ftrace_graph_call: 43 b ftrace_graph_stub 44_GLOBAL(ftrace_graph_stub) 45#endif 46 MCOUNT_RESTORE_FRAME 47 /* old link register ends up in ctr reg */ 48 bctr 49 50EXPORT_SYMBOL(_mcount) 51 52_GLOBAL(ftrace_stub) 53 blr 54 55#ifdef CONFIG_FUNCTION_GRAPH_TRACER 56_GLOBAL(ftrace_graph_caller) 57 /* load r4 with local address */ 58 lwz r4, 44(r1) 59 subi r4, r4, MCOUNT_INSN_SIZE 60 61 /* Grab the LR out of the caller stack frame */ 62 lwz r3,52(r1) 63 64 bl prepare_ftrace_return 65 nop 66 67 /* 68 * prepare_ftrace_return gives us the address we divert to. 69 * Change the LR in the callers stack frame to this. 70 */ 71 stw r3,52(r1) 72 73 MCOUNT_RESTORE_FRAME 74 /* old link register ends up in ctr reg */ 75 bctr 76 77_GLOBAL(return_to_handler) 78 /* need to save return values */ 79 stwu r1, -32(r1) 80 stw r3, 20(r1) 81 stw r4, 16(r1) 82 stw r31, 12(r1) 83 mr r31, r1 84 85 bl ftrace_return_to_handler 86 nop 87 88 /* return value has real return address */ 89 mtlr r3 90 91 lwz r3, 20(r1) 92 lwz r4, 16(r1) 93 lwz r31,12(r1) 94 lwz r1, 0(r1) 95 96 /* Jump back to real return address */ 97 blr 98#endif /* CONFIG_FUNCTION_GRAPH_TRACER */ 99