From 5606330627ab680f5e6b7549d14ec3ffdae58c15 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Mon, 2 May 2016 14:38:29 +0200 Subject: s390/dumpstack: implement and use return_address() Implement return_address() and use it instead of __builtin_return_address(n). __builtin_return_address(n) is not guaranteed to work for n > 0, therefore implement a private return_address() function which walks the stack frames and returns the proper return address. This way we get also rid of a compile warning which gcc 6.1 emits and look like all other architectures. Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/dumpstack.c | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) (limited to 'arch/s390/kernel') diff --git a/arch/s390/kernel/dumpstack.c b/arch/s390/kernel/dumpstack.c index 1b6081c..69f9908 100644 --- a/arch/s390/kernel/dumpstack.c +++ b/arch/s390/kernel/dumpstack.c @@ -89,6 +89,30 @@ void dump_trace(dump_trace_func_t func, void *data, struct task_struct *task, } EXPORT_SYMBOL_GPL(dump_trace); +struct return_address_data { + unsigned long address; + int depth; +}; + +static int __return_address(void *data, unsigned long address) +{ + struct return_address_data *rd = data; + + if (rd->depth--) + return 0; + rd->address = address; + return 1; +} + +unsigned long return_address(int depth) +{ + struct return_address_data rd = { .depth = depth + 2 }; + + dump_trace(__return_address, &rd, NULL, current_stack_pointer()); + return rd.address; +} +EXPORT_SYMBOL_GPL(return_address); + static int show_address(void *data, unsigned long address) { printk("([<%016lx>] %pSR)\n", address, (void *)address); -- cgit v1.1