diff options
author | Ulf Hermann <ulf.hermann@qt.io> | 2018-10-11 17:20:12 +0200 |
---|---|---|
committer | Ulf Hermann <ulf.hermann@qt.io> | 2018-10-11 17:54:03 +0200 |
commit | 5da108a40dd24c7d3e4183ec9ae1904bb3f01575 (patch) | |
tree | b3aacdcce39ec53a581137229e4a30ccb235f09d /backends | |
parent | c8dd3e3985dce3ae94bb09d6df82a516852e78c4 (diff) | |
parent | 52b6b2f1f49e7385527e9f311f248092be0c0b61 (diff) |
Merge tag 'elfutils-0.174'
elfutils 0.174 release
Change-Id: Ibcbdfca61cf0b65391ab6d0ad00f18ba61027e07
Diffstat (limited to 'backends')
-rw-r--r-- | backends/ChangeLog | 38 | ||||
-rw-r--r-- | backends/Makefile.am | 5 | ||||
-rw-r--r-- | backends/aarch64_symbol.c | 9 | ||||
-rw-r--r-- | backends/alpha_symbol.c | 1 | ||||
-rw-r--r-- | backends/m68k_cfi.c | 58 | ||||
-rw-r--r-- | backends/m68k_init.c | 4 | ||||
-rw-r--r-- | backends/m68k_initreg.c | 82 | ||||
-rw-r--r-- | backends/ppc64_init.c | 6 | ||||
-rw-r--r-- | backends/ppc64_symbol.c | 7 | ||||
-rw-r--r-- | backends/ppc_symbol.c | 7 | ||||
-rw-r--r-- | backends/riscv_corenote.c | 60 | ||||
-rw-r--r-- | backends/riscv_init.c | 2 | ||||
-rw-r--r-- | backends/riscv_initreg.c | 77 | ||||
-rw-r--r-- | backends/riscv_regs.c | 2 | ||||
-rw-r--r-- | backends/riscv_symbol.c | 7 |
15 files changed, 350 insertions, 15 deletions
diff --git a/backends/ChangeLog b/backends/ChangeLog index be1da46a..3e0dd266 100644 --- a/backends/ChangeLog +++ b/backends/ChangeLog @@ -13,6 +13,44 @@ * Makefile.am: Link backends against libgnu.a if requested. +2018-09-12 Mark Wielaard <mark@klomp.org> + + * ppc64_init.c (ppc64_init): Use elf_getshdrstrndx. + +2018-09-12 Mark Wielaard <mark@klomp.org> + + * aarch64_symbol.c (aarch64_check_special_symbol): Drop ehdr argument, + use elf_getshdrstrndx. + * alpha_symbol.c (alpha_check_special_symbol): Drop ehdr argument. + * ppc64_symbol.c (ppc64_check_special_symbol): Likewise and use + elf_getshdrstrndx. + * ppc_symbol.c (ppc_check_special_symbol): Likewise. + * riscv_symbol.c (riscv_check_special_symbol): Likewise. + +2018-07-21 Andreas Schwab <schwab@linux-m68k.org> + + * Makefile.am (m68k_SRCS): Add m68k_cfi.c and m68k_initreg.c. + * m68k_cfi.c: New file. + * m68k_initreg.c: New file. + * m68k_init.c (m68k_init): Hook abi_cfi and + set_initial_registers_tid. + +2018-07-19 Andreas Schwab <schwab@suse.de> + + * riscv_regs.c (riscv_register_info): Fix typo. + +2018-07-17 Andreas Schwab <schwab@suse.de> + + * Makefile.am (riscv_SRCS): Add riscv_corenote.c. + * riscv_corenote.c: New file. + * riscv_init.c (riscv_init): Hook core_note. + +2018-07-11 Andreas Schwab <schwab@suse.de> + + * Makefile.am (riscv_SRCS): Add riscv_initreg.c. + * riscv_initreg.c: New file. + * riscv_init.c (riscv_init): Hook set_initial_registers_tid. + 2018-06-16 Yonghong Song <yhs@fb.com> * Makefile.am (bpf_SRCS): Add bpf_symbol.c. diff --git a/backends/Makefile.am b/backends/Makefile.am index 41530099..a48b1762 100644 --- a/backends/Makefile.am +++ b/backends/Makefile.am @@ -122,7 +122,7 @@ libebl_tilegx_pic_a_SOURCES = $(tilegx_SRCS) am_libebl_tilegx_pic_a_OBJECTS = $(tilegx_SRCS:.c=.os) m68k_SRCS = m68k_init.c m68k_symbol.c m68k_regs.c \ - m68k_retval.c m68k_corenote.c + m68k_retval.c m68k_corenote.c m68k_cfi.c m68k_initreg.c libebl_m68k_pic_a_SOURCES = $(m68k_SRCS) am_libebl_m68k_pic_a_OBJECTS = $(m68k_SRCS:.c=.os) @@ -138,7 +138,8 @@ cpu_bpf = ../libcpu/libcpu_bpf.a libebl_bpf_pic_a_SOURCES = $(bpf_SRCS) am_libebl_bpf_pic_a_OBJECTS = $(bpf_SRCS:.c=.os) -riscv_SRCS = riscv_init.c riscv_symbol.c riscv_cfi.c riscv_regs.c +riscv_SRCS = riscv_init.c riscv_symbol.c riscv_cfi.c riscv_regs.c \ + riscv_initreg.c riscv_corenote.c libebl_riscv_pic_a_SOURCES = $(riscv_SRCS) am_libebl_riscv_pic_a_OBJECTS = $(riscv_SRCS:.c=.os) diff --git a/backends/aarch64_symbol.c b/backends/aarch64_symbol.c index da3382e9..dfd755a5 100644 --- a/backends/aarch64_symbol.c +++ b/backends/aarch64_symbol.c @@ -62,13 +62,16 @@ aarch64_reloc_simple_type (Ebl *ebl __attribute__ ((unused)), int type) https://bugzilla.redhat.com/show_bug.cgi?id=1201778 */ bool -aarch64_check_special_symbol (Elf *elf, GElf_Ehdr *ehdr, const GElf_Sym *sym, +aarch64_check_special_symbol (Elf *elf, const GElf_Sym *sym, const char *name, const GElf_Shdr *destshdr) { if (name != NULL && strcmp (name, "_GLOBAL_OFFSET_TABLE_") == 0) { - const char *sname = elf_strptr (elf, ehdr->e_shstrndx, destshdr->sh_name); + size_t shstrndx; + if (elf_getshdrstrndx (elf, &shstrndx) != 0) + return false; + const char *sname = elf_strptr (elf, shstrndx, destshdr->sh_name); if (sname != NULL && (strcmp (sname, ".got") == 0 || strcmp (sname, ".got.plt") == 0)) { @@ -79,7 +82,7 @@ aarch64_check_special_symbol (Elf *elf, GElf_Ehdr *ehdr, const GElf_Sym *sym, GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem); if (shdr != NULL) { - sname = elf_strptr (elf, ehdr->e_shstrndx, shdr->sh_name); + sname = elf_strptr (elf, shstrndx, shdr->sh_name); if (sname != NULL && strcmp (sname, ".got") == 0) return (sym->st_value >= shdr->sh_addr && sym->st_value < shdr->sh_addr + shdr->sh_size); diff --git a/backends/alpha_symbol.c b/backends/alpha_symbol.c index 657d9eec..b7f7c17a 100644 --- a/backends/alpha_symbol.c +++ b/backends/alpha_symbol.c @@ -130,7 +130,6 @@ alpha_check_special_section (Ebl *ebl, normal checks. */ bool alpha_check_special_symbol (Elf *elf __attribute__ ((unused)), - GElf_Ehdr *ehdr __attribute__ ((unused)), const GElf_Sym *sym __attribute__ ((unused)), const char *name, const GElf_Shdr *destshdr __attribute__ ((unused))) diff --git a/backends/m68k_cfi.c b/backends/m68k_cfi.c new file mode 100644 index 00000000..9303fb22 --- /dev/null +++ b/backends/m68k_cfi.c @@ -0,0 +1,58 @@ +/* m68k ABI-specified defaults for DWARF CFI. + 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 + +#include <dwarf.h> + +#define BACKEND m68k_ +#include "libebl_CPU.h" + +int +m68k_abi_cfi (Ebl *ebl __attribute__ ((unused)), Dwarf_CIE *abi_info) +{ + static const uint8_t abi_cfi[] = + { +#define SV(n) DW_CFA_same_value, ULEB128_7 (n) + /* Call-saved registers %d2-%d7, %a2-%a6. */ + SV (2), SV (3), SV (4), SV (5), SV (6), SV (7), + SV (10), SV (11), SV (12), SV (13), SV (14), + + /* The CFA is the SP. */ + DW_CFA_val_offset, ULEB128_7 (15), ULEB128_7 (0), + }; + + abi_info->initial_instructions = abi_cfi; + abi_info->initial_instructions_end = &abi_cfi[sizeof abi_cfi]; + abi_info->data_alignment_factor = -4; + + abi_info->return_address_register = 24; /* %pc */ + + return 0; +} diff --git a/backends/m68k_init.c b/backends/m68k_init.c index 943478fb..8cae710b 100644 --- a/backends/m68k_init.c +++ b/backends/m68k_init.c @@ -55,6 +55,10 @@ m68k_init (Elf *elf __attribute__ ((unused)), HOOK (eh, return_value_location); HOOK (eh, register_info); HOOK (eh, core_note); + HOOK (eh, abi_cfi); + /* gcc/config/ #define DWARF_FRAME_REGISTERS. */ + eh->frame_nregs = 25; + HOOK (eh, set_initial_registers_tid); return MODVERSION; } diff --git a/backends/m68k_initreg.c b/backends/m68k_initreg.c new file mode 100644 index 00000000..61f260f6 --- /dev/null +++ b/backends/m68k_initreg.c @@ -0,0 +1,82 @@ +/* Fetch live process registers from TID. + 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 + +#if defined __m68k__ && defined __linux__ +# include <sys/types.h> +# include <sys/user.h> +# include <sys/ptrace.h> +#endif + +#define BACKEND m68k_ +#include "libebl_CPU.h" + +bool +m68k_set_initial_registers_tid (pid_t tid __attribute__ ((unused)), + ebl_tid_registers_t *setfunc __attribute__ ((unused)), + void *arg __attribute__ ((unused))) +{ +#if !defined __m68k__ || !defined __linux__ + return false; +#else /* __m68k__ */ + struct user_regs_struct user_regs; + if (ptrace (PTRACE_GETREGS, tid, NULL, &user_regs) != 0) + return false; + + Dwarf_Word dwarf_regs[16]; + dwarf_regs[0] = user_regs.d0; + dwarf_regs[1] = user_regs.d1; + dwarf_regs[2] = user_regs.d2; + dwarf_regs[3] = user_regs.d3; + dwarf_regs[4] = user_regs.d4; + dwarf_regs[5] = user_regs.d5; + dwarf_regs[6] = user_regs.d6; + dwarf_regs[7] = user_regs.d7; + dwarf_regs[8] = user_regs.a0; + dwarf_regs[9] = user_regs.a1; + dwarf_regs[10] = user_regs.a2; + dwarf_regs[11] = user_regs.a3; + dwarf_regs[12] = user_regs.a4; + dwarf_regs[13] = user_regs.a5; + dwarf_regs[14] = user_regs.a6; + dwarf_regs[15] = user_regs.usp; + + /* D0..D7, A0..A7. */ + if (! setfunc (0, 16, dwarf_regs, arg)) + return false; + + /* PC. */ + dwarf_regs[0] = user_regs.pc; + if (! setfunc (24, 1, dwarf_regs, arg)) + return false; + + return true; +#endif /* __m68k__ */ +} diff --git a/backends/ppc64_init.c b/backends/ppc64_init.c index e5670338..3db5e766 100644 --- a/backends/ppc64_init.c +++ b/backends/ppc64_init.c @@ -80,7 +80,9 @@ ppc64_init (Elf *elf __attribute__ ((unused)), if (elf != NULL) { GElf_Ehdr ehdr_mem, *ehdr = gelf_getehdr (elf, &ehdr_mem); - if (ehdr != NULL && ehdr->e_type != ET_REL) + size_t shstrndx; + if (ehdr != NULL && ehdr->e_type != ET_REL + && elf_getshdrstrndx (elf, &shstrndx) == 0) { /* We could also try through DT_PPC64_OPD and DT_PPC64_OPDSZ. */ GElf_Shdr opd_shdr_mem, *opd_shdr; @@ -93,7 +95,7 @@ ppc64_init (Elf *elf __attribute__ ((unused)), && opd_shdr->sh_type == SHT_PROGBITS && opd_shdr->sh_size > 0) { - const char *name = elf_strptr (elf, ehdr->e_shstrndx, + const char *name = elf_strptr (elf, shstrndx, opd_shdr->sh_name); if (name != NULL && strcmp (name, ".opd") == 0) { diff --git a/backends/ppc64_symbol.c b/backends/ppc64_symbol.c index 0feddcee..40ba4f74 100644 --- a/backends/ppc64_symbol.c +++ b/backends/ppc64_symbol.c @@ -94,12 +94,15 @@ ppc64_dynamic_tag_check (int64_t tag) /* Check whether given symbol's st_value and st_size are OK despite failing normal checks. */ bool -ppc64_check_special_symbol (Elf *elf, GElf_Ehdr *ehdr, +ppc64_check_special_symbol (Elf *elf, const GElf_Sym *sym __attribute__ ((unused)), const char *name __attribute__ ((unused)), const GElf_Shdr *destshdr) { - const char *sname = elf_strptr (elf, ehdr->e_shstrndx, destshdr->sh_name); + size_t shstrndx; + if (elf_getshdrstrndx (elf, &shstrndx) != 0) + return false; + const char *sname = elf_strptr (elf, shstrndx, destshdr->sh_name); if (sname == NULL) return false; return strcmp (sname, ".opd") == 0; diff --git a/backends/ppc_symbol.c b/backends/ppc_symbol.c index 4b32003a..35b14319 100644 --- a/backends/ppc_symbol.c +++ b/backends/ppc_symbol.c @@ -135,7 +135,7 @@ find_dyn_got (Elf *elf, GElf_Addr *addr) /* Check whether given symbol's st_value and st_size are OK despite failing normal checks. */ bool -ppc_check_special_symbol (Elf *elf, GElf_Ehdr *ehdr, const GElf_Sym *sym, +ppc_check_special_symbol (Elf *elf, const GElf_Sym *sym, const char *name, const GElf_Shdr *destshdr) { if (name == NULL) @@ -152,7 +152,10 @@ ppc_check_special_symbol (Elf *elf, GElf_Ehdr *ehdr, const GElf_Sym *sym, return true; } - const char *sname = elf_strptr (elf, ehdr->e_shstrndx, destshdr->sh_name); + size_t shstrndx; + if (elf_getshdrstrndx (elf, &shstrndx) != 0) + return false; + const char *sname = elf_strptr (elf, shstrndx, destshdr->sh_name); if (sname == NULL) return false; diff --git a/backends/riscv_corenote.c b/backends/riscv_corenote.c new file mode 100644 index 00000000..37cce7e3 --- /dev/null +++ b/backends/riscv_corenote.c @@ -0,0 +1,60 @@ +/* RISC-V specific core note handling. + 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 + +#include <elf.h> +#include <inttypes.h> +#include <stddef.h> +#include <stdio.h> +#include <sys/time.h> + +#define BACKEND riscv_ +#include "libebl_CPU.h" + +#define ULONG uint64_t +#define PID_T int32_t +#define UID_T uint32_t +#define GID_T uint32_t +#define ALIGN_ULONG 8 +#define ALIGN_PID_T 4 +#define ALIGN_UID_T 4 +#define ALIGN_GID_T 4 +#define TYPE_ULONG ELF_T_XWORD +#define TYPE_PID_T ELF_T_SWORD +#define TYPE_UID_T ELF_T_WORD +#define TYPE_GID_T ELF_T_WORD + +static const Ebl_Register_Location prstatus_regs[] = + { + { .offset = 1, .regno = 1, .count = 31, .bits = 64 } /* x1..x31 */ + }; +#define PRSTATUS_REGS_SIZE (32 * 8) + +#include "linux-core-note.c" diff --git a/backends/riscv_init.c b/backends/riscv_init.c index 5588a6b7..8b7ce8b5 100644 --- a/backends/riscv_init.c +++ b/backends/riscv_init.c @@ -57,6 +57,8 @@ riscv_init (Elf *elf __attribute__ ((unused)), eh->frame_nregs = 66; HOOK (eh, check_special_symbol); HOOK (eh, machine_flag_check); + HOOK (eh, set_initial_registers_tid); + HOOK (eh, core_note); return MODVERSION; } diff --git a/backends/riscv_initreg.c b/backends/riscv_initreg.c new file mode 100644 index 00000000..e31a4dfd --- /dev/null +++ b/backends/riscv_initreg.c @@ -0,0 +1,77 @@ +/* Fetch live process registers from TID. + 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 + +#include "system.h" +#include <assert.h> +#if defined __riscv && defined __linux__ +# include <sys/uio.h> +# include <sys/procfs.h> +# include <sys/ptrace.h> +#endif + +#define BACKEND riscv_ +#include "libebl_CPU.h" + +bool +riscv_set_initial_registers_tid (pid_t tid __attribute__ ((unused)), + ebl_tid_registers_t *setfunc __attribute__ ((unused)), + void *arg __attribute__ ((unused))) +{ +#if !defined __riscv || !defined __linux__ + return false; +#else /* __riscv */ + + /* General registers. */ + elf_gregset_t gregs; + struct iovec iovec; + iovec.iov_base = &gregs; + iovec.iov_len = sizeof (gregs); + if (ptrace (PTRACE_GETREGSET, tid, NT_PRSTATUS, &iovec) != 0) + return false; + + /* X0 is constant 0. */ + Dwarf_Word zero = 0; + if (! setfunc (0, 1, &zero, arg)) + return false; + + /* X1..X31. */ + if (! setfunc (1, 32, (Dwarf_Word *) &gregs[1], arg)) + return false; + + /* PC. */ + if (! setfunc (-1, 1, (Dwarf_Word *) &gregs[0], arg)) + return false; + + /* FP registers not yet supported. */ + + return true; +#endif /* __riscv */ +} diff --git a/backends/riscv_regs.c b/backends/riscv_regs.c index 7b577ca0..d5961ad5 100644 --- a/backends/riscv_regs.c +++ b/backends/riscv_regs.c @@ -106,7 +106,7 @@ riscv_register_info (Ebl *ebl, int regno, char *name, size_t namelen, case 26 ... 27: name[0] = 's'; name[1] = '1'; - name[1] = regno - 26 + '0'; + name[2] = regno - 26 + '0'; namelen = 3; break; diff --git a/backends/riscv_symbol.c b/backends/riscv_symbol.c index dce8e358..866a2d7a 100644 --- a/backends/riscv_symbol.c +++ b/backends/riscv_symbol.c @@ -64,13 +64,16 @@ riscv_machine_flag_check (GElf_Word flags) /* Check whether given symbol's st_value and st_size are OK despite failing normal checks. */ bool -riscv_check_special_symbol (Elf *elf, GElf_Ehdr *ehdr, const GElf_Sym *sym, +riscv_check_special_symbol (Elf *elf, const GElf_Sym *sym, const char *name, const GElf_Shdr *destshdr) { if (name == NULL) return false; - const char *sname = elf_strptr (elf, ehdr->e_shstrndx, destshdr->sh_name); + size_t shstrndx; + if (elf_getshdrstrndx (elf, &shstrndx) != 0) + return false; + const char *sname = elf_strptr (elf, shstrndx, destshdr->sh_name); if (sname == NULL) return false; |