Branch data Line data Source code
1 : : /* AArch64 specific symbolic name handling. 2 : : Copyright (C) 2013, 2015, 2017 Red Hat, Inc. 3 : : This file is part of elfutils. 4 : : 5 : : This file is free software; you can redistribute it and/or modify 6 : : it under the terms of either 7 : : 8 : : * the GNU Lesser General Public License as published by the Free 9 : : Software Foundation; either version 3 of the License, or (at 10 : : your option) any later version 11 : : 12 : : or 13 : : 14 : : * the GNU General Public License as published by the Free 15 : : Software Foundation; either version 2 of the License, or (at 16 : : your option) any later version 17 : : 18 : : or both in parallel, as here. 19 : : 20 : : elfutils is distributed in the hope that it will be useful, but 21 : : WITHOUT ANY WARRANTY; without even the implied warranty of 22 : : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 23 : : General Public License for more details. 24 : : 25 : : You should have received copies of the GNU General Public License and 26 : : the GNU Lesser General Public License along with this program. If 27 : : not, see <http://www.gnu.org/licenses/>. */ 28 : : 29 : : #ifdef HAVE_CONFIG_H 30 : : # include <config.h> 31 : : #endif 32 : : 33 : : #include <system.h> 34 : : 35 : : #include <elf.h> 36 : : #include <stddef.h> 37 : : #include <string.h> 38 : : 39 : : #define BACKEND aarch64_ 40 : : #include "libebl_CPU.h" 41 : : 42 : : 43 : : /* Check for the simple reloc types. */ 44 : : Elf_Type 45 : 2192 : aarch64_reloc_simple_type (Ebl *ebl __attribute__ ((unused)), int type, 46 : : int *addsub __attribute__ ((unused))) 47 : : { 48 [ + + ]: 2192 : switch (type) 49 : : { 50 : : case R_AARCH64_ABS64: 51 : : return ELF_T_XWORD; 52 : : case R_AARCH64_ABS32: 53 : : return ELF_T_WORD; 54 : : case R_AARCH64_ABS16: 55 : : return ELF_T_HALF; 56 : : 57 : : default: 58 : : return ELF_T_NUM; 59 : : } 60 : : } 61 : : 62 : : /* If this is the _GLOBAL_OFFSET_TABLE_ symbol, then it should point in 63 : : the .got even if there is a .got.plt section. 64 : : https://sourceware.org/ml/libc-ports/2013-06/msg00057.html 65 : : https://bugzilla.redhat.com/show_bug.cgi?id=1201778 66 : : */ 67 : : bool 68 : 0 : aarch64_check_special_symbol (Elf *elf, const GElf_Sym *sym, 69 : : const char *name, const GElf_Shdr *destshdr) 70 : : { 71 [ # # ]: 0 : if (name != NULL 72 [ # # ]: 0 : && strcmp (name, "_GLOBAL_OFFSET_TABLE_") == 0) 73 : : { 74 : 0 : size_t shstrndx; 75 [ # # ]: 0 : if (elf_getshdrstrndx (elf, &shstrndx) != 0) 76 : 0 : return false; 77 : 0 : const char *sname = elf_strptr (elf, shstrndx, destshdr->sh_name); 78 [ # # ]: 0 : if (sname != NULL 79 [ # # # # ]: 0 : && (strcmp (sname, ".got") == 0 || strcmp (sname, ".got.plt") == 0)) 80 : : { 81 : : Elf_Scn *scn = NULL; 82 [ # # ]: 0 : while ((scn = elf_nextscn (elf, scn)) != NULL) 83 : : { 84 : 0 : GElf_Shdr shdr_mem; 85 : 0 : GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem); 86 [ # # ]: 0 : if (shdr != NULL) 87 : : { 88 : 0 : sname = elf_strptr (elf, shstrndx, shdr->sh_name); 89 [ # # # # ]: 0 : if (sname != NULL && strcmp (sname, ".got") == 0) 90 : 0 : return (sym->st_value >= shdr->sh_addr 91 [ # # # # ]: 0 : && sym->st_value < shdr->sh_addr + shdr->sh_size); 92 : : } 93 : : } 94 : : } 95 : : } 96 : : 97 : : return false; 98 : : } 99 : : 100 : : /* A data mapping symbol is a symbol with "$d" name or "$d.<any...>" name, 101 : : STT_NOTYPE, STB_LOCAL and st_size of zero. The indicate the stat of a 102 : : sequence of data items. */ 103 : : bool 104 : 4 : aarch64_data_marker_symbol (const GElf_Sym *sym, const char *sname) 105 : : { 106 : 4 : return (sym != NULL && sname != NULL 107 [ + - + - ]: 4 : && sym->st_size == 0 && GELF_ST_BIND (sym->st_info) == STB_LOCAL 108 [ + - ]: 4 : && GELF_ST_TYPE (sym->st_info) == STT_NOTYPE 109 [ + - - + : 8 : && (strcmp (sname, "$d") == 0 || startswith (sname, "$d."))); - - ] 110 : : } 111 : : 112 : : const char * 113 : 0 : aarch64_dynamic_tag_name (int64_t tag, char *buf __attribute__ ((unused)), 114 : : size_t len __attribute__ ((unused))) 115 : : { 116 [ # # # # ]: 0 : switch (tag) 117 : : { 118 : : case DT_AARCH64_BTI_PLT: 119 : : return "AARCH64_BTI_PLT"; 120 : 0 : case DT_AARCH64_PAC_PLT: 121 : 0 : return "AARCH64_PAC_PLT"; 122 : 0 : case DT_AARCH64_VARIANT_PCS: 123 : 0 : return "AARCH64_VARIANT_PCS"; 124 : : default: 125 : 0 : break; 126 : : } 127 : 0 : return NULL; 128 : : } 129 : : 130 : : bool 131 : 0 : aarch64_dynamic_tag_check (int64_t tag) 132 : : { 133 : 0 : return (tag == DT_AARCH64_BTI_PLT 134 [ # # ]: 0 : || tag == DT_AARCH64_PAC_PLT 135 : 0 : || tag == DT_AARCH64_VARIANT_PCS); 136 : : }