1 /* Copyright (C) 2021 Free Software Foundation, Inc.
2 Contributed by Oracle.
3
4 This file is part of GNU Binutils.
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 3, or (at your option)
9 any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, 51 Franklin Street - Fifth Floor, Boston,
19 MA 02110-1301, USA. */
20
21 #include "config.h"
22 #include <unistd.h>
23
24 #include "util.h"
25 #include "bfd.h"
26 #include "elf-bfd.h"
27 #include "Elf.h"
28 #include "Map.h"
29 #include "StringBuilder.h"
30 #include "DbeFile.h"
31
32 typedef uint32_t Elf32_Word;
33 typedef uint32_t Elf64_Word;
34 typedef uint32_t Elf32_Addr;
35 typedef uint64_t Elf64_Addr;
36 typedef uint64_t Elf64_Xword;
37 typedef int32_t Elf32_Sword;
38 typedef int64_t Elf64_Sxword;
39 typedef uint16_t Elf32_Half;
40 typedef uint16_t Elf64_Half;
41
42 // Ancillary entry
43 typedef struct
44 {
45 Elf32_Word a_tag; /* how to interpret value */
46 union
47 {
48 Elf32_Word a_val;
49 Elf32_Addr a_ptr;
50 } a_un;
51 } Elf32_Ancillary;
52
53 struct S_Elf64_Ancillary
54 {
55 Elf64_Xword a_tag; /* how to interpret value */
56 union
57 {
58 Elf64_Xword a_val;
59 Elf64_Addr a_ptr;
60 } a_un;
61 };
62
63 /* Dynamic section entry. */
64 typedef struct
65 {
66 Elf32_Sword d_tag; /* Dynamic entry type */
67
68 union
69 {
70 Elf32_Word d_val; /* Integer value */
71 Elf32_Addr d_ptr; /* Address value */
72 } d_un;
73 } Elf32_Dyn;
74
75 struct S_Elf64_Dyn
76 {
77 Elf64_Sxword d_tag; /* Dynamic entry type */
78
79 union
80 {
81 Elf64_Xword d_val; /* Integer value */
82 Elf64_Addr d_ptr; /* Address value */
83 } d_un;
84 };
85
86
87 // Symbol table
88 typedef struct
89 {
90 Elf32_Word st_name;
91 Elf32_Addr st_value;
92 Elf32_Word st_size;
93 unsigned char st_info; /* bind, type: ELF_32_ST_... */
94 unsigned char st_other;
95 Elf32_Half st_shndx; /* SHN_... */
96 } Elf32_Sym;
97
98 typedef struct
99 {
100 Elf64_Word st_name;
101 unsigned char st_info; /* bind, type: ELF_64_ST_... */
102 unsigned char st_other;
103 Elf64_Half st_shndx; /* SHN_... */
104 Elf64_Addr st_value;
105 Elf64_Xword st_size;
106 } Elf64_Sym;
107
108
109 // Relocation
110 typedef struct
111 {
112 Elf32_Addr r_offset;
113 Elf32_Word r_info; /* sym, type: ELF32_R_... */
114 } Elf32_Rel;
115
116 typedef struct
117 {
118 Elf32_Addr r_offset;
119 Elf32_Word r_info; /* sym, type: ELF32_R_... */
120 Elf32_Sword r_addend;
121 } Elf32_Rela;
122
123 typedef struct
124 {
125 Elf64_Addr r_offset;
126 Elf64_Xword r_info; /* sym, type: ELF64_R_... */
127 } Elf64_Rel;
128
129 typedef struct
130 {
131 Elf64_Addr r_offset;
132 Elf64_Xword r_info; /* sym, type: ELF64_R_... */
133 Elf64_Sxword r_addend;
134 } Elf64_Rela;
135
136 int Elf::bfd_status = -1;
137
138 void
elf_init()139 Elf::elf_init ()
140 {
141 if (bfd_status == -1)
142 bfd_status = bfd_init ();
143 }
144
Elf(char * filename)145 Elf::Elf (char *filename) : DbeMessages (), Data_window (filename)
146 {
147 ehdrp = NULL;
148 data = NULL;
149 ancillary_files = NULL;
150 elfSymbols = NULL;
151 gnu_debug_file = NULL;
152 dbeFile = NULL;
153 abfd = NULL;
154 if (bfd_status != BFD_INIT_MAGIC)
155 {
156 status = ELF_ERR_CANT_OPEN_FILE;
157 return;
158 }
159 abfd = bfd_openr (filename, NULL);
160 if (abfd == NULL)
161 {
162 status = ELF_ERR_CANT_OPEN_FILE;
163 return;
164 }
165 if (!bfd_check_format (abfd, bfd_object))
166 {
167 bfd_close (abfd);
168 abfd = NULL;
169 status = ELF_ERR_CANT_OPEN_FILE;
170 return;
171 }
172 ehdrp = elf_getehdr ();
173 if (ehdrp == NULL)
174 {
175 bfd_close (abfd);
176 abfd = NULL;
177 status = ELF_ERR_BAD_ELF_FORMAT;
178 return;
179 }
180 elf_class = ehdrp->e_ident[EI_CLASS];
181 elf_datatype = ehdrp->e_ident[EI_DATA];
182
183 if (not_opened ())
184 {
185 status = ELF_ERR_CANT_OPEN_FILE;
186 return;
187 }
188 status = ELF_ERR_NONE;
189
190 #if ARCH(SPARC)
191 need_swap_endian = is_Intel ();
192 #else
193 need_swap_endian = !is_Intel ();
194 #endif
195
196 analyzerInfo = 0;
197 SUNW_ldynsym = 0;
198 gnuLink = 0;
199 stab = 0;
200 stabStr = 0;
201 stabIndex = 0;
202 stabIndexStr = 0;
203 stabExcl = 0;
204 stabExclStr = 0;
205 symtab = 0;
206 dynsym = 0;
207 info = 0;
208 plt = 0;
209 dwarf = false;
210
211 for (unsigned int sec = 1; sec < elf_getehdr ()->e_shnum; sec++)
212 {
213 char *name = get_sec_name (sec);
214 if (name == NULL)
215 continue;
216 if (streq (name, NTXT (".stab")))
217 stab = sec;
218 else if (streq (name, NTXT (".stabstr")))
219 stabStr = sec;
220 else if (streq (name, NTXT (".stab.index")))
221 stabIndex = sec;
222 else if (streq (name, NTXT (".stab.indexstr")))
223 stabIndexStr = sec;
224 else if (streq (name, NTXT (".stab.excl")))
225 stabExcl = sec;
226 else if (streq (name, NTXT (".stab.exclstr")))
227 stabExclStr = sec;
228 else if (streq (name, NTXT (".gnu_debuglink")))
229 gnuLink = sec;
230 else if (streq (name, NTXT (".__analyzer_info")))
231 analyzerInfo = sec;
232 else if (streq (name, NTXT (".info")))
233 info = true;
234 else if (streq (name, NTXT (".plt")))
235 plt = sec;
236 else if (streq (name, NTXT (".SUNW_ldynsym")))
237 SUNW_ldynsym = sec;
238 else if (streq (name, NTXT (".dynsym")))
239 dynsym = sec;
240 else if (streq (name, NTXT (".symtab")))
241 symtab = sec;
242 else if (strncmp (name, NTXT (".debug"), 6) == 0)
243 dwarf = true;
244 }
245 if (fd != -1)
246 {
247 close (fd);
248 fd = -1;
249 }
250 }
251
~Elf()252 Elf::~Elf ()
253 {
254 if (data)
255 {
256 for (int i = 0; i < (int) ehdrp->e_shnum; i++)
257 {
258 Elf_Data *p = data[i];
259 if (p && !mmap_on_file && (p->d_flags & SHF_SUNW_ABSENT) == 0)
260 free (p->d_buf);
261 delete p;
262 }
263 free (data);
264 }
265 if (ancillary_files)
266 {
267 ancillary_files->destroy ();
268 delete ancillary_files;
269 }
270 delete elfSymbols;
271 delete gnu_debug_file;
272 delete dbeFile;
273 if (abfd)
274 bfd_close (abfd);
275 }
276
277 Elf_Internal_Ehdr *
elf_getehdr()278 Elf::elf_getehdr ()
279 {
280 if (ehdrp == NULL && abfd)
281 ehdrp = elf_elfheader (abfd);
282 return ehdrp;
283 }
284
285 Elf_Internal_Phdr *
get_phdr(unsigned int ndx)286 Elf::get_phdr (unsigned int ndx)
287 {
288 if (ehdrp == NULL || ndx >= ehdrp->e_phnum)
289 return NULL;
290 return &(elf_tdata (abfd)->phdr[ndx]);
291 }
292
293 Elf_Internal_Shdr *
get_shdr(unsigned int ndx)294 Elf::get_shdr (unsigned int ndx)
295 {
296 if (ehdrp == NULL || ndx >= ehdrp->e_shnum)
297 return NULL;
298 return elf_elfsections (abfd)[ndx];
299 }
300
301 Elf64_Dyn *
elf_getdyn(Elf_Internal_Phdr * phdr,unsigned int ndx,Elf64_Dyn * pdyn)302 Elf::elf_getdyn (Elf_Internal_Phdr *phdr, unsigned int ndx, Elf64_Dyn *pdyn)
303 {
304 if (elf_getclass () == ELFCLASS32)
305 {
306 if (ndx * sizeof (Elf32_Dyn) >= phdr->p_filesz)
307 return NULL;
308 Elf32_Dyn *hdr = (Elf32_Dyn*) bind (phdr->p_offset + ndx * sizeof (Elf32_Dyn),
309 sizeof (Elf32_Dyn));
310 if (hdr == NULL)
311 return NULL;
312 pdyn->d_tag = decode (hdr->d_tag);
313 pdyn->d_un.d_val = decode (hdr->d_un.d_val);
314 }
315 else
316 {
317 if (ndx * sizeof (Elf64_Dyn) >= phdr->p_filesz)
318 return NULL;
319 Elf64_Dyn *hdr = (Elf64_Dyn*) bind (phdr->p_offset + ndx * sizeof (Elf64_Dyn),
320 sizeof (Elf64_Dyn));
321 if (hdr == NULL)
322 return NULL;
323 pdyn->d_tag = decode (hdr->d_tag);
324 pdyn->d_un.d_val = decode (hdr->d_un.d_val);
325 }
326 return pdyn;
327 }
328
329 unsigned
elf_version(unsigned ver)330 Elf::elf_version (unsigned ver)
331 {
332 // We compile locally, no need to check the version
333 return ver;
334 }
335
336 Elf *
elf_begin(char * fname,Elf_status * stp)337 Elf::elf_begin (char *fname, Elf_status *stp)
338 {
339 if (fname == NULL)
340 {
341 if (stp)
342 *stp = ELF_ERR_CANT_OPEN_FILE;
343 return NULL;
344 }
345 Elf *elf = new Elf (fname);
346 if (stp)
347 *stp = elf->status;
348 if (elf->status != ELF_ERR_NONE)
349 {
350 delete elf;
351 return NULL;
352 }
353 #if DEBUG
354 if (DUMP_ELF_SEC)
355 {
356 char *str = elf->dump ();
357 fprintf (stderr, NTXT ("%s\n\n"), str);
358 free (str);
359 }
360 #endif /* DEBUG */
361 return elf;
362 }
363
364 unsigned int
elf_get_sec_num(const char * name)365 Elf::elf_get_sec_num (const char *name)
366 {
367 if (name == NULL || ehdrp == NULL)
368 return 0;
369 for (unsigned int sec = 1; sec < ehdrp->e_shnum; sec++)
370 {
371 Elf_Internal_Shdr *shdr = get_shdr (sec);
372 if (shdr == NULL)
373 continue;
374 char *sname = elf_strptr (ehdrp->e_shstrndx, shdr->sh_name);
375 if (sname != NULL && strcmp (name, sname) == 0)
376 return sec;
377 }
378 return 0;
379 }
380
381 char *
get_sec_name(unsigned int sec)382 Elf::get_sec_name (unsigned int sec)
383 {
384 Elf_Internal_Shdr *shdr = get_shdr (sec);
385 if (ehdrp == NULL || shdr == NULL)
386 return NULL;
387 return elf_strptr (ehdrp->e_shstrndx, shdr->sh_name);
388 }
389
390 Elf_Data *
elf_getdata(unsigned int sec)391 Elf::elf_getdata (unsigned int sec)
392 {
393 if (data == NULL)
394 {
395 data = (Elf_Data **) malloc (ehdrp->e_shnum * sizeof (Elf_Data *));
396 for (int i = 0; i < (int) ehdrp->e_shnum; i++)
397 data[i] = NULL;
398 }
399 Elf_Data *edta = data[sec];
400 if (edta == NULL)
401 {
402 Elf_Internal_Shdr *shdr = get_shdr (sec);
403 if (shdr == NULL)
404 return NULL;
405 edta = new Elf_Data;
406 data[sec] = edta;
407 if ((shdr->sh_flags & SHF_SUNW_ABSENT) != 0)
408 {
409 char *sname = get_sec_name (sec);
410 for (int i = 0, sz = VecSize(ancillary_files); i < sz; i++)
411 {
412 Elf *ancElf = ancillary_files->fetch (i);
413 int secNum = sec;
414 if (dbe_strcmp (sname, ancElf->get_sec_name (sec)) != 0)
415 {
416 append_msg (CMSG_WARN,
417 "Warning: the section #%d (%s) is mismatch in ancillary file '%s')\n",
418 sec, STR (sname), STR (ancElf->fname));
419 secNum = ancElf->elf_get_sec_num (sname);
420 }
421 if (secNum > 0)
422 {
423 Elf_Data *ed = ancElf->elf_getdata (secNum);
424 if (ed && ed->d_buf)
425 {
426 *edta = *ed;
427 edta->d_flags |= SHF_SUNW_ABSENT;
428 return edta;
429 }
430 }
431 }
432 }
433 edta->d_buf = get_data (shdr->sh_offset, (size_t) shdr->sh_size, NULL);
434 edta->d_flags = shdr->sh_flags;
435 edta->d_size = ((edta->d_buf == NULL) || (shdr->sh_type == SHT_NOBITS)) ? 0 : shdr->sh_size;
436 edta->d_off = shdr->sh_offset;
437 edta->d_align = shdr->sh_addralign;
438 }
439 return edta;
440 }
441
442 int64_t
elf_checksum()443 Elf::elf_checksum ()
444 {
445 if (ehdrp == NULL)
446 return 0;
447 int64_t chk = 0;
448 for (unsigned int ndx = 0; ndx < ehdrp->e_phnum; ndx++)
449 {
450 Elf_Internal_Phdr *phdr = get_phdr (ndx);
451 if (phdr == NULL)
452 continue;
453 if (phdr->p_type == PT_DYNAMIC)
454 {
455 Elf64_Dyn edyn;
456 for (unsigned int i = 0; elf_getdyn (phdr, i, &edyn) != NULL; i++)
457 {
458 if (!edyn.d_tag)
459 break;
460 if (edyn.d_tag == DT_CHECKSUM)
461 {
462 chk = edyn.d_un.d_val;
463 break;
464 }
465 }
466 }
467 }
468 return normalize_checksum (chk);
469 }
470
471 uint64_t
get_baseAddr()472 Elf::get_baseAddr ()
473 {
474 uint64_t addr = 0;
475 for (unsigned int pnum = 0; pnum < elf_getehdr ()->e_phnum; pnum++)
476 {
477 Elf_Internal_Phdr *phdr = get_phdr (pnum);
478 if (phdr->p_type == PT_LOAD && phdr->p_flags == (PF_R | PF_X))
479 {
480 if (addr == 0)
481 addr = phdr->p_vaddr;
482 else
483 {
484 addr = 0;
485 break;
486 }
487 }
488 }
489 return addr;
490 }
491
492 char *
elf_strptr(unsigned int sec,uint64_t off)493 Elf::elf_strptr (unsigned int sec, uint64_t off)
494 {
495 Elf_Data *edta = elf_getdata (sec);
496 if (edta && edta->d_buf && edta->d_size > off)
497 return ((char *) edta->d_buf) + off;
498 return NULL;
499 }
500
501 Elf_Internal_Sym *
elf_getsym(Elf_Data * edta,unsigned int ndx,Elf_Internal_Sym * dst)502 Elf::elf_getsym (Elf_Data *edta, unsigned int ndx, Elf_Internal_Sym *dst)
503 {
504 if (dst == NULL || edta == NULL)
505 return NULL;
506 if (elf_getclass () == ELFCLASS32)
507 {
508 if (edta->d_size <= ndx * sizeof (Elf32_Sym))
509 return NULL;
510 Elf32_Sym *hdr = (Elf32_Sym*) bind (edta->d_off + ndx * sizeof (Elf32_Sym), sizeof (Elf32_Sym));
511 if (hdr == NULL)
512 return NULL;
513 dst->st_name = decode (hdr->st_name);
514 dst->st_value = decode (hdr->st_value);
515 dst->st_size = decode (hdr->st_size);
516 dst->st_info = ELF64_ST_INFO (ELF32_ST_BIND (decode (hdr->st_info)),
517 ELF32_ST_TYPE (decode (hdr->st_info)));
518 dst->st_other = decode (hdr->st_other);
519 dst->st_shndx = decode (hdr->st_shndx);
520 }
521 else
522 {
523 if (edta->d_size <= ndx * sizeof (Elf64_Sym))
524 return NULL;
525 Elf64_Sym *hdr = (Elf64_Sym*) bind (edta->d_off + ndx * sizeof (Elf64_Sym),
526 sizeof (Elf64_Sym));
527 if (hdr == NULL)
528 return NULL;
529 dst->st_name = decode (hdr->st_name);
530 dst->st_value = decode (hdr->st_value);
531 dst->st_size = decode (hdr->st_size);
532 dst->st_info = decode (hdr->st_info);
533 dst->st_other = decode (hdr->st_other);
534 dst->st_shndx = decode (hdr->st_shndx);
535 }
536 return dst;
537 }
538
539 Elf_Internal_Rela *
elf_getrel(Elf_Data * edta,unsigned int ndx,Elf_Internal_Rela * dst)540 Elf::elf_getrel (Elf_Data *edta, unsigned int ndx, Elf_Internal_Rela *dst)
541 {
542 if (dst == NULL || edta == NULL || edta->d_buf == NULL)
543 return NULL;
544 if (elf_getclass () == ELFCLASS32)
545 {
546 Elf32_Rel *rel = ((Elf32_Rel *) edta->d_buf) + ndx;
547 dst->r_offset = decode (rel->r_offset);
548 dst->r_info = ELF64_R_INFO (ELF32_R_SYM (decode (rel->r_info)),
549 ELF32_R_TYPE (decode (rel->r_info)));
550 }
551 else
552 {
553 Elf64_Rel *rel = ((Elf64_Rel *) edta->d_buf) + ndx;
554 dst->r_offset = decode (rel->r_offset);
555 dst->r_info = decode (rel->r_info);
556 }
557 return dst;
558 }
559
560 Elf_Internal_Rela *
elf_getrela(Elf_Data * edta,unsigned int ndx,Elf_Internal_Rela * dst)561 Elf::elf_getrela (Elf_Data *edta, unsigned int ndx, Elf_Internal_Rela *dst)
562 {
563 if (dst == NULL || edta == NULL || edta->d_buf == NULL)
564 return NULL;
565 if (elf_getclass () == ELFCLASS32)
566 {
567 Elf32_Rela *rela = ((Elf32_Rela *) edta->d_buf) + ndx;
568 dst->r_offset = decode (rela->r_offset);
569 dst->r_addend = decode (rela->r_addend);
570 dst->r_info = ELF64_R_INFO (ELF32_R_SYM (decode (rela->r_info)),
571 ELF32_R_TYPE (decode (rela->r_info)));
572 }
573 else
574 {
575 Elf64_Rela *rela = ((Elf64_Rela *) edta->d_buf) + ndx;
576 dst->r_offset = decode (rela->r_offset);
577 dst->r_addend = decode (rela->r_addend);
578 dst->r_info = decode (rela->r_info);
579 }
580 return dst;
581 }
582
583 Elf64_Ancillary *
elf_getancillary(Elf_Data * edta,unsigned int ndx,Elf64_Ancillary * dst)584 Elf::elf_getancillary (Elf_Data *edta, unsigned int ndx, Elf64_Ancillary *dst)
585 {
586 if (dst == NULL || edta == NULL || edta->d_buf == NULL)
587 return NULL;
588 if (elf_getclass () == ELFCLASS32)
589 {
590 Elf32_Ancillary *p = ((Elf32_Ancillary *) edta->d_buf) + ndx;
591 dst->a_tag = decode (p->a_tag);
592 dst->a_un.a_val = decode (p->a_un.a_val);
593 }
594 else
595 {
596 Elf64_Ancillary *p = ((Elf64_Ancillary *) edta->d_buf) + ndx;
597 dst->a_tag = decode (p->a_tag);
598 dst->a_un.a_val = decode (p->a_un.a_val);
599 }
600 return dst;
601 }
602
603 Elf *
get_related_file(const char * lo_name,const char * nm)604 Elf::get_related_file (const char *lo_name, const char *nm)
605 {
606 DbeFile *df;
607 if (*nm == '/')
608 {
609 df = new DbeFile (nm);
610 df->filetype |= (DbeFile::F_FILE | DbeFile::F_DEBUG_FILE);
611 }
612 else
613 {
614 char *bname = get_basename (lo_name);
615 char *fnm = dbe_sprintf ("%.*s/%s", (int) (bname - lo_name), lo_name, nm);
616 df = new DbeFile (fnm);
617 df->filetype |= (DbeFile::F_FILE | DbeFile::F_DEBUG_FILE);
618 free (fnm);
619 }
620 Dprintf (DEBUG_STABS, "get_related_file: %s -> '%s'\n", nm, df->get_name ());
621 Elf_status st = ELF_ERR_CANT_OPEN_FILE;
622 Elf *elf = elf_begin (df->get_location (), &st);
623 if (elf)
624 {
625 elf->dbeFile = df;
626 return elf;
627 }
628 switch (st)
629 {
630 case ELF_ERR_CANT_OPEN_FILE:
631 append_msg (CMSG_ERROR, GTXT ("Cannot open file `%s'"), df->get_name ());
632 break;
633 case ELF_ERR_BAD_ELF_FORMAT:
634 default:
635 append_msg (CMSG_ERROR, GTXT ("Cannot read ELF header of `%s'"),
636 df->get_name ());
637 break;
638 }
639 delete df;
640 return NULL;
641 }
642
643 Elf *
find_ancillary_files(char * lo_name)644 Elf::find_ancillary_files (char *lo_name)
645 {
646 // read the .gnu_debuglink and .SUNW_ancillary seections
647 if (gnu_debug_file)
648 return gnu_debug_file;
649 unsigned int sec = elf_get_sec_num (NTXT (".gnu_debuglink"));
650 if (sec > 0)
651 {
652 Elf_Data *dp = elf_getdata (sec);
653 if (dp)
654 {
655 gnu_debug_file = get_related_file (lo_name, (char *) (dp->d_buf));
656 if (gnu_debug_file)
657 return gnu_debug_file;
658 }
659 }
660
661 sec = elf_get_sec_num (NTXT (".SUNW_ancillary"));
662 if (sec > 0)
663 {
664 Elf_Internal_Shdr *shdr = get_shdr (sec);
665 uint64_t check_sum = 0;
666 char *ancName = NULL;
667 if (shdr)
668 {
669 Elf_Data *dp = elf_getdata (sec);
670 for (int i = 0, sz = (int) (shdr->sh_size / shdr->sh_entsize);
671 i < sz; i++)
672 {
673 Elf64_Ancillary anc;
674 if (elf_getancillary (dp, i, &anc) == NULL
675 || anc.a_tag == ANC_SUNW_NULL)
676 break;
677 if (anc.a_tag == ANC_SUNW_MEMBER)
678 ancName = elf_strptr (shdr->sh_link, anc.a_un.a_ptr);
679 else if (anc.a_tag == ANC_SUNW_CHECKSUM)
680 {
681 if (i == 0)
682 {
683 check_sum = anc.a_un.a_val;
684 continue;
685 }
686 if (check_sum == anc.a_un.a_val)
687 ancName = NULL;
688 if (ancName)
689 {
690 Elf *ancElf = get_related_file (lo_name, ancName);
691 if (ancElf == NULL)
692 continue;
693 int ancSec = ancElf->elf_get_sec_num (".SUNW_ancillary");
694 if (ancSec > 0)
695 {
696 Elf_Internal_Shdr *ancHdr = ancElf->get_shdr (ancSec);
697 if (ancHdr)
698 {
699 Elf_Data *anc_dp = ancElf->elf_getdata (ancSec);
700 Elf64_Ancillary anc1;
701 if (ancElf->elf_getancillary (anc_dp, 0, &anc1)
702 && (anc1.a_tag == ANC_SUNW_CHECKSUM) &&
703 anc1.a_un.a_val == anc.a_un.a_val)
704 {
705 if (ancillary_files == NULL)
706 ancillary_files = new Vector<Elf*>(2);
707 ancillary_files->append (ancElf);
708 }
709 else
710 append_msg (CMSG_WARN, GTXT ("Load Object: '%s' (checksum Ox%lld). The .anc file '%s' has checksum Ox%llx"),
711 STR (fname), (long long) check_sum,
712 STR (ancElf->dbeFile->get_location ()),
713 (long long) anc1.a_un.a_val);
714 }
715 }
716 ancName = NULL;
717 }
718 }
719 }
720 }
721 }
722 return NULL;
723 }
724
725 char*
get_location()726 Elf::get_location ()
727 {
728 return dbeFile ? dbeFile->get_location () : fname;
729 }
730
731 #define RET_S(x) if (t == x) return (char *) #x
732
733 static char *
get_elf_class_name(int t)734 get_elf_class_name (int t)
735 {
736 RET_S (ELFCLASSNONE);
737 RET_S (ELFCLASS32);
738 RET_S (ELFCLASS64);
739 return NTXT ("ELFCLASS_UNKNOWN");
740 }
741
742 static char *
get_elf_data_name(int t)743 get_elf_data_name (int t)
744 {
745 RET_S (ELFDATANONE);
746 RET_S (ELFDATA2LSB);
747 RET_S (ELFDATA2MSB);
748 return NTXT ("ELFDATA_UNKNOWN");
749 }
750
751 static char *
get_elf_osabi_name(int t)752 get_elf_osabi_name (int t)
753 {
754 RET_S (ELFOSABI_NONE);
755 RET_S (ELFOSABI_HPUX);
756 RET_S (ELFOSABI_NETBSD);
757 RET_S (ELFOSABI_LINUX);
758 RET_S (ELFOSABI_SOLARIS);
759 RET_S (ELFOSABI_AIX);
760 RET_S (ELFOSABI_IRIX);
761 RET_S (ELFOSABI_FREEBSD);
762 RET_S (ELFOSABI_TRU64);
763 RET_S (ELFOSABI_MODESTO);
764 RET_S (ELFOSABI_OPENBSD);
765 return NTXT ("ELFOSABI_UNKNOWN");
766 }
767
768 static char *
get_elf_etype_name(int t)769 get_elf_etype_name (int t)
770 {
771 RET_S (ET_NONE);
772 RET_S (ET_REL);
773 RET_S (ET_EXEC);
774 RET_S (ET_DYN);
775 RET_S (ET_CORE);
776 RET_S (ET_LOPROC);
777 RET_S (ET_HIPROC);
778 return NTXT ("ETYPE_UNKNOWN");
779 }
780
781 static char *
get_elf_ptype_name(int t)782 get_elf_ptype_name (int t)
783 {
784 RET_S (PT_NULL);
785 RET_S (PT_LOAD);
786 RET_S (PT_DYNAMIC);
787 RET_S (PT_INTERP);
788 RET_S (PT_NOTE);
789 RET_S (PT_SHLIB);
790 RET_S (PT_PHDR);
791 RET_S (PT_TLS);
792 RET_S (PT_LOOS);
793 RET_S (PT_GNU_EH_FRAME);
794 RET_S (PT_GNU_EH_FRAME);
795 RET_S (PT_HIOS);
796 RET_S (PT_LOPROC);
797 RET_S (PT_HIPROC);
798 return NTXT ("PTYPE_UNKNOWN");
799 }
800
801 static char *
get_elf_shtype_name(unsigned int t)802 get_elf_shtype_name (unsigned int t)
803 {
804 RET_S (SHT_NULL);
805 RET_S (SHT_PROGBITS);
806 RET_S (SHT_SYMTAB);
807 RET_S (SHT_STRTAB);
808 RET_S (SHT_RELA);
809 RET_S (SHT_HASH);
810 RET_S (SHT_DYNAMIC);
811 RET_S (SHT_NOTE);
812 RET_S (SHT_NOBITS);
813 RET_S (SHT_REL);
814 RET_S (SHT_SHLIB);
815 RET_S (SHT_DYNSYM);
816 RET_S (SHT_INIT_ARRAY);
817 RET_S (SHT_FINI_ARRAY);
818 RET_S (SHT_PREINIT_ARRAY);
819 RET_S (SHT_GROUP);
820 RET_S (SHT_SYMTAB_SHNDX);
821 RET_S (SHT_LOOS);
822 RET_S (SHT_SUNW_verdef);
823 RET_S (SHT_SUNW_verneed);
824 RET_S (SHT_HIOS);
825 RET_S (SHT_LOPROC);
826 RET_S (SHT_HIPROC);
827 RET_S (SHT_LOUSER);
828 RET_S (SHT_HIUSER);
829 return NTXT ("SHTYPE_UNKNOWN");
830 }
831
832 static char *
get_elf_machine_name(int t)833 get_elf_machine_name (int t)
834 {
835 RET_S (EM_NONE);
836 RET_S (EM_M32);
837 RET_S (EM_SPARC);
838 RET_S (EM_386);
839 RET_S (EM_68K);
840 RET_S (EM_88K);
841 RET_S (EM_860);
842 RET_S (EM_MIPS);
843 RET_S (EM_S370);
844 RET_S (EM_MIPS_RS3_LE);
845 RET_S (EM_SPARC32PLUS);
846 RET_S (EM_960);
847 RET_S (EM_PPC);
848 RET_S (EM_PPC64);
849 RET_S (EM_V800);
850 RET_S (EM_FR20);
851 RET_S (EM_RH32);
852 RET_S (EM_RCE);
853 RET_S (EM_ARM);
854 RET_S (EM_ALPHA);
855 RET_S (EM_SH);
856 RET_S (EM_SPARCV9);
857 RET_S (EM_TRICORE);
858 RET_S (EM_ARC);
859 RET_S (EM_H8_300);
860 RET_S (EM_H8_300H);
861 RET_S (EM_H8S);
862 RET_S (EM_H8_500);
863 RET_S (EM_IA_64);
864 RET_S (EM_MIPS_X);
865 RET_S (EM_COLDFIRE);
866 RET_S (EM_68HC12);
867 RET_S (EM_MMA);
868 RET_S (EM_PCP);
869 RET_S (EM_NCPU);
870 RET_S (EM_NDR1);
871 RET_S (EM_STARCORE);
872 RET_S (EM_ME16);
873 RET_S (EM_ST100);
874 RET_S (EM_TINYJ);
875 RET_S (EM_X86_64);
876 RET_S (EM_PDSP);
877 RET_S (EM_FX66);
878 RET_S (EM_ST9PLUS);
879 RET_S (EM_ST7);
880 RET_S (EM_68HC16);
881 RET_S (EM_68HC11);
882 RET_S (EM_68HC08);
883 RET_S (EM_68HC05);
884 RET_S (EM_SVX);
885 RET_S (EM_ST19);
886 RET_S (EM_VAX);
887 RET_S (EM_CRIS);
888 RET_S (EM_JAVELIN);
889 RET_S (EM_FIREPATH);
890 RET_S (EM_ZSP);
891 RET_S (EM_MMIX);
892 RET_S (EM_HUANY);
893 RET_S (EM_PRISM);
894 RET_S (EM_AVR);
895 RET_S (EM_FR30);
896 RET_S (EM_D10V);
897 RET_S (EM_D30V);
898 RET_S (EM_V850);
899 RET_S (EM_M32R);
900 RET_S (EM_MN10300);
901 RET_S (EM_MN10200);
902 RET_S (EM_PJ);
903 RET_S (EM_OPENRISC);
904 RET_S (EM_XTENSA);
905 return NTXT ("ELFMACHINE_UNKNOWN");
906 }
907
908 static char *
get_elf_version_name(int t)909 get_elf_version_name (int t)
910 {
911 RET_S (EV_NONE);
912 RET_S (EV_CURRENT);
913 return NTXT ("VERSION_UNKNOWN");
914 }
915
916 static char *
get_elf_ancillary_tag(int t)917 get_elf_ancillary_tag (int t)
918 {
919 RET_S (ANC_SUNW_NULL);
920 RET_S (ANC_SUNW_CHECKSUM);
921 RET_S (ANC_SUNW_MEMBER);
922 RET_S (ANC_SUNW_NUM);
923 return NTXT ("ANCILLARY_TAG_UNKNOWN");
924 }
925
926 #define ADD_S(x) if ((f & (x)) == (x)) { sb->append(' '); sb->append(#x); f &= ~(x); }
927
928 static void
dump_sh_flags(StringBuilder * sb,long long flags)929 dump_sh_flags (StringBuilder *sb, long long flags)
930 {
931 long long f = flags;
932 if (f != 0)
933 {
934 sb->append (NTXT (" ["));
935 ADD_S (SHF_WRITE)
936 ADD_S (SHF_ALLOC)
937 ADD_S (SHF_EXECINSTR)
938 ADD_S (SHF_MERGE)
939 ADD_S (SHF_STRINGS)
940 ADD_S (SHF_INFO_LINK)
941 ADD_S (SHF_LINK_ORDER)
942 ADD_S (SHF_OS_NONCONFORMING)
943 ADD_S (SHF_GROUP)
944 ADD_S (SHF_TLS)
945 ADD_S (SHF_SUNW_ABSENT)
946 ADD_S (SHF_EXCLUDE)
947 if (f != 0 && f != flags)
948 sb->appendf (NTXT (" 0x%llx"), (long long) f);
949 sb->append (NTXT (" ]"));
950 }
951 sb->append (NTXT ("\n"));
952 }
953
954 static void
dump_p_flags(StringBuilder * sb,long long flags)955 dump_p_flags (StringBuilder *sb, long long flags)
956 {
957 long long f = flags;
958 if (f != 0)
959 {
960 sb->append (NTXT (" ["));
961 ADD_S (PF_X)
962 ADD_S (PF_W)
963 ADD_S (PF_R)
964 ADD_S (PF_MASKPROC)
965 if (f != 0 && f != flags)
966 sb->appendf (NTXT (" 0x%llx"), (long long) f);
967 sb->append (NTXT (" ]"));
968 }
969 sb->append (NTXT ("\n"));
970 }
971
972 char *
dump()973 Elf::dump ()
974 {
975 StringBuilder sb;
976 sb.sprintf (NTXT ("ELF Header: %s\n"), fname ? fname : GTXT ("(unknown)"));
977 if (ehdrp == NULL)
978 {
979 sb.appendf (GTXT ("\n\n Cannot read Elf header\n"));
980 return sb.toString ();
981 }
982 sb.appendf (NTXT (" %-15s "), NTXT ("e_ident"));
983 for (int i = 0; i < EI_NIDENT; i++)
984 sb.appendf (NTXT ("%x"), ehdrp->e_ident[i]);
985 sb.append (NTXT ("\n"));
986 char *fmt0 = NTXT (" %-15s %10lld ( %s )\n");
987 char *fmt1 = NTXT (" %-15s 0x%08llx ( %lld )\n");
988 char *fmt2 = NTXT (" %-15s 0x%08llx");
989 sb.appendf (fmt0, NTXT ("EI_CLASS"), (long long) ehdrp->e_ident[EI_CLASS],
990 get_elf_class_name (ehdrp->e_ident[EI_CLASS]));
991 sb.appendf (fmt0, NTXT ("EI_DATA"), (long long) ehdrp->e_ident[EI_DATA],
992 get_elf_data_name (ehdrp->e_ident[EI_DATA]));
993 sb.appendf (fmt0, NTXT ("EI_OSABI"), (long long) ehdrp->e_ident[EI_OSABI],
994 get_elf_osabi_name (ehdrp->e_ident[EI_OSABI]));
995 sb.appendf (fmt0, NTXT ("e_type"), (long long) ehdrp->e_type,
996 get_elf_etype_name (ehdrp->e_type));
997 sb.appendf (fmt0, NTXT ("e_machine"), (long long) ehdrp->e_machine,
998 get_elf_machine_name (ehdrp->e_machine));
999 sb.appendf (fmt0, NTXT ("e_version"), (long long) ehdrp->e_version,
1000 get_elf_version_name (ehdrp->e_version));
1001 sb.appendf (fmt1, NTXT ("e_entry"), (long long) ehdrp->e_entry,
1002 (long long) ehdrp->e_entry);
1003 sb.appendf (fmt1, NTXT ("e_phoff"), (long long) ehdrp->e_phoff,
1004 (long long) ehdrp->e_phoff);
1005 sb.appendf (fmt1, NTXT ("e_shoff"), (long long) ehdrp->e_shoff,
1006 (long long) ehdrp->e_shoff);
1007 sb.appendf (fmt1, NTXT ("e_flags"), (long long) ehdrp->e_flags,
1008 (long long) ehdrp->e_flags);
1009 sb.appendf (fmt1, NTXT ("e_ehsize"), (long long) ehdrp->e_ehsize,
1010 (long long) ehdrp->e_ehsize);
1011 sb.appendf (fmt1, NTXT ("e_phentsize"), (long long) ehdrp->e_phentsize,
1012 (long long) ehdrp->e_phentsize);
1013 sb.appendf (fmt1, NTXT ("e_phnum"), (long long) ehdrp->e_phnum,
1014 (long long) ehdrp->e_phnum);
1015 sb.appendf (fmt1, NTXT ("e_shentsize"), (long long) ehdrp->e_shentsize,
1016 (long long) ehdrp->e_shentsize);
1017 sb.appendf (fmt1, NTXT ("e_shnum"), (long long) ehdrp->e_shnum,
1018 (long long) ehdrp->e_shnum);
1019 sb.appendf (fmt1, NTXT ("e_shstrndx"), (long long) ehdrp->e_shstrndx,
1020 (long long) ehdrp->e_shstrndx);
1021
1022 for (unsigned int i = 0; i < ehdrp->e_phnum; i++)
1023 {
1024 sb.appendf (NTXT ("\nProgram Header[%d]:\n"), i);
1025 Elf_Internal_Phdr *phdr = get_phdr (i);
1026 if (phdr == NULL)
1027 {
1028 sb.appendf (NTXT (" ERROR: get_phdr(%d) failed\n"), i);
1029 continue;
1030 }
1031 sb.appendf (fmt0, "p_type", (long long) phdr->p_type,
1032 get_elf_ptype_name (phdr->p_type));
1033 sb.appendf (fmt2, "p_flags", (long long) phdr->p_flags);
1034 dump_p_flags (&sb, phdr->p_flags);
1035 sb.appendf (fmt1, "p_offset", (long long) phdr->p_offset,
1036 (long long) phdr->p_offset);
1037 sb.appendf (fmt1, "p_vaddr", (long long) phdr->p_vaddr,
1038 (long long) phdr->p_vaddr);
1039 sb.appendf (fmt1, "p_paddr", (long long) phdr->p_paddr,
1040 (long long) phdr->p_paddr);
1041 sb.appendf (fmt1, "p_filesz", (long long) phdr->p_filesz,
1042 (long long) phdr->p_filesz);
1043 sb.appendf (fmt1, "p_memsz", (long long) phdr->p_memsz,
1044 (long long) phdr->p_memsz);
1045 sb.appendf (fmt1, "p_align", (long long) phdr->p_align,
1046 (long long) phdr->p_align);
1047 }
1048
1049 for (unsigned int i = 1; i < ehdrp->e_shnum; i++)
1050 {
1051 sb.appendf (NTXT ("\nSection Header[%d]:\n"), i);
1052 Elf_Internal_Shdr *shdr = get_shdr (i);
1053 if (shdr == NULL)
1054 {
1055 sb.appendf (NTXT (" ERROR: get_shdr(%d) failed\n"), i);
1056 continue;
1057 }
1058 char *s = get_sec_name (i);
1059 sb.appendf (fmt0, "sh_name", (long long) shdr->sh_name,
1060 s ? s : NTXT ("NULL"));
1061 sb.appendf (fmt0, "sh_type", (long long) shdr->sh_type,
1062 get_elf_shtype_name (shdr->sh_type));
1063 sb.appendf (fmt2, "sh_flags", (long long) shdr->sh_flags);
1064 dump_sh_flags (&sb, shdr->sh_flags);
1065 sb.appendf (fmt1, "sh_addr", (long long) shdr->sh_addr,
1066 (long long) shdr->sh_addr);
1067 sb.appendf (fmt1, "sh_offset", (long long) shdr->sh_offset,
1068 (long long) shdr->sh_offset);
1069 sb.appendf (fmt1, "sh_size", (long long) shdr->sh_size,
1070 (long long) shdr->sh_size);
1071 sb.appendf (fmt1, "sh_link", (long long) shdr->sh_link,
1072 (long long) shdr->sh_link);
1073 sb.appendf (fmt1, "sh_info", (long long) shdr->sh_info,
1074 (long long) shdr->sh_info);
1075 sb.appendf (fmt1, "sh_addralign", (long long) shdr->sh_addralign,
1076 (long long) shdr->sh_addralign);
1077 sb.appendf (fmt1, "sh_entsize", (long long) shdr->sh_entsize,
1078 (long long) shdr->sh_entsize);
1079 }
1080
1081 for (unsigned int i = 1; i < ehdrp->e_shnum; i++)
1082 {
1083 Elf_Internal_Shdr *shdr = get_shdr (i);
1084 if (shdr == NULL)
1085 continue;
1086 char *secName = get_sec_name (i);
1087 if (secName == NULL)
1088 continue;
1089 if (strcmp (NTXT (".SUNW_ancillary"), secName) == 0)
1090 {
1091 sb.appendf (NTXT ("\nSection[%d]: %s\n"), i, secName);
1092 Elf_Data *dp = elf_getdata (i);
1093 for (int j = 0, cnt = (int) (shdr->sh_size / shdr->sh_entsize);
1094 j < cnt; j++)
1095 {
1096 Elf64_Ancillary anc;
1097 if (elf_getancillary (dp, j, &anc) == NULL)
1098 break;
1099 sb.appendf (NTXT ("%10d %-20s 0x%08llx %6lld"), j,
1100 get_elf_ancillary_tag ((int) anc.a_tag),
1101 (long long) anc.a_un.a_ptr, (long long) anc.a_un.a_ptr);
1102 if (anc.a_tag == ANC_SUNW_MEMBER)
1103 sb.appendf (NTXT (" %s\n"), STR (elf_strptr (shdr->sh_link, anc.a_un.a_ptr)));
1104 else
1105 sb.append (NTXT ("\n"));
1106 }
1107 }
1108 }
1109 return sb.toString ();
1110 }
1111
1112 void
dump_elf_sec()1113 Elf::dump_elf_sec ()
1114 {
1115 if (!DUMP_ELF_SEC)
1116 return;
1117 if (ehdrp == NULL)
1118 return;
1119 Dprintf (DUMP_ELF_SEC, "======= DwarfLib::dump_elf_sec\n"
1120 " N |type|flags| sh_addr | sh_offset | sh_size | sh_link |"
1121 " sh_info | sh_addralign | sh_entsize | sh_name | name\n");
1122 for (unsigned int sec = 1; sec < ehdrp->e_shnum; sec++)
1123 {
1124 Elf_Internal_Shdr *shdr = get_shdr (sec);
1125 if (shdr == NULL)
1126 continue;
1127 char *name = elf_strptr (ehdrp->e_shstrndx, shdr->sh_name);
1128 Dprintf (DUMP_ELF_SEC, "%3d:%3d |%4d |%9lld | %9lld |%8lld |%8lld |"
1129 "%8lld |%14d |%11lld | %6lld %s\n",
1130 sec, (int) shdr->sh_type, (int) shdr->sh_flags,
1131 (long long) shdr->sh_addr, (long long) shdr->sh_offset,
1132 (long long) shdr->sh_size, (long long) shdr->sh_link,
1133 (long long) shdr->sh_info,
1134 (int) shdr->sh_addralign, (long long) shdr->sh_entsize,
1135 (long long) shdr->sh_name, name ? name : NTXT ("NULL"));
1136 }
1137 Dprintf (DUMP_ELF_SEC, NTXT ("\n"));
1138 }
1139