diff options
| -rw-r--r-- | backends/ChangeLog | 6 | ||||
| -rw-r--r-- | backends/Makefile.am | 2 | ||||
| -rw-r--r-- | backends/ppc64_init.c | 1 | ||||
| -rw-r--r-- | backends/ppc64_unwind.c | 76 | ||||
| -rw-r--r-- | tests/ChangeLog | 10 | ||||
| -rw-r--r-- | tests/Makefile.am | 3 | ||||
| -rw-r--r-- | tests/backtrace-subr.sh | 2 | ||||
| -rw-r--r-- | tests/backtrace.ppc64le.fp.core.bz2 | bin | 0 -> 37786 bytes | |||
| -rwxr-xr-x | tests/backtrace.ppc64le.fp.exec.bz2 | bin | 0 -> 383808 bytes | |||
| -rwxr-xr-x | tests/run-backtrace-fp-core-ppc64le.sh | 29 |
10 files changed, 127 insertions, 2 deletions
diff --git a/backends/ChangeLog b/backends/ChangeLog index 1ac5bab3..f0d29f62 100644 --- a/backends/ChangeLog +++ b/backends/ChangeLog @@ -1,3 +1,9 @@ +2017-05-30 Mark Wielaard <[email protected]> + + * ppc64_unwind.c: New file. + * ppc64_init.c (pcc64_init): Hook unwind. + * Makefile.am (ppc64_SRCS): Add ppc64_unwind.c + 2017-04-06 Mark Wielaard <[email protected]> * i386_unwind.c: New file. diff --git a/backends/Makefile.am b/backends/Makefile.am index ff80a82c..ac45a452 100644 --- a/backends/Makefile.am +++ b/backends/Makefile.am @@ -98,7 +98,7 @@ am_libebl_ppc_pic_a_OBJECTS = $(ppc_SRCS:.c=.os) ppc64_SRCS = ppc64_init.c ppc64_symbol.c ppc64_retval.c \ ppc64_corenote.c ppc_regs.c ppc_auxv.c ppc_attrs.c ppc_syscall.c \ - ppc_cfi.c ppc_initreg.c ppc64_resolve_sym.c + ppc_cfi.c ppc_initreg.c ppc64_unwind.c ppc64_resolve_sym.c libebl_ppc64_pic_a_SOURCES = $(ppc64_SRCS) am_libebl_ppc64_pic_a_OBJECTS = $(ppc64_SRCS:.c=.os) diff --git a/backends/ppc64_init.c b/backends/ppc64_init.c index 11d3a77f..e5670338 100644 --- a/backends/ppc64_init.c +++ b/backends/ppc64_init.c @@ -73,6 +73,7 @@ ppc64_init (Elf *elf __attribute__ ((unused)), eh->frame_nregs = (114 - 1) + 32; HOOK (eh, set_initial_registers_tid); HOOK (eh, dwarf_to_regno); + HOOK (eh, unwind); HOOK (eh, resolve_sym_value); /* Find the function descriptor .opd table for resolve_sym_value. */ diff --git a/backends/ppc64_unwind.c b/backends/ppc64_unwind.c new file mode 100644 index 00000000..4fa0b5a9 --- /dev/null +++ b/backends/ppc64_unwind.c @@ -0,0 +1,76 @@ +/* Get previous frame state for an existing frame state. + Copyright (C) 2017 Red Hat, Inc. + This file is part of elfutils. + + This file is free software; you can redistribute it and/or modify + it under the terms of either + + * the GNU Lesser General Public License as published by the Free + Software Foundation; either version 3 of the License, or (at + your option) any later version + + or + + * the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at + your option) any later version + + or both in parallel, as here. + + elfutils is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received copies of the GNU General Public License and + the GNU Lesser General Public License along with this program. If + not, see <http://www.gnu.org/licenses/>. */ + +#ifdef HAVE_CONFIG_H +# include <config.h> +#endif + +#define BACKEND ppc64_ + +#define LR_REG 65 /* Not 108, see ppc_dwarf_to_regno. */ +#define SP_REG 1 + +#define LR_OFFSET 16 + +#include "libebl_CPU.h" + +/* Simplistic fallback frame unwinder. SP points to the backchain (contains + address of previous stack pointer). At SP offset 16 is the LR save area + (contains the value of the previous LR). */ + +bool +EBLHOOK(unwind) (Ebl *ebl __attribute__ ((unused)), + Dwarf_Addr pc __attribute__ ((unused)), + ebl_tid_registers_t *setfunc, ebl_tid_registers_get_t *getfunc, + ebl_pid_memory_read_t *readfunc, void *arg, + bool *signal_framep __attribute__ ((unused))) +{ + Dwarf_Word sp, newSp, lr, newLr; + + /* Stack pointer points to the backchain which contains the previous sp. */ + if (! getfunc (SP_REG, 1, &sp, arg)) + sp = 0; + + /* Link register contains previous program counter. */ + if (! getfunc (LR_REG, 1, &lr, arg) + || lr == 0 + || ! setfunc (-1, 1, &lr, arg)) + return false; + + if (! readfunc(sp, &newSp, arg)) + newSp = 0; + + if (! readfunc(newSp + LR_OFFSET, &newLr, arg)) + newLr = 0; + + setfunc(SP_REG, 1, &newSp, arg); + setfunc(LR_REG, 1, &newLr, arg); + + /* Sanity check the stack grows down. */ + return newSp > sp; +} diff --git a/tests/ChangeLog b/tests/ChangeLog index 5b0d486e..43b5bd8a 100644 --- a/tests/ChangeLog +++ b/tests/ChangeLog @@ -1,3 +1,13 @@ +2017-05-30 Mark Wielaard <[email protected]> + + * run-backtrace-fp-core-ppc64le.sh: New test. + * backtrace.ppc64le.fp.core.bz2: New test file. + * backtrace.ppc64le.fp.exec.bz2: New testfile. + * backtrace-subr.sh (check_backtracegen): Accept '(null)'. + * Makefile.am (TESTS): Add run-backtrace-fp-core-ppc64le.sh. + (EXTRA_DIST): Add run-backtrace-fp-core-ppc64le.sh, + backtrace.ppc64le.fp.core.bz2 and backtrace.ppc64le.fp.exec.bz2. + 2017-02-13 Ulf Hermann <[email protected]> Mark Wielaard <[email protected]> diff --git a/tests/Makefile.am b/tests/Makefile.am index 3a12fe3a..50648db8 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -117,6 +117,7 @@ TESTS = run-arextract.sh run-arsymtest.sh newfile test-nlist \ run-backtrace-native-core-biarch.sh run-backtrace-core-x86_64.sh \ run-backtrace-fp-core-x86_64.sh \ run-backtrace-fp-core-aarch64.sh \ + run-backtrace-fp-core-ppc64le.sh \ run-backtrace-core-x32.sh \ run-backtrace-core-i386.sh run-backtrace-fp-core-i386.sh \ run-backtrace-core-ppc.sh \ @@ -303,6 +304,8 @@ EXTRA_DIST = run-arextract.sh run-arsymtest.sh \ backtrace-subr.sh backtrace.i386.core.bz2 backtrace.i386.exec.bz2 \ run-backtrace-fp-core-i386.sh \ backtrace.i386.fp.core.bz2 backtrace.i386.fp.exec.bz2 \ + run-backtrace-fp-core-ppc64le.sh \ + backtrace.ppc64le.fp.core.bz2 backtrace.ppc64le.fp.exec.bz2 \ backtrace.x86_64.core.bz2 backtrace.x86_64.exec.bz2 \ backtrace.x86_64.fp.core.bz2 backtrace.x86_64.fp.exec.bz2 \ backtrace.ppc.core.bz2 backtrace.ppc.exec.bz2 \ diff --git a/tests/backtrace-subr.sh b/tests/backtrace-subr.sh index 9731c43a..c1f31569 100644 --- a/tests/backtrace-subr.sh +++ b/tests/backtrace-subr.sh @@ -59,7 +59,7 @@ check_backtracegen() # Ignore it here as it is a bug of OS, not a bug of elfutils. check_err() { - if [ $(egrep -v <$1 'dwfl_thread_getframes: (No DWARF information found|no matching address range|address out of range|Invalid register)$' \ + if [ $(egrep -v <$1 'dwfl_thread_getframes: (No DWARF information found|no matching address range|address out of range|Invalid register|\(null\))$' \ | wc -c) \ -eq 0 ] then diff --git a/tests/backtrace.ppc64le.fp.core.bz2 b/tests/backtrace.ppc64le.fp.core.bz2 Binary files differnew file mode 100644 index 00000000..e63babf3 --- /dev/null +++ b/tests/backtrace.ppc64le.fp.core.bz2 diff --git a/tests/backtrace.ppc64le.fp.exec.bz2 b/tests/backtrace.ppc64le.fp.exec.bz2 Binary files differnew file mode 100755 index 00000000..ed1352af --- /dev/null +++ b/tests/backtrace.ppc64le.fp.exec.bz2 diff --git a/tests/run-backtrace-fp-core-ppc64le.sh b/tests/run-backtrace-fp-core-ppc64le.sh new file mode 100755 index 00000000..326ca342 --- /dev/null +++ b/tests/run-backtrace-fp-core-ppc64le.sh @@ -0,0 +1,29 @@ +#! /bin/bash +# Copyright (C) 2017 Red Hat, Inc. +# This file is part of elfutils. +# +# This file is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# elfutils is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see <http://www.gnu.org/licenses/>. + +. $srcdir/backtrace-subr.sh + +# The binary is generated by compiling backtrace-child without unwind +# information, but with -fno-omit-frame-pointer. +# +# gcc -static -O2 -fno-omit-frame-pointer -fno-asynchronous-unwind-tables \ +# -D_GNU_SOURCE -pthread -o tests/backtrace.ppc64le.fp.exec -I. -Ilib \ +# tests/backtrace-child.c +# +# The core is generated by calling tests/backtrace.ppc64le.fp.exec --gencore + +check_core ppc64le.fp |
