~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/arch/x86/tools/relocs.c

Version: ~ [ linux-6.11.5 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.58 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.114 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.169 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.228 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.284 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.322 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.9 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 // SPDX-License-Identifier: GPL-2.0
  2 /* This is included from relocs_32/64.c */
  3 
  4 #define ElfW(type)              _ElfW(ELF_BITS, type)
  5 #define _ElfW(bits, type)       __ElfW(bits, type)
  6 #define __ElfW(bits, type)      Elf##bits##_##type
  7 
  8 #define Elf_Addr                ElfW(Addr)
  9 #define Elf_Ehdr                ElfW(Ehdr)
 10 #define Elf_Phdr                ElfW(Phdr)
 11 #define Elf_Shdr                ElfW(Shdr)
 12 #define Elf_Sym                 ElfW(Sym)
 13 
 14 static Elf_Ehdr                 ehdr;
 15 static unsigned long            shnum;
 16 static unsigned int             shstrndx;
 17 static unsigned int             shsymtabndx;
 18 static unsigned int             shxsymtabndx;
 19 
 20 static int sym_index(Elf_Sym *sym);
 21 
 22 struct relocs {
 23                                 uint32_t        *offset;
 24                                 unsigned long   count;
 25                                 unsigned long   size;
 26 };
 27 
 28 static struct relocs            relocs16;
 29 static struct relocs            relocs32;
 30 
 31 #if ELF_BITS == 64
 32 static struct relocs            relocs32neg;
 33 static struct relocs            relocs64;
 34 # define FMT PRIu64
 35 #else
 36 # define FMT PRIu32
 37 #endif
 38 
 39 struct section {
 40                                 Elf_Shdr       shdr;
 41                                 struct section *link;
 42                                 Elf_Sym        *symtab;
 43                                 Elf32_Word     *xsymtab;
 44                                 Elf_Rel        *reltab;
 45                                 char           *strtab;
 46 };
 47 static struct section           *secs;
 48 
 49 static const char * const       sym_regex_kernel[S_NSYMTYPES] = {
 50 /*
 51  * Following symbols have been audited. There values are constant and do
 52  * not change if bzImage is loaded at a different physical address than
 53  * the address for which it has been compiled. Don't warn user about
 54  * absolute relocations present w.r.t these symbols.
 55  */
 56         [S_ABS] =
 57         "^(xen_irq_disable_direct_reloc$|"
 58         "xen_save_fl_direct_reloc$|"
 59         "VDSO|"
 60         "__kcfi_typeid_|"
 61         "__crc_)",
 62 
 63 /*
 64  * These symbols are known to be relative, even if the linker marks them
 65  * as absolute (typically defined outside any section in the linker script.)
 66  */
 67         [S_REL] =
 68         "^(__init_(begin|end)|"
 69         "__x86_cpu_dev_(start|end)|"
 70         "__alt_instructions(_end)?|"
 71         "(__iommu_table|__apicdrivers|__smp_locks)(_end)?|"
 72         "__(start|end)_pci_.*|"
 73 #if CONFIG_FW_LOADER
 74         "__(start|end)_builtin_fw|"
 75 #endif
 76         "__(start|stop)___ksymtab(_gpl)?|"
 77         "__(start|stop)___kcrctab(_gpl)?|"
 78         "__(start|stop)___param|"
 79         "__(start|stop)___modver|"
 80         "__(start|stop)___bug_table|"
 81         "__tracedata_(start|end)|"
 82         "__(start|stop)_notes|"
 83         "__end_rodata|"
 84         "__end_rodata_aligned|"
 85         "__initramfs_start|"
 86         "(jiffies|jiffies_64)|"
 87 #if ELF_BITS == 64
 88         "__per_cpu_load|"
 89         "init_per_cpu__.*|"
 90         "__end_rodata_hpage_align|"
 91 #endif
 92         "__vvar_page|"
 93         "_end)$"
 94 };
 95 
 96 
 97 static const char * const sym_regex_realmode[S_NSYMTYPES] = {
 98 /*
 99  * These symbols are known to be relative, even if the linker marks them
100  * as absolute (typically defined outside any section in the linker script.)
101  */
102         [S_REL] =
103         "^pa_",
104 
105 /*
106  * These are 16-bit segment symbols when compiling 16-bit code.
107  */
108         [S_SEG] =
109         "^real_mode_seg$",
110 
111 /*
112  * These are offsets belonging to segments, as opposed to linear addresses,
113  * when compiling 16-bit code.
114  */
115         [S_LIN] =
116         "^pa_",
117 };
118 
119 static const char * const       *sym_regex;
120 
121 static regex_t                  sym_regex_c[S_NSYMTYPES];
122 
123 static int is_reloc(enum symtype type, const char *sym_name)
124 {
125         return sym_regex[type] && !regexec(&sym_regex_c[type], sym_name, 0, NULL, 0);
126 }
127 
128 static void regex_init(int use_real_mode)
129 {
130         char errbuf[128];
131         int err;
132         int i;
133 
134         if (use_real_mode)
135                 sym_regex = sym_regex_realmode;
136         else
137                 sym_regex = sym_regex_kernel;
138 
139         for (i = 0; i < S_NSYMTYPES; i++) {
140                 if (!sym_regex[i])
141                         continue;
142 
143                 err = regcomp(&sym_regex_c[i], sym_regex[i], REG_EXTENDED|REG_NOSUB);
144 
145                 if (err) {
146                         regerror(err, &sym_regex_c[i], errbuf, sizeof(errbuf));
147                         die("%s", errbuf);
148                 }
149         }
150 }
151 
152 static const char *sym_type(unsigned type)
153 {
154         static const char *type_name[] = {
155 #define SYM_TYPE(X) [X] = #X
156                 SYM_TYPE(STT_NOTYPE),
157                 SYM_TYPE(STT_OBJECT),
158                 SYM_TYPE(STT_FUNC),
159                 SYM_TYPE(STT_SECTION),
160                 SYM_TYPE(STT_FILE),
161                 SYM_TYPE(STT_COMMON),
162                 SYM_TYPE(STT_TLS),
163 #undef SYM_TYPE
164         };
165         const char *name = "unknown sym type name";
166 
167         if (type < ARRAY_SIZE(type_name))
168                 name = type_name[type];
169 
170         return name;
171 }
172 
173 static const char *sym_bind(unsigned bind)
174 {
175         static const char *bind_name[] = {
176 #define SYM_BIND(X) [X] = #X
177                 SYM_BIND(STB_LOCAL),
178                 SYM_BIND(STB_GLOBAL),
179                 SYM_BIND(STB_WEAK),
180 #undef SYM_BIND
181         };
182         const char *name = "unknown sym bind name";
183 
184         if (bind < ARRAY_SIZE(bind_name))
185                 name = bind_name[bind];
186 
187         return name;
188 }
189 
190 static const char *sym_visibility(unsigned visibility)
191 {
192         static const char *visibility_name[] = {
193 #define SYM_VISIBILITY(X) [X] = #X
194                 SYM_VISIBILITY(STV_DEFAULT),
195                 SYM_VISIBILITY(STV_INTERNAL),
196                 SYM_VISIBILITY(STV_HIDDEN),
197                 SYM_VISIBILITY(STV_PROTECTED),
198 #undef SYM_VISIBILITY
199         };
200         const char *name = "unknown sym visibility name";
201 
202         if (visibility < ARRAY_SIZE(visibility_name))
203                 name = visibility_name[visibility];
204 
205         return name;
206 }
207 
208 static const char *rel_type(unsigned type)
209 {
210         static const char *type_name[] = {
211 #define REL_TYPE(X) [X] = #X
212 #if ELF_BITS == 64
213                 REL_TYPE(R_X86_64_NONE),
214                 REL_TYPE(R_X86_64_64),
215                 REL_TYPE(R_X86_64_PC64),
216                 REL_TYPE(R_X86_64_PC32),
217                 REL_TYPE(R_X86_64_GOT32),
218                 REL_TYPE(R_X86_64_PLT32),
219                 REL_TYPE(R_X86_64_COPY),
220                 REL_TYPE(R_X86_64_GLOB_DAT),
221                 REL_TYPE(R_X86_64_JUMP_SLOT),
222                 REL_TYPE(R_X86_64_RELATIVE),
223                 REL_TYPE(R_X86_64_GOTPCREL),
224                 REL_TYPE(R_X86_64_32),
225                 REL_TYPE(R_X86_64_32S),
226                 REL_TYPE(R_X86_64_16),
227                 REL_TYPE(R_X86_64_PC16),
228                 REL_TYPE(R_X86_64_8),
229                 REL_TYPE(R_X86_64_PC8),
230 #else
231                 REL_TYPE(R_386_NONE),
232                 REL_TYPE(R_386_32),
233                 REL_TYPE(R_386_PC32),
234                 REL_TYPE(R_386_GOT32),
235                 REL_TYPE(R_386_PLT32),
236                 REL_TYPE(R_386_COPY),
237                 REL_TYPE(R_386_GLOB_DAT),
238                 REL_TYPE(R_386_JMP_SLOT),
239                 REL_TYPE(R_386_RELATIVE),
240                 REL_TYPE(R_386_GOTOFF),
241                 REL_TYPE(R_386_GOTPC),
242                 REL_TYPE(R_386_8),
243                 REL_TYPE(R_386_PC8),
244                 REL_TYPE(R_386_16),
245                 REL_TYPE(R_386_PC16),
246 #endif
247 #undef REL_TYPE
248         };
249         const char *name = "unknown type rel type name";
250 
251         if (type < ARRAY_SIZE(type_name) && type_name[type])
252                 name = type_name[type];
253 
254         return name;
255 }
256 
257 static const char *sec_name(unsigned shndx)
258 {
259         const char *sec_strtab;
260         const char *name;
261         sec_strtab = secs[shstrndx].strtab;
262         name = "<noname>";
263 
264         if (shndx < shnum)
265                 name = sec_strtab + secs[shndx].shdr.sh_name;
266         else if (shndx == SHN_ABS)
267                 name = "ABSOLUTE";
268         else if (shndx == SHN_COMMON)
269                 name = "COMMON";
270 
271         return name;
272 }
273 
274 static const char *sym_name(const char *sym_strtab, Elf_Sym *sym)
275 {
276         const char *name;
277         name = "<noname>";
278 
279         if (sym->st_name)
280                 name = sym_strtab + sym->st_name;
281         else
282                 name = sec_name(sym_index(sym));
283 
284         return name;
285 }
286 
287 static Elf_Sym *sym_lookup(const char *symname)
288 {
289         int i;
290 
291         for (i = 0; i < shnum; i++) {
292                 struct section *sec = &secs[i];
293                 long nsyms;
294                 char *strtab;
295                 Elf_Sym *symtab;
296                 Elf_Sym *sym;
297 
298                 if (sec->shdr.sh_type != SHT_SYMTAB)
299                         continue;
300 
301                 nsyms = sec->shdr.sh_size/sizeof(Elf_Sym);
302                 symtab = sec->symtab;
303                 strtab = sec->link->strtab;
304 
305                 for (sym = symtab; --nsyms >= 0; sym++) {
306                         if (!sym->st_name)
307                                 continue;
308                         if (strcmp(symname, strtab + sym->st_name) == 0)
309                                 return sym;
310                 }
311         }
312         return 0;
313 }
314 
315 #if BYTE_ORDER == LITTLE_ENDIAN
316 # define le16_to_cpu(val)       (val)
317 # define le32_to_cpu(val)       (val)
318 # define le64_to_cpu(val)       (val)
319 #endif
320 
321 #if BYTE_ORDER == BIG_ENDIAN
322 # define le16_to_cpu(val)       bswap_16(val)
323 # define le32_to_cpu(val)       bswap_32(val)
324 # define le64_to_cpu(val)       bswap_64(val)
325 #endif
326 
327 static uint16_t elf16_to_cpu(uint16_t val)
328 {
329         return le16_to_cpu(val);
330 }
331 
332 static uint32_t elf32_to_cpu(uint32_t val)
333 {
334         return le32_to_cpu(val);
335 }
336 
337 #define elf_half_to_cpu(x)      elf16_to_cpu(x)
338 #define elf_word_to_cpu(x)      elf32_to_cpu(x)
339 
340 #if ELF_BITS == 64
341 static uint64_t elf64_to_cpu(uint64_t val)
342 {
343         return le64_to_cpu(val);
344 }
345 # define elf_addr_to_cpu(x)     elf64_to_cpu(x)
346 # define elf_off_to_cpu(x)      elf64_to_cpu(x)
347 # define elf_xword_to_cpu(x)    elf64_to_cpu(x)
348 #else
349 # define elf_addr_to_cpu(x)     elf32_to_cpu(x)
350 # define elf_off_to_cpu(x)      elf32_to_cpu(x)
351 # define elf_xword_to_cpu(x)    elf32_to_cpu(x)
352 #endif
353 
354 static int sym_index(Elf_Sym *sym)
355 {
356         Elf_Sym *symtab = secs[shsymtabndx].symtab;
357         Elf32_Word *xsymtab = secs[shxsymtabndx].xsymtab;
358         unsigned long offset;
359         int index;
360 
361         if (sym->st_shndx != SHN_XINDEX)
362                 return sym->st_shndx;
363 
364         /* calculate offset of sym from head of table. */
365         offset = (unsigned long)sym - (unsigned long)symtab;
366         index = offset / sizeof(*sym);
367 
368         return elf32_to_cpu(xsymtab[index]);
369 }
370 
371 static void read_ehdr(FILE *fp)
372 {
373         if (fread(&ehdr, sizeof(ehdr), 1, fp) != 1)
374                 die("Cannot read ELF header: %s\n", strerror(errno));
375         if (memcmp(ehdr.e_ident, ELFMAG, SELFMAG) != 0)
376                 die("No ELF magic\n");
377         if (ehdr.e_ident[EI_CLASS] != ELF_CLASS)
378                 die("Not a %d bit executable\n", ELF_BITS);
379         if (ehdr.e_ident[EI_DATA] != ELFDATA2LSB)
380                 die("Not a LSB ELF executable\n");
381         if (ehdr.e_ident[EI_VERSION] != EV_CURRENT)
382                 die("Unknown ELF version\n");
383 
384         /* Convert the fields to native endian */
385         ehdr.e_type      = elf_half_to_cpu(ehdr.e_type);
386         ehdr.e_machine   = elf_half_to_cpu(ehdr.e_machine);
387         ehdr.e_version   = elf_word_to_cpu(ehdr.e_version);
388         ehdr.e_entry     = elf_addr_to_cpu(ehdr.e_entry);
389         ehdr.e_phoff     = elf_off_to_cpu(ehdr.e_phoff);
390         ehdr.e_shoff     = elf_off_to_cpu(ehdr.e_shoff);
391         ehdr.e_flags     = elf_word_to_cpu(ehdr.e_flags);
392         ehdr.e_ehsize    = elf_half_to_cpu(ehdr.e_ehsize);
393         ehdr.e_phentsize = elf_half_to_cpu(ehdr.e_phentsize);
394         ehdr.e_phnum     = elf_half_to_cpu(ehdr.e_phnum);
395         ehdr.e_shentsize = elf_half_to_cpu(ehdr.e_shentsize);
396         ehdr.e_shnum     = elf_half_to_cpu(ehdr.e_shnum);
397         ehdr.e_shstrndx  = elf_half_to_cpu(ehdr.e_shstrndx);
398 
399         shnum = ehdr.e_shnum;
400         shstrndx = ehdr.e_shstrndx;
401 
402         if ((ehdr.e_type != ET_EXEC) && (ehdr.e_type != ET_DYN))
403                 die("Unsupported ELF header type\n");
404         if (ehdr.e_machine != ELF_MACHINE)
405                 die("Not for %s\n", ELF_MACHINE_NAME);
406         if (ehdr.e_version != EV_CURRENT)
407                 die("Unknown ELF version\n");
408         if (ehdr.e_ehsize != sizeof(Elf_Ehdr))
409                 die("Bad ELF header size\n");
410         if (ehdr.e_phentsize != sizeof(Elf_Phdr))
411                 die("Bad program header entry\n");
412         if (ehdr.e_shentsize != sizeof(Elf_Shdr))
413                 die("Bad section header entry\n");
414 
415 
416         if (shnum == SHN_UNDEF || shstrndx == SHN_XINDEX) {
417                 Elf_Shdr shdr;
418 
419                 if (fseek(fp, ehdr.e_shoff, SEEK_SET) < 0)
420                         die("Seek to %" FMT " failed: %s\n", ehdr.e_shoff, strerror(errno));
421 
422                 if (fread(&shdr, sizeof(shdr), 1, fp) != 1)
423                         die("Cannot read initial ELF section header: %s\n", strerror(errno));
424 
425                 if (shnum == SHN_UNDEF)
426                         shnum = elf_xword_to_cpu(shdr.sh_size);
427 
428                 if (shstrndx == SHN_XINDEX)
429                         shstrndx = elf_word_to_cpu(shdr.sh_link);
430         }
431 
432         if (shstrndx >= shnum)
433                 die("String table index out of bounds\n");
434 }
435 
436 static void read_shdrs(FILE *fp)
437 {
438         int i;
439         Elf_Shdr shdr;
440 
441         secs = calloc(shnum, sizeof(struct section));
442         if (!secs)
443                 die("Unable to allocate %ld section headers\n", shnum);
444 
445         if (fseek(fp, ehdr.e_shoff, SEEK_SET) < 0)
446                 die("Seek to %" FMT " failed: %s\n", ehdr.e_shoff, strerror(errno));
447 
448         for (i = 0; i < shnum; i++) {
449                 struct section *sec = &secs[i];
450 
451                 if (fread(&shdr, sizeof(shdr), 1, fp) != 1)
452                         die("Cannot read ELF section headers %d/%ld: %s\n", i, shnum, strerror(errno));
453 
454                 sec->shdr.sh_name      = elf_word_to_cpu(shdr.sh_name);
455                 sec->shdr.sh_type      = elf_word_to_cpu(shdr.sh_type);
456                 sec->shdr.sh_flags     = elf_xword_to_cpu(shdr.sh_flags);
457                 sec->shdr.sh_addr      = elf_addr_to_cpu(shdr.sh_addr);
458                 sec->shdr.sh_offset    = elf_off_to_cpu(shdr.sh_offset);
459                 sec->shdr.sh_size      = elf_xword_to_cpu(shdr.sh_size);
460                 sec->shdr.sh_link      = elf_word_to_cpu(shdr.sh_link);
461                 sec->shdr.sh_info      = elf_word_to_cpu(shdr.sh_info);
462                 sec->shdr.sh_addralign = elf_xword_to_cpu(shdr.sh_addralign);
463                 sec->shdr.sh_entsize   = elf_xword_to_cpu(shdr.sh_entsize);
464                 if (sec->shdr.sh_link < shnum)
465                         sec->link = &secs[sec->shdr.sh_link];
466         }
467 
468 }
469 
470 static void read_strtabs(FILE *fp)
471 {
472         int i;
473 
474         for (i = 0; i < shnum; i++) {
475                 struct section *sec = &secs[i];
476 
477                 if (sec->shdr.sh_type != SHT_STRTAB)
478                         continue;
479 
480                 sec->strtab = malloc(sec->shdr.sh_size);
481                 if (!sec->strtab)
482                         die("malloc of %" FMT " bytes for strtab failed\n", sec->shdr.sh_size);
483 
484                 if (fseek(fp, sec->shdr.sh_offset, SEEK_SET) < 0)
485                         die("Seek to %" FMT " failed: %s\n", sec->shdr.sh_offset, strerror(errno));
486 
487                 if (fread(sec->strtab, 1, sec->shdr.sh_size, fp) != sec->shdr.sh_size)
488                         die("Cannot read symbol table: %s\n", strerror(errno));
489         }
490 }
491 
492 static void read_symtabs(FILE *fp)
493 {
494         int i, j;
495 
496         for (i = 0; i < shnum; i++) {
497                 struct section *sec = &secs[i];
498                 int num_syms;
499 
500                 switch (sec->shdr.sh_type) {
501                 case SHT_SYMTAB_SHNDX:
502                         sec->xsymtab = malloc(sec->shdr.sh_size);
503                         if (!sec->xsymtab)
504                                 die("malloc of %" FMT " bytes for xsymtab failed\n", sec->shdr.sh_size);
505 
506                         if (fseek(fp, sec->shdr.sh_offset, SEEK_SET) < 0)
507                                 die("Seek to %" FMT " failed: %s\n", sec->shdr.sh_offset, strerror(errno));
508 
509                         if (fread(sec->xsymtab, 1, sec->shdr.sh_size, fp) != sec->shdr.sh_size)
510                                 die("Cannot read extended symbol table: %s\n", strerror(errno));
511 
512                         shxsymtabndx = i;
513                         continue;
514 
515                 case SHT_SYMTAB:
516                         num_syms = sec->shdr.sh_size / sizeof(Elf_Sym);
517 
518                         sec->symtab = malloc(sec->shdr.sh_size);
519                         if (!sec->symtab)
520                                 die("malloc of %" FMT " bytes for symtab failed\n", sec->shdr.sh_size);
521 
522                         if (fseek(fp, sec->shdr.sh_offset, SEEK_SET) < 0)
523                                 die("Seek to %" FMT " failed: %s\n", sec->shdr.sh_offset, strerror(errno));
524 
525                         if (fread(sec->symtab, 1, sec->shdr.sh_size, fp) != sec->shdr.sh_size)
526                                 die("Cannot read symbol table: %s\n", strerror(errno));
527 
528                         for (j = 0; j < num_syms; j++) {
529                                 Elf_Sym *sym = &sec->symtab[j];
530 
531                                 sym->st_name  = elf_word_to_cpu(sym->st_name);
532                                 sym->st_value = elf_addr_to_cpu(sym->st_value);
533                                 sym->st_size  = elf_xword_to_cpu(sym->st_size);
534                                 sym->st_shndx = elf_half_to_cpu(sym->st_shndx);
535                         }
536                         shsymtabndx = i;
537                         continue;
538 
539                 default:
540                         continue;
541                 }
542         }
543 }
544 
545 
546 static void read_relocs(FILE *fp)
547 {
548         int i, j;
549 
550         for (i = 0; i < shnum; i++) {
551                 struct section *sec = &secs[i];
552 
553                 if (sec->shdr.sh_type != SHT_REL_TYPE)
554                         continue;
555 
556                 sec->reltab = malloc(sec->shdr.sh_size);
557                 if (!sec->reltab)
558                         die("malloc of %" FMT " bytes for relocs failed\n", sec->shdr.sh_size);
559 
560                 if (fseek(fp, sec->shdr.sh_offset, SEEK_SET) < 0)
561                         die("Seek to %" FMT " failed: %s\n", sec->shdr.sh_offset, strerror(errno));
562 
563                 if (fread(sec->reltab, 1, sec->shdr.sh_size, fp) != sec->shdr.sh_size)
564                         die("Cannot read symbol table: %s\n", strerror(errno));
565 
566                 for (j = 0; j < sec->shdr.sh_size/sizeof(Elf_Rel); j++) {
567                         Elf_Rel *rel = &sec->reltab[j];
568 
569                         rel->r_offset = elf_addr_to_cpu(rel->r_offset);
570                         rel->r_info   = elf_xword_to_cpu(rel->r_info);
571 #if (SHT_REL_TYPE == SHT_RELA)
572                         rel->r_addend = elf_xword_to_cpu(rel->r_addend);
573 #endif
574                 }
575         }
576 }
577 
578 
579 static void print_absolute_symbols(void)
580 {
581         int i;
582         const char *format;
583 
584         if (ELF_BITS == 64)
585                 format = "%5d %016"PRIx64" %5"PRId64" %10s %10s %12s %s\n";
586         else
587                 format = "%5d %08"PRIx32"  %5"PRId32" %10s %10s %12s %s\n";
588 
589         printf("Absolute symbols\n");
590         printf(" Num:    Value Size  Type       Bind        Visibility  Name\n");
591 
592         for (i = 0; i < shnum; i++) {
593                 struct section *sec = &secs[i];
594                 char *sym_strtab;
595                 int j;
596 
597                 if (sec->shdr.sh_type != SHT_SYMTAB)
598                         continue;
599 
600                 sym_strtab = sec->link->strtab;
601 
602                 for (j = 0; j < sec->shdr.sh_size/sizeof(Elf_Sym); j++) {
603                         Elf_Sym *sym;
604                         const char *name;
605 
606                         sym = &sec->symtab[j];
607                         name = sym_name(sym_strtab, sym);
608 
609                         if (sym->st_shndx != SHN_ABS)
610                                 continue;
611 
612                         printf(format,
613                                 j, sym->st_value, sym->st_size,
614                                 sym_type(ELF_ST_TYPE(sym->st_info)),
615                                 sym_bind(ELF_ST_BIND(sym->st_info)),
616                                 sym_visibility(ELF_ST_VISIBILITY(sym->st_other)),
617                                 name);
618                 }
619         }
620         printf("\n");
621 }
622 
623 static void print_absolute_relocs(void)
624 {
625         int i, printed = 0;
626         const char *format;
627 
628         if (ELF_BITS == 64)
629                 format = "%016"PRIx64" %016"PRIx64" %10s %016"PRIx64"  %s\n";
630         else
631                 format = "%08"PRIx32" %08"PRIx32" %10s %08"PRIx32"  %s\n";
632 
633         for (i = 0; i < shnum; i++) {
634                 struct section *sec = &secs[i];
635                 struct section *sec_applies, *sec_symtab;
636                 char *sym_strtab;
637                 Elf_Sym *sh_symtab;
638                 int j;
639 
640                 if (sec->shdr.sh_type != SHT_REL_TYPE)
641                         continue;
642 
643                 sec_symtab  = sec->link;
644                 sec_applies = &secs[sec->shdr.sh_info];
645                 if (!(sec_applies->shdr.sh_flags & SHF_ALLOC))
646                         continue;
647 
648                 /*
649                  * Do not perform relocations in .notes section; any
650                  * values there are meant for pre-boot consumption (e.g.
651                  * startup_xen).
652                  */
653                 if (sec_applies->shdr.sh_type == SHT_NOTE)
654                         continue;
655 
656                 sh_symtab  = sec_symtab->symtab;
657                 sym_strtab = sec_symtab->link->strtab;
658 
659                 for (j = 0; j < sec->shdr.sh_size/sizeof(Elf_Rel); j++) {
660                         Elf_Rel *rel;
661                         Elf_Sym *sym;
662                         const char *name;
663 
664                         rel = &sec->reltab[j];
665                         sym = &sh_symtab[ELF_R_SYM(rel->r_info)];
666                         name = sym_name(sym_strtab, sym);
667 
668                         if (sym->st_shndx != SHN_ABS)
669                                 continue;
670 
671                         /* Absolute symbols are not relocated if bzImage is
672                          * loaded at a non-compiled address. Display a warning
673                          * to user at compile time about the absolute
674                          * relocations present.
675                          *
676                          * User need to audit the code to make sure
677                          * some symbols which should have been section
678                          * relative have not become absolute because of some
679                          * linker optimization or wrong programming usage.
680                          *
681                          * Before warning check if this absolute symbol
682                          * relocation is harmless.
683                          */
684                         if (is_reloc(S_ABS, name) || is_reloc(S_REL, name))
685                                 continue;
686 
687                         if (!printed) {
688                                 printf("WARNING: Absolute relocations present\n");
689                                 printf("Offset     Info     Type     Sym.Value Sym.Name\n");
690                                 printed = 1;
691                         }
692 
693                         printf(format,
694                                 rel->r_offset,
695                                 rel->r_info,
696                                 rel_type(ELF_R_TYPE(rel->r_info)),
697                                 sym->st_value,
698                                 name);
699                 }
700         }
701 
702         if (printed)
703                 printf("\n");
704 }
705 
706 static void add_reloc(struct relocs *r, uint32_t offset)
707 {
708         if (r->count == r->size) {
709                 unsigned long newsize = r->size + 50000;
710                 void *mem = realloc(r->offset, newsize * sizeof(r->offset[0]));
711 
712                 if (!mem)
713                         die("realloc of %ld entries for relocs failed\n", newsize);
714 
715                 r->offset = mem;
716                 r->size = newsize;
717         }
718         r->offset[r->count++] = offset;
719 }
720 
721 static void walk_relocs(int (*process)(struct section *sec, Elf_Rel *rel,
722                         Elf_Sym *sym, const char *symname))
723 {
724         int i;
725 
726         /* Walk through the relocations */
727         for (i = 0; i < shnum; i++) {
728                 char *sym_strtab;
729                 Elf_Sym *sh_symtab;
730                 struct section *sec_applies, *sec_symtab;
731                 int j;
732                 struct section *sec = &secs[i];
733 
734                 if (sec->shdr.sh_type != SHT_REL_TYPE)
735                         continue;
736 
737                 sec_symtab  = sec->link;
738                 sec_applies = &secs[sec->shdr.sh_info];
739                 if (!(sec_applies->shdr.sh_flags & SHF_ALLOC))
740                         continue;
741 
742                 /*
743                  * Do not perform relocations in .notes sections; any
744                  * values there are meant for pre-boot consumption (e.g.
745                  * startup_xen).
746                  */
747                 if (sec_applies->shdr.sh_type == SHT_NOTE)
748                         continue;
749 
750                 sh_symtab = sec_symtab->symtab;
751                 sym_strtab = sec_symtab->link->strtab;
752 
753                 for (j = 0; j < sec->shdr.sh_size/sizeof(Elf_Rel); j++) {
754                         Elf_Rel *rel = &sec->reltab[j];
755                         Elf_Sym *sym = &sh_symtab[ELF_R_SYM(rel->r_info)];
756                         const char *symname = sym_name(sym_strtab, sym);
757 
758                         process(sec, rel, sym, symname);
759                 }
760         }
761 }
762 
763 /*
764  * The .data..percpu section is a special case for x86_64 SMP kernels.
765  * It is used to initialize the actual per_cpu areas and to provide
766  * definitions for the per_cpu variables that correspond to their offsets
767  * within the percpu area. Since the values of all of the symbols need
768  * to be offsets from the start of the per_cpu area the virtual address
769  * (sh_addr) of .data..percpu is 0 in SMP kernels.
770  *
771  * This means that:
772  *
773  *      Relocations that reference symbols in the per_cpu area do not
774  *      need further relocation (since the value is an offset relative
775  *      to the start of the per_cpu area that does not change).
776  *
777  *      Relocations that apply to the per_cpu area need to have their
778  *      offset adjusted by by the value of __per_cpu_load to make them
779  *      point to the correct place in the loaded image (because the
780  *      virtual address of .data..percpu is 0).
781  *
782  * For non SMP kernels .data..percpu is linked as part of the normal
783  * kernel data and does not require special treatment.
784  *
785  */
786 static int per_cpu_shndx = -1;
787 static Elf_Addr per_cpu_load_addr;
788 
789 static void percpu_init(void)
790 {
791         int i;
792 
793         for (i = 0; i < shnum; i++) {
794                 ElfW(Sym) *sym;
795 
796                 if (strcmp(sec_name(i), ".data..percpu"))
797                         continue;
798 
799                 if (secs[i].shdr.sh_addr != 0)  /* non SMP kernel */
800                         return;
801 
802                 sym = sym_lookup("__per_cpu_load");
803                 if (!sym)
804                         die("can't find __per_cpu_load\n");
805 
806                 per_cpu_shndx = i;
807                 per_cpu_load_addr = sym->st_value;
808 
809                 return;
810         }
811 }
812 
813 #if ELF_BITS == 64
814 
815 /*
816  * Check to see if a symbol lies in the .data..percpu section.
817  *
818  * The linker incorrectly associates some symbols with the
819  * .data..percpu section so we also need to check the symbol
820  * name to make sure that we classify the symbol correctly.
821  *
822  * The GNU linker incorrectly associates:
823  *      __init_begin
824  *      __per_cpu_load
825  *
826  * The "gold" linker incorrectly associates:
827  *      init_per_cpu__fixed_percpu_data
828  *      init_per_cpu__gdt_page
829  */
830 static int is_percpu_sym(ElfW(Sym) *sym, const char *symname)
831 {
832         int shndx = sym_index(sym);
833 
834         return (shndx == per_cpu_shndx) &&
835                 strcmp(symname, "__init_begin") &&
836                 strcmp(symname, "__per_cpu_load") &&
837                 strncmp(symname, "init_per_cpu_", 13);
838 }
839 
840 
841 static int do_reloc64(struct section *sec, Elf_Rel *rel, ElfW(Sym) *sym,
842                       const char *symname)
843 {
844         unsigned r_type = ELF64_R_TYPE(rel->r_info);
845         ElfW(Addr) offset = rel->r_offset;
846         int shn_abs = (sym->st_shndx == SHN_ABS) && !is_reloc(S_REL, symname);
847 
848         if (sym->st_shndx == SHN_UNDEF)
849                 return 0;
850 
851         /*
852          * Adjust the offset if this reloc applies to the percpu section.
853          */
854         if (sec->shdr.sh_info == per_cpu_shndx)
855                 offset += per_cpu_load_addr;
856 
857         switch (r_type) {
858         case R_X86_64_NONE:
859                 /* NONE can be ignored. */
860                 break;
861 
862         case R_X86_64_PC32:
863         case R_X86_64_PLT32:
864                 /*
865                  * PC relative relocations don't need to be adjusted unless
866                  * referencing a percpu symbol.
867                  *
868                  * NB: R_X86_64_PLT32 can be treated as R_X86_64_PC32.
869                  */
870                 if (is_percpu_sym(sym, symname))
871                         add_reloc(&relocs32neg, offset);
872                 break;
873 
874         case R_X86_64_PC64:
875                 /*
876                  * Only used by jump labels
877                  */
878                 if (is_percpu_sym(sym, symname))
879                         die("Invalid R_X86_64_PC64 relocation against per-CPU symbol %s\n", symname);
880                 break;
881 
882         case R_X86_64_32:
883         case R_X86_64_32S:
884         case R_X86_64_64:
885                 /*
886                  * References to the percpu area don't need to be adjusted.
887                  */
888                 if (is_percpu_sym(sym, symname))
889                         break;
890 
891                 if (shn_abs) {
892                         /*
893                          * Whitelisted absolute symbols do not require
894                          * relocation.
895                          */
896                         if (is_reloc(S_ABS, symname))
897                                 break;
898 
899                         die("Invalid absolute %s relocation: %s\n", rel_type(r_type), symname);
900                         break;
901                 }
902 
903                 /*
904                  * Relocation offsets for 64 bit kernels are output
905                  * as 32 bits and sign extended back to 64 bits when
906                  * the relocations are processed.
907                  * Make sure that the offset will fit.
908                  */
909                 if ((int32_t)offset != (int64_t)offset)
910                         die("Relocation offset doesn't fit in 32 bits\n");
911 
912                 if (r_type == R_X86_64_64)
913                         add_reloc(&relocs64, offset);
914                 else
915                         add_reloc(&relocs32, offset);
916                 break;
917 
918         default:
919                 die("Unsupported relocation type: %s (%d)\n", rel_type(r_type), r_type);
920                 break;
921         }
922 
923         return 0;
924 }
925 
926 #else
927 
928 static int do_reloc32(struct section *sec, Elf_Rel *rel, Elf_Sym *sym,
929                       const char *symname)
930 {
931         unsigned r_type = ELF32_R_TYPE(rel->r_info);
932         int shn_abs = (sym->st_shndx == SHN_ABS) && !is_reloc(S_REL, symname);
933 
934         switch (r_type) {
935         case R_386_NONE:
936         case R_386_PC32:
937         case R_386_PC16:
938         case R_386_PC8:
939         case R_386_PLT32:
940                 /*
941                  * NONE can be ignored and PC relative relocations don't need
942                  * to be adjusted. Because sym must be defined, R_386_PLT32 can
943                  * be treated the same way as R_386_PC32.
944                  */
945                 break;
946 
947         case R_386_32:
948                 if (shn_abs) {
949                         /*
950                          * Whitelisted absolute symbols do not require
951                          * relocation.
952                          */
953                         if (is_reloc(S_ABS, symname))
954                                 break;
955 
956                         die("Invalid absolute %s relocation: %s\n", rel_type(r_type), symname);
957                         break;
958                 }
959 
960                 add_reloc(&relocs32, rel->r_offset);
961                 break;
962 
963         default:
964                 die("Unsupported relocation type: %s (%d)\n", rel_type(r_type), r_type);
965                 break;
966         }
967 
968         return 0;
969 }
970 
971 static int do_reloc_real(struct section *sec, Elf_Rel *rel, Elf_Sym *sym, const char *symname)
972 {
973         unsigned r_type = ELF32_R_TYPE(rel->r_info);
974         int shn_abs = (sym->st_shndx == SHN_ABS) && !is_reloc(S_REL, symname);
975 
976         switch (r_type) {
977         case R_386_NONE:
978         case R_386_PC32:
979         case R_386_PC16:
980         case R_386_PC8:
981         case R_386_PLT32:
982                 /*
983                  * NONE can be ignored and PC relative relocations don't need
984                  * to be adjusted. Because sym must be defined, R_386_PLT32 can
985                  * be treated the same way as R_386_PC32.
986                  */
987                 break;
988 
989         case R_386_16:
990                 if (shn_abs) {
991                         /*
992                          * Whitelisted absolute symbols do not require
993                          * relocation.
994                          */
995                         if (is_reloc(S_ABS, symname))
996                                 break;
997 
998                         if (is_reloc(S_SEG, symname)) {
999                                 add_reloc(&relocs16, rel->r_offset);
1000                                 break;
1001                         }
1002                 } else {
1003                         if (!is_reloc(S_LIN, symname))
1004                                 break;
1005                 }
1006                 die("Invalid %s %s relocation: %s\n", shn_abs ? "absolute" : "relative", rel_type(r_type), symname);
1007                 break;
1008 
1009         case R_386_32:
1010                 if (shn_abs) {
1011                         /*
1012                          * Whitelisted absolute symbols do not require
1013                          * relocation.
1014                          */
1015                         if (is_reloc(S_ABS, symname))
1016                                 break;
1017 
1018                         if (is_reloc(S_REL, symname)) {
1019                                 add_reloc(&relocs32, rel->r_offset);
1020                                 break;
1021                         }
1022                 } else {
1023                         if (is_reloc(S_LIN, symname))
1024                                 add_reloc(&relocs32, rel->r_offset);
1025                         break;
1026                 }
1027                 die("Invalid %s %s relocation: %s\n", shn_abs ? "absolute" : "relative", rel_type(r_type), symname);
1028                 break;
1029 
1030         default:
1031                 die("Unsupported relocation type: %s (%d)\n", rel_type(r_type), r_type);
1032                 break;
1033         }
1034 
1035         return 0;
1036 }
1037 
1038 #endif
1039 
1040 static int cmp_relocs(const void *va, const void *vb)
1041 {
1042         const uint32_t *a, *b;
1043 
1044         a = va;
1045         b = vb;
1046 
1047         return (*a == *b)? 0 : (*a > *b)? 1 : -1;
1048 }
1049 
1050 static void sort_relocs(struct relocs *r)
1051 {
1052         qsort(r->offset, r->count, sizeof(r->offset[0]), cmp_relocs);
1053 }
1054 
1055 static int write32(uint32_t v, FILE *f)
1056 {
1057         unsigned char buf[4];
1058 
1059         put_unaligned_le32(v, buf);
1060 
1061         return fwrite(buf, 1, 4, f) == 4 ? 0 : -1;
1062 }
1063 
1064 static int write32_as_text(uint32_t v, FILE *f)
1065 {
1066         return fprintf(f, "\t.long 0x%08"PRIx32"\n", v) > 0 ? 0 : -1;
1067 }
1068 
1069 static void emit_relocs(int as_text, int use_real_mode)
1070 {
1071         int i;
1072         int (*write_reloc)(uint32_t, FILE *) = write32;
1073         int (*do_reloc)(struct section *sec, Elf_Rel *rel, Elf_Sym *sym, const char *symname);
1074 
1075 #if ELF_BITS == 64
1076         if (!use_real_mode)
1077                 do_reloc = do_reloc64;
1078         else
1079                 die("--realmode not valid for a 64-bit ELF file");
1080 #else
1081         if (!use_real_mode)
1082                 do_reloc = do_reloc32;
1083         else
1084                 do_reloc = do_reloc_real;
1085 #endif
1086 
1087         /* Collect up the relocations */
1088         walk_relocs(do_reloc);
1089 
1090         if (relocs16.count && !use_real_mode)
1091                 die("Segment relocations found but --realmode not specified\n");
1092 
1093         /* Order the relocations for more efficient processing */
1094         sort_relocs(&relocs32);
1095 #if ELF_BITS == 64
1096         sort_relocs(&relocs32neg);
1097         sort_relocs(&relocs64);
1098 #else
1099         sort_relocs(&relocs16);
1100 #endif
1101 
1102         /* Print the relocations */
1103         if (as_text) {
1104                 /* Print the relocations in a form suitable that
1105                  * gas will like.
1106                  */
1107                 printf(".section \".data.reloc\",\"a\"\n");
1108                 printf(".balign 4\n");
1109                 write_reloc = write32_as_text;
1110         }
1111 
1112         if (use_real_mode) {
1113                 write_reloc(relocs16.count, stdout);
1114                 for (i = 0; i < relocs16.count; i++)
1115                         write_reloc(relocs16.offset[i], stdout);
1116 
1117                 write_reloc(relocs32.count, stdout);
1118                 for (i = 0; i < relocs32.count; i++)
1119                         write_reloc(relocs32.offset[i], stdout);
1120         } else {
1121 #if ELF_BITS == 64
1122                 /* Print a stop */
1123                 write_reloc(0, stdout);
1124 
1125                 /* Now print each relocation */
1126                 for (i = 0; i < relocs64.count; i++)
1127                         write_reloc(relocs64.offset[i], stdout);
1128 
1129                 /* Print a stop */
1130                 write_reloc(0, stdout);
1131 
1132                 /* Now print each inverse 32-bit relocation */
1133                 for (i = 0; i < relocs32neg.count; i++)
1134                         write_reloc(relocs32neg.offset[i], stdout);
1135 #endif
1136 
1137                 /* Print a stop */
1138                 write_reloc(0, stdout);
1139 
1140                 /* Now print each relocation */
1141                 for (i = 0; i < relocs32.count; i++)
1142                         write_reloc(relocs32.offset[i], stdout);
1143         }
1144 }
1145 
1146 /*
1147  * As an aid to debugging problems with different linkers
1148  * print summary information about the relocs.
1149  * Since different linkers tend to emit the sections in
1150  * different orders we use the section names in the output.
1151  */
1152 static int do_reloc_info(struct section *sec, Elf_Rel *rel, ElfW(Sym) *sym,
1153                                 const char *symname)
1154 {
1155         printf("%s\t%s\t%s\t%s\n",
1156                 sec_name(sec->shdr.sh_info),
1157                 rel_type(ELF_R_TYPE(rel->r_info)),
1158                 symname,
1159                 sec_name(sym_index(sym)));
1160 
1161         return 0;
1162 }
1163 
1164 static void print_reloc_info(void)
1165 {
1166         printf("reloc section\treloc type\tsymbol\tsymbol section\n");
1167         walk_relocs(do_reloc_info);
1168 }
1169 
1170 #if ELF_BITS == 64
1171 # define process process_64
1172 #else
1173 # define process process_32
1174 #endif
1175 
1176 void process(FILE *fp, int use_real_mode, int as_text,
1177              int show_absolute_syms, int show_absolute_relocs,
1178              int show_reloc_info)
1179 {
1180         regex_init(use_real_mode);
1181         read_ehdr(fp);
1182         read_shdrs(fp);
1183         read_strtabs(fp);
1184         read_symtabs(fp);
1185         read_relocs(fp);
1186 
1187         if (ELF_BITS == 64)
1188                 percpu_init();
1189 
1190         if (show_absolute_syms) {
1191                 print_absolute_symbols();
1192                 return;
1193         }
1194 
1195         if (show_absolute_relocs) {
1196                 print_absolute_relocs();
1197                 return;
1198         }
1199 
1200         if (show_reloc_info) {
1201                 print_reloc_info();
1202                 return;
1203         }
1204 
1205         emit_relocs(as_text, use_real_mode);
1206 }
1207 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php