aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMartin Schwidefsky <schwidefsky@de.ibm.com>2019-02-18 10:51:28 -0500
committerMartin Schwidefsky <schwidefsky@de.ibm.com>2019-05-02 07:54:11 -0400
commitec7bf4789d95a0053bac0dfa36fbefd8cc584eea (patch)
tree5ad08bd5f30c065e312944baf8eafd0b4766f654
parent78c98f9074135d3dab4e39544e0a537f92388fce (diff)
s390/ftrace: use HAVE_FUNCTION_GRAPH_RET_ADDR_PTR
Make the call chain more reliable by tagging the ftrace stack entries with the stack pointer that is associated with the return address. Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
-rw-r--r--arch/s390/include/asm/ftrace.h2
-rw-r--r--arch/s390/kernel/entry.h2
-rw-r--r--arch/s390/kernel/ftrace.c9
-rw-r--r--arch/s390/kernel/mcount.S4
-rw-r--r--arch/s390/kernel/unwind_bc.c2
5 files changed, 11 insertions, 8 deletions
diff --git a/arch/s390/include/asm/ftrace.h b/arch/s390/include/asm/ftrace.h
index 6e0ed0338785..68d362f8d6c1 100644
--- a/arch/s390/include/asm/ftrace.h
+++ b/arch/s390/include/asm/ftrace.h
@@ -11,6 +11,8 @@
11#define MCOUNT_RETURN_FIXUP 18 11#define MCOUNT_RETURN_FIXUP 18
12#endif 12#endif
13 13
14#define HAVE_FUNCTION_GRAPH_RET_ADDR_PTR
15
14#ifndef __ASSEMBLY__ 16#ifndef __ASSEMBLY__
15 17
16#ifdef CONFIG_CC_IS_CLANG 18#ifdef CONFIG_CC_IS_CLANG
diff --git a/arch/s390/kernel/entry.h b/arch/s390/kernel/entry.h
index c3816ae108b0..20420c2b8a14 100644
--- a/arch/s390/kernel/entry.h
+++ b/arch/s390/kernel/entry.h
@@ -65,7 +65,7 @@ int setup_profiling_timer(unsigned int multiplier);
65void __init time_init(void); 65void __init time_init(void);
66int pfn_is_nosave(unsigned long); 66int pfn_is_nosave(unsigned long);
67void s390_early_resume(void); 67void s390_early_resume(void);
68unsigned long prepare_ftrace_return(unsigned long parent, unsigned long ip); 68unsigned long prepare_ftrace_return(unsigned long parent, unsigned long sp, unsigned long ip);
69 69
70struct s390_mmap_arg_struct; 70struct s390_mmap_arg_struct;
71struct fadvise64_64_args; 71struct fadvise64_64_args;
diff --git a/arch/s390/kernel/ftrace.c b/arch/s390/kernel/ftrace.c
index 39b13d71a8fe..1bb85f60c0dd 100644
--- a/arch/s390/kernel/ftrace.c
+++ b/arch/s390/kernel/ftrace.c
@@ -201,17 +201,18 @@ device_initcall(ftrace_plt_init);
201 * Hook the return address and push it in the stack of return addresses 201 * Hook the return address and push it in the stack of return addresses
202 * in current thread info. 202 * in current thread info.
203 */ 203 */
204unsigned long prepare_ftrace_return(unsigned long parent, unsigned long ip) 204unsigned long prepare_ftrace_return(unsigned long ra, unsigned long sp,
205 unsigned long ip)
205{ 206{
206 if (unlikely(ftrace_graph_is_dead())) 207 if (unlikely(ftrace_graph_is_dead()))
207 goto out; 208 goto out;
208 if (unlikely(atomic_read(&current->tracing_graph_pause))) 209 if (unlikely(atomic_read(&current->tracing_graph_pause)))
209 goto out; 210 goto out;
210 ip -= MCOUNT_INSN_SIZE; 211 ip -= MCOUNT_INSN_SIZE;
211 if (!function_graph_enter(parent, ip, 0, NULL)) 212 if (!function_graph_enter(ra, ip, 0, (void *) sp))
212 parent = (unsigned long) return_to_handler; 213 ra = (unsigned long) return_to_handler;
213out: 214out:
214 return parent; 215 return ra;
215} 216}
216NOKPROBE_SYMBOL(prepare_ftrace_return); 217NOKPROBE_SYMBOL(prepare_ftrace_return);
217 218
diff --git a/arch/s390/kernel/mcount.S b/arch/s390/kernel/mcount.S
index 09ae6da0aaa5..9e1660a6b9db 100644
--- a/arch/s390/kernel/mcount.S
+++ b/arch/s390/kernel/mcount.S
@@ -65,8 +65,8 @@ ENTRY(ftrace_caller)
65 .globl ftrace_graph_caller 65 .globl ftrace_graph_caller
66ftrace_graph_caller: 66ftrace_graph_caller:
67 j ftrace_graph_caller_end 67 j ftrace_graph_caller_end
68 lg %r2,(STACK_PTREGS_GPRS+14*8)(%r15) 68 lmg %r2,%r3,(STACK_PTREGS_GPRS+14*8)(%r15)
69 lg %r3,(STACK_PTREGS_PSW+8)(%r15) 69 lg %r4,(STACK_PTREGS_PSW+8)(%r15)
70 brasl %r14,prepare_ftrace_return 70 brasl %r14,prepare_ftrace_return
71 stg %r2,(STACK_PTREGS_GPRS+14*8)(%r15) 71 stg %r2,(STACK_PTREGS_GPRS+14*8)(%r15)
72ftrace_graph_caller_end: 72ftrace_graph_caller_end:
diff --git a/arch/s390/kernel/unwind_bc.c b/arch/s390/kernel/unwind_bc.c
index cf5a630f3aa9..57fd4e902f1f 100644
--- a/arch/s390/kernel/unwind_bc.c
+++ b/arch/s390/kernel/unwind_bc.c
@@ -84,7 +84,7 @@ bool unwind_next_frame(struct unwind_state *state)
84 /* Decode any ftrace redirection */ 84 /* Decode any ftrace redirection */
85 if (ip == (unsigned long) return_to_handler) 85 if (ip == (unsigned long) return_to_handler)
86 ip = ftrace_graph_ret_addr(state->task, &state->graph_idx, 86 ip = ftrace_graph_ret_addr(state->task, &state->graph_idx,
87 ip, NULL); 87 ip, (void *) sp);
88#endif 88#endif
89 89
90 /* Update unwind state */ 90 /* Update unwind state */