Update elftoolchain to upstream rev 3130
This includes a number of libdwarf improvements (particularly DWARF4 related) and updates to elftoolchain tools such as strip(1). It also includes a large number of miscellaneous fixes (memory leaks, sign and cast warnings, integer overflow and underflow, etc.). This is a merge of r276167,276170-276172 from the projects/elftoolchain-update-r3130 branch. Sponsored by: The FreeBSD Foundation
This commit is contained in:
commit
b4e9f2392c
@ -1,4 +1,4 @@
|
||||
# $Id: Makefile 2606 2012-10-02 17:52:57Z jkoshy $
|
||||
# $Id: Makefile 3022 2014-04-17 18:05:58Z jkoshy $
|
||||
|
||||
TOP= ..
|
||||
|
||||
@ -12,4 +12,7 @@ all depend obj:
|
||||
clean clobber:
|
||||
rm -f ${CLEANFILES}
|
||||
|
||||
cleandepend:
|
||||
rm -f .depend
|
||||
|
||||
.include "${TOP}/mk/elftoolchain.inc.mk"
|
||||
|
@ -23,7 +23,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: elfdefinitions.h 2950 2013-06-15 13:36:02Z jkoshy $
|
||||
* $Id: elfdefinitions.h 3110 2014-12-20 08:32:46Z kaiwang27 $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -821,7 +821,8 @@ enum {
|
||||
EM__LAST__
|
||||
};
|
||||
|
||||
/* Older synonyms. */
|
||||
/* Other synonyms. */
|
||||
#define EM_AMD64 EM_X86_64
|
||||
#define EM_ARC_A5 EM_ARC_COMPACT
|
||||
|
||||
/*
|
||||
@ -2114,11 +2115,11 @@ typedef struct {
|
||||
|
||||
/* 64-bit entry. */
|
||||
typedef struct {
|
||||
Elf64_Word l_name;
|
||||
Elf64_Word l_time_stamp;
|
||||
Elf64_Word l_checksum;
|
||||
Elf64_Word l_version;
|
||||
Elf64_Word l_flags;
|
||||
Elf64_Word l_name; /* The name of a shared object. */
|
||||
Elf64_Word l_time_stamp; /* 32-bit timestamp. */
|
||||
Elf64_Word l_checksum; /* Checksum of visible symbols, sizes. */
|
||||
Elf64_Word l_version; /* Interface version string index. */
|
||||
Elf64_Word l_flags; /* Flags (LL_*). */
|
||||
} Elf64_Lib;
|
||||
|
||||
#define _ELF_DEFINE_LL_FLAGS() \
|
||||
@ -2366,12 +2367,12 @@ typedef struct {
|
||||
/* 64 bit PHDR entry. */
|
||||
typedef struct {
|
||||
Elf64_Word p_type; /* Type of segment. */
|
||||
Elf64_Word p_flags; /* File offset to segment. */
|
||||
Elf64_Off p_offset; /* Virtual address in memory. */
|
||||
Elf64_Addr p_vaddr; /* Physical address (if relevant). */
|
||||
Elf64_Addr p_paddr; /* Size of segment in file. */
|
||||
Elf64_Xword p_filesz; /* Size of segment in memory. */
|
||||
Elf64_Xword p_memsz; /* Segment flags. */
|
||||
Elf64_Word p_flags; /* Segment flags. */
|
||||
Elf64_Off p_offset; /* File offset to segment. */
|
||||
Elf64_Addr p_vaddr; /* Virtual address in memory. */
|
||||
Elf64_Addr p_paddr; /* Physical address (if relevant). */
|
||||
Elf64_Xword p_filesz; /* Size of segment in file. */
|
||||
Elf64_Xword p_memsz; /* Size of segment in memory. */
|
||||
Elf64_Xword p_align; /* Alignment constraints. */
|
||||
} Elf64_Phdr;
|
||||
|
||||
@ -2455,11 +2456,11 @@ typedef struct {
|
||||
|
||||
typedef struct {
|
||||
Elf64_Word st_name; /* index of symbol's name */
|
||||
unsigned char st_info; /* value for the symbol */
|
||||
unsigned char st_other; /* size of associated data */
|
||||
Elf64_Half st_shndx; /* type and binding attributes */
|
||||
Elf64_Addr st_value; /* visibility */
|
||||
Elf64_Xword st_size; /* index of related section */
|
||||
unsigned char st_info; /* type and binding attributes */
|
||||
unsigned char st_other; /* visibility */
|
||||
Elf64_Half st_shndx; /* index of related section */
|
||||
Elf64_Addr st_value; /* value for the symbol */
|
||||
Elf64_Xword st_size; /* size of associated data */
|
||||
} Elf64_Sym;
|
||||
|
||||
#define ELF32_ST_BIND(I) ((I) >> 4)
|
||||
|
@ -40,7 +40,7 @@
|
||||
|
||||
#include "elfcopy.h"
|
||||
|
||||
ELFTC_VCSID("$Id: archive.c 2370 2011-12-29 12:48:12Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: archive.c 3102 2014-10-29 21:09:01Z jkoshy $");
|
||||
|
||||
#define _ARMAG_LEN 8 /* length of ar magic string */
|
||||
#define _ARHDR_LEN 60 /* length of ar header */
|
||||
@ -350,7 +350,6 @@ ac_detect_ar(int ifd)
|
||||
r = -1;
|
||||
if ((a = archive_read_new()) == NULL)
|
||||
return (0);
|
||||
archive_read_support_filter_none(a);
|
||||
archive_read_support_format_ar(a);
|
||||
if (archive_read_open_fd(a, ifd, 10240) == ARCHIVE_OK)
|
||||
r = archive_read_next_header(a, &entry);
|
||||
@ -386,7 +385,6 @@ ac_read_objs(struct elfcopy *ecp, int ifd)
|
||||
err(EXIT_FAILURE, "lseek failed");
|
||||
if ((a = archive_read_new()) == NULL)
|
||||
errx(EXIT_FAILURE, "%s", archive_error_string(a));
|
||||
archive_read_support_filter_none(a);
|
||||
archive_read_support_format_ar(a);
|
||||
AC(archive_read_open_fd(a, ifd, 10240));
|
||||
for(;;) {
|
||||
@ -449,7 +447,6 @@ ac_write_objs(struct elfcopy *ecp, int ofd)
|
||||
if ((a = archive_write_new()) == NULL)
|
||||
errx(EXIT_FAILURE, "%s", archive_error_string(a));
|
||||
archive_write_set_format_ar_svr4(a);
|
||||
archive_write_add_filter_none(a);
|
||||
AC(archive_write_open_fd(a, ofd));
|
||||
|
||||
/* Write the archive symbol table, even if it's empty. */
|
||||
|
@ -40,7 +40,7 @@
|
||||
|
||||
#include "elfcopy.h"
|
||||
|
||||
ELFTC_VCSID("$Id: main.c 2970 2013-12-01 15:22:12Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: main.c 3111 2014-12-20 08:33:01Z kaiwang27 $");
|
||||
|
||||
enum options
|
||||
{
|
||||
|
@ -35,7 +35,7 @@
|
||||
|
||||
#include "elfcopy.h"
|
||||
|
||||
ELFTC_VCSID("$Id: sections.c 2358 2011-12-19 18:22:32Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: sections.c 3126 2014-12-21 08:03:31Z kaiwang27 $");
|
||||
|
||||
static void add_gnu_debuglink(struct elfcopy *ecp);
|
||||
static uint32_t calc_crc32(const char *p, size_t len, uint32_t crc);
|
||||
@ -372,6 +372,14 @@ create_scn(struct elfcopy *ecp)
|
||||
is_remove_reloc_sec(ecp, ish.sh_info))
|
||||
continue;
|
||||
|
||||
/*
|
||||
* Section groups should be removed if symbol table will
|
||||
* be removed. (section group's signature stored in symbol
|
||||
* table)
|
||||
*/
|
||||
if (ish.sh_type == SHT_GROUP && ecp->strip == STRIP_ALL)
|
||||
continue;
|
||||
|
||||
/* Get section flags set by user. */
|
||||
sec_flags = get_section_flags(ecp, name);
|
||||
|
||||
|
@ -35,7 +35,7 @@
|
||||
|
||||
#include "elfcopy.h"
|
||||
|
||||
ELFTC_VCSID("$Id: segments.c 2542 2012-08-12 16:14:15Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: segments.c 3113 2014-12-20 08:33:29Z kaiwang27 $");
|
||||
|
||||
static void insert_to_inseg_list(struct segment *seg, struct section *sec);
|
||||
|
||||
@ -73,13 +73,15 @@ add_to_inseg_list(struct elfcopy *ecp, struct section *s)
|
||||
*/
|
||||
loadable = 0;
|
||||
STAILQ_FOREACH(seg, &ecp->v_seg, seg_list) {
|
||||
if (s->off < seg->off)
|
||||
if (s->off < seg->off || (s->vma < seg->addr && !s->pseudo))
|
||||
continue;
|
||||
if (s->off + s->sz > seg->off + seg->fsz &&
|
||||
s->type != SHT_NOBITS)
|
||||
continue;
|
||||
if (s->off + s->sz > seg->off + seg->msz)
|
||||
continue;
|
||||
if (s->vma + s->sz > seg->addr + seg->msz)
|
||||
continue;
|
||||
|
||||
insert_to_inseg_list(seg, s);
|
||||
if (seg->type == PT_LOAD)
|
||||
@ -97,7 +99,7 @@ adjust_addr(struct elfcopy *ecp)
|
||||
struct section *s, *s0;
|
||||
struct segment *seg;
|
||||
struct sec_action *sac;
|
||||
uint64_t dl, lma, old_vma, start, end;
|
||||
uint64_t dl, lma, start, end;
|
||||
int found, i;
|
||||
|
||||
/*
|
||||
@ -114,8 +116,6 @@ adjust_addr(struct elfcopy *ecp)
|
||||
s->lma += ecp->change_addr;
|
||||
|
||||
if (!s->pseudo) {
|
||||
old_vma = s->vma;
|
||||
|
||||
/* Apply global VMA adjustment. */
|
||||
if (ecp->change_addr != 0)
|
||||
s->vma += ecp->change_addr;
|
||||
|
@ -34,7 +34,7 @@
|
||||
|
||||
#include "elfcopy.h"
|
||||
|
||||
ELFTC_VCSID("$Id: symbols.c 2971 2013-12-01 15:22:21Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: symbols.c 3019 2014-04-17 14:53:40Z jkoshy $");
|
||||
|
||||
/* Symbol table buffer structure. */
|
||||
struct symbuf {
|
||||
@ -300,7 +300,7 @@ generate_symbols(struct elfcopy *ecp)
|
||||
GElf_Sym sym;
|
||||
Elf_Data* id;
|
||||
Elf_Scn *is;
|
||||
size_t ishstrndx, namelen, ndx, nsyms, sc, symndx;
|
||||
size_t ishstrndx, namelen, ndx, sc, symndx;
|
||||
int ec, elferr, i;
|
||||
|
||||
if (elf_getshstrndx(ecp->ein, &ishstrndx) == 0)
|
||||
@ -320,7 +320,6 @@ generate_symbols(struct elfcopy *ecp)
|
||||
st_buf->lcap = 64;
|
||||
st_buf->lsz = 1; /* '\0' at start. */
|
||||
st_buf->gsz = 0;
|
||||
nsyms = 0;
|
||||
|
||||
ecp->symtab->sz = 0;
|
||||
ecp->strtab->sz = 0;
|
||||
|
@ -1,4 +1,4 @@
|
||||
# $Id: Makefile 2937 2013-04-27 04:48:23Z jkoshy $
|
||||
# $Id: Makefile 3097 2014-09-02 22:10:18Z kaiwang27 $
|
||||
|
||||
TOP= ${.CURDIR}/..
|
||||
|
||||
@ -42,6 +42,7 @@ SRCS= \
|
||||
dwarf_pubtypes.c \
|
||||
dwarf_ranges.c \
|
||||
dwarf_reloc.c \
|
||||
dwarf_sections.c \
|
||||
dwarf_seterror.c \
|
||||
dwarf_str.c \
|
||||
dwarf_types.c \
|
||||
@ -115,6 +116,7 @@ MAN= dwarf.3 \
|
||||
dwarf_add_weakname.3 \
|
||||
dwarf_attr.3 \
|
||||
dwarf_attrlist.3 \
|
||||
dwarf_attroffset.3 \
|
||||
dwarf_attrval_signed.3 \
|
||||
dwarf_child.3 \
|
||||
dwarf_dealloc.3 \
|
||||
@ -154,6 +156,7 @@ MAN= dwarf.3 \
|
||||
dwarf_get_cie_info.3 \
|
||||
dwarf_get_cie_of_fde.3 \
|
||||
dwarf_get_cu_die_offset.3 \
|
||||
dwarf_get_die_infotypes_flag.3 \
|
||||
dwarf_get_elf.3 \
|
||||
dwarf_get_fde_at_pc.3 \
|
||||
dwarf_get_fde_info_for_all_regs.3 \
|
||||
@ -175,6 +178,7 @@ MAN= dwarf.3 \
|
||||
dwarf_get_relocation_info.3 \
|
||||
dwarf_get_relocation_info_count.3 \
|
||||
dwarf_get_section_bytes.3 \
|
||||
dwarf_get_section_max_offsets.3 \
|
||||
dwarf_get_str.3 \
|
||||
dwarf_get_types.3 \
|
||||
dwarf_get_vars.3 \
|
||||
@ -192,6 +196,7 @@ MAN= dwarf.3 \
|
||||
dwarf_new_expr.3 \
|
||||
dwarf_new_fde.3 \
|
||||
dwarf_next_cu_header.3 \
|
||||
dwarf_next_types_section.3 \
|
||||
dwarf_object_init.3 \
|
||||
dwarf_producer_init.3 \
|
||||
dwarf_producer_set_isa.3 \
|
||||
@ -220,7 +225,9 @@ MLINKS+= \
|
||||
dwarf_attrval_signed.3 dwarf_attrval_string.3 \
|
||||
dwarf_attrval_signed.3 dwarf_attrval_unsigned.3 \
|
||||
dwarf_child.3 dwarf_offdie.3 \
|
||||
dwarf_child.3 dwarf_offdie_b.3 \
|
||||
dwarf_child.3 dwarf_siblingof.3 \
|
||||
dwarf_child.3 dwarf_siblingof_b.3 \
|
||||
dwarf_dealloc.3 dwarf_fde_cie_list_dealloc.3 \
|
||||
dwarf_dealloc.3 dwarf_funcs_dealloc.3 \
|
||||
dwarf_dealloc.3 dwarf_globals_dealloc.3 \
|
||||
@ -234,6 +241,7 @@ MLINKS+= \
|
||||
dwarf_dieoffset.3 dwarf_die_CU_offset.3 \
|
||||
dwarf_dieoffset.3 dwarf_die_CU_offset_range.3 \
|
||||
dwarf_dieoffset.3 dwarf_get_cu_die_offset_given_cu_header_offset.3 \
|
||||
dwarf_dieoffset.3 dwarf_get_cu_die_offset_given_cu_header_offset_b.3 \
|
||||
dwarf_finish.3 dwarf_object_finish.3 \
|
||||
dwarf_formref.3 dwarf_global_formref.3 \
|
||||
dwarf_formudata.3 dwarf_formsdata.3 \
|
||||
@ -273,6 +281,7 @@ MLINKS+= \
|
||||
dwarf_get_pubtypes.3 dwarf_pubtype_name_offsets.3 \
|
||||
dwarf_get_pubtypes.3 dwarf_pubtypename.3 \
|
||||
dwarf_get_ranges.3 dwarf_get_ranges_a.3 \
|
||||
dwarf_get_section_max_offsets.3 dwarf_get_section_max_offsets_b.3 \
|
||||
dwarf_get_types.3 dwarf_type_die_offset.3 \
|
||||
dwarf_get_types.3 dwarf_type_cu_offset.3 \
|
||||
dwarf_get_types.3 dwarf_type_name_offsets.3 \
|
||||
@ -291,6 +300,7 @@ MLINKS+= \
|
||||
dwarf_highpc.3 dwarf_bitoffset.3 \
|
||||
dwarf_highpc.3 dwarf_bitsize.3 \
|
||||
dwarf_highpc.3 dwarf_bytesize.3 \
|
||||
dwarf_highpc.3 dwarf_highpc_b.3 \
|
||||
dwarf_highpc.3 dwarf_lowpc.3 \
|
||||
dwarf_highpc.3 dwarf_srclang.3 \
|
||||
dwarf_lineno.3 dwarf_lineaddr.3 \
|
||||
@ -302,6 +312,9 @@ MLINKS+= \
|
||||
dwarf_lineno.3 dwarf_line_srcfileno.3 \
|
||||
dwarf_loclist.3 dwarf_loclist_n.3 \
|
||||
dwarf_loclist_from_expr.3 dwarf_loclist_from_expr_a.3 \
|
||||
dwarf_loclist_from_expr.3 dwarf_loclist_from_expr_b.3 \
|
||||
dwarf_next_cu_header.3 dwarf_next_cu_header_b.3 \
|
||||
dwarf_next_cu_header.3 dwarf_next_cu_header_c.3 \
|
||||
dwarf_producer_init.3 dwarf_producer_init_b.3 \
|
||||
dwarf_seterrarg.3 dwarf_seterrhand.3 \
|
||||
dwarf_set_frame_cfa_value.3 dwarf_set_frame_rule_initial_value.3 \
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $Id: Version.map 2576 2012-09-13 09:16:11Z jkoshy $ */
|
||||
/* $Id: Version.map 3085 2014-09-02 22:08:23Z kaiwang27 $ */
|
||||
|
||||
R1.0 {
|
||||
global:
|
||||
@ -39,6 +39,7 @@ global:
|
||||
dwarf_arrayorder;
|
||||
dwarf_attr;
|
||||
dwarf_attrlist;
|
||||
dwarf_attroffset;
|
||||
dwarf_attrval_flag;
|
||||
dwarf_attrval_signed;
|
||||
dwarf_attrval_string;
|
||||
@ -116,6 +117,8 @@ global:
|
||||
dwarf_get_cie_of_fde;
|
||||
dwarf_get_cu_die_offset;
|
||||
dwarf_get_cu_die_offset_given_cu_header_offset;
|
||||
dwarf_get_cu_die_offset_given_cu_header_offset_b;
|
||||
dwarf_get_die_infotypes_flag;
|
||||
dwarf_get_elf;
|
||||
dwarf_get_fde_at_pc;
|
||||
dwarf_get_fde_info_for_all_regs3;
|
||||
@ -139,6 +142,8 @@ global:
|
||||
dwarf_get_relocation_info;
|
||||
dwarf_get_relocation_info_count;
|
||||
dwarf_get_section_bytes;
|
||||
dwarf_get_section_max_offsets;
|
||||
dwarf_get_section_max_offsets_b;
|
||||
dwarf_get_str;
|
||||
dwarf_get_types;
|
||||
dwarf_get_vars;
|
||||
@ -152,6 +157,7 @@ global:
|
||||
dwarf_hasattr;
|
||||
dwarf_hasform;
|
||||
dwarf_highpc;
|
||||
dwarf_highpc_b;
|
||||
dwarf_init;
|
||||
dwarf_line_srcfileno;
|
||||
dwarf_lineaddr;
|
||||
@ -166,6 +172,7 @@ global:
|
||||
dwarf_loclist;
|
||||
dwarf_loclist_from_expr;
|
||||
dwarf_loclist_from_expr_a;
|
||||
dwarf_loclist_from_expr_b;
|
||||
dwarf_loclist_n;
|
||||
dwarf_lowpc;
|
||||
dwarf_new_die;
|
||||
@ -173,9 +180,12 @@ global:
|
||||
dwarf_new_fde;
|
||||
dwarf_next_cu_header;
|
||||
dwarf_next_cu_header_b;
|
||||
dwarf_next_cu_header_c;
|
||||
dwarf_next_types_section;
|
||||
dwarf_object_finish;
|
||||
dwarf_object_init;
|
||||
dwarf_offdie;
|
||||
dwarf_offdie_b;
|
||||
dwarf_producer_finish;
|
||||
dwarf_producer_init;
|
||||
dwarf_producer_init_b;
|
||||
@ -196,6 +206,7 @@ global:
|
||||
dwarf_seterrarg;
|
||||
dwarf_seterrhand;
|
||||
dwarf_siblingof;
|
||||
dwarf_siblingof_b;
|
||||
dwarf_srcfiles;
|
||||
dwarf_srclang;
|
||||
dwarf_srclines;
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 2007 John Birrell (jb@freebsd.org)
|
||||
* Copyright (c) 2009-2011 Kai Wang
|
||||
* Copyright (c) 2009-2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -24,7 +24,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: _libdwarf.h 2075 2011-10-27 03:47:28Z jkoshy $
|
||||
* $Id: _libdwarf.h 3106 2014-12-19 16:00:58Z kaiwang27 $
|
||||
*/
|
||||
|
||||
#ifndef __LIBDWARF_H_
|
||||
@ -89,6 +89,7 @@ extern struct _libdwarf_globals _libdwarf;
|
||||
goto gen_fail; \
|
||||
} while(0)
|
||||
|
||||
typedef struct _Dwarf_CU *Dwarf_CU;
|
||||
|
||||
struct _Dwarf_AttrDef {
|
||||
uint64_t ad_attrib; /* DW_AT_XXX */
|
||||
@ -147,14 +148,6 @@ struct _Dwarf_Die {
|
||||
STAILQ_ENTRY(_Dwarf_Die) die_pro_next; /* Next die in pro-die list. */
|
||||
};
|
||||
|
||||
struct _Dwarf_Loclist {
|
||||
Dwarf_Locdesc **ll_ldlist; /* Array of Locdesc pointer. */
|
||||
int ll_ldlen; /* Number of Locdesc. */
|
||||
Dwarf_Unsigned ll_offset; /* Offset in .debug_loc section. */
|
||||
Dwarf_Unsigned ll_length; /* Length (in bytes) of the loclist. */
|
||||
TAILQ_ENTRY(_Dwarf_Loclist) ll_next; /* Next loclist in list. */
|
||||
};
|
||||
|
||||
struct _Dwarf_P_Expr_Entry {
|
||||
Dwarf_Loc ee_loc; /* Location expression. */
|
||||
Dwarf_Unsigned ee_sym; /* Optional related reloc sym index. */
|
||||
@ -265,6 +258,8 @@ struct _Dwarf_Cie {
|
||||
Dwarf_Half cie_version; /* CIE version. */
|
||||
uint8_t *cie_augment; /* CIE augmentation (UTF-8). */
|
||||
Dwarf_Unsigned cie_ehdata; /* Optional EH Data. */
|
||||
uint8_t cie_addrsize; /* Address size. (DWARF4) */
|
||||
uint8_t cie_segmentsize; /* Segment size. (DWARF4) */
|
||||
Dwarf_Unsigned cie_caf; /* Code alignment factor. */
|
||||
Dwarf_Signed cie_daf; /* Data alignment factor. */
|
||||
Dwarf_Unsigned cie_ra; /* Return address register. */
|
||||
@ -333,11 +328,14 @@ struct _Dwarf_CU {
|
||||
uint64_t cu_lineno_offset; /* Offset into .debug_lineno. */
|
||||
uint8_t cu_pointer_size;/* Number of bytes in pointer. */
|
||||
uint8_t cu_dwarf_size; /* CU section dwarf size. */
|
||||
Dwarf_Sig8 cu_type_sig; /* Type unit's signature. */
|
||||
uint64_t cu_type_offset; /* Type unit's type offset. */
|
||||
Dwarf_Off cu_next_offset; /* Offset to the next CU. */
|
||||
uint64_t cu_1st_offset; /* First DIE offset. */
|
||||
int cu_pass2; /* Two pass DIE traverse. */
|
||||
Dwarf_LineInfo cu_lineinfo; /* Ptr to Dwarf_LineInfo. */
|
||||
Dwarf_Abbrev cu_abbrev_hash; /* Abbrev hash table. */
|
||||
Dwarf_Bool cu_is_info; /* Compilation/type unit flag. */
|
||||
STAILQ_ENTRY(_Dwarf_CU) cu_next; /* Next compilation unit. */
|
||||
};
|
||||
|
||||
@ -399,17 +397,21 @@ struct _Dwarf_Debug {
|
||||
Dwarf_Section *dbg_section; /* Dwarf section list. */
|
||||
Dwarf_Section *dbg_info_sec; /* Pointer to info section. */
|
||||
Dwarf_Off dbg_info_off; /* Current info section offset. */
|
||||
Dwarf_Section *dbg_types_sec; /* Pointer to type section. */
|
||||
Dwarf_Off dbg_types_off; /* Current types section offset. */
|
||||
Dwarf_Unsigned dbg_seccnt; /* Total number of dwarf sections. */
|
||||
int dbg_mode; /* Access mode. */
|
||||
int dbg_pointer_size; /* Object address size. */
|
||||
int dbg_offset_size; /* DWARF offset size. */
|
||||
int dbg_info_loaded; /* Flag indicating all CU loaded. */
|
||||
int dbg_types_loaded; /* Flag indicating all TU loaded. */
|
||||
Dwarf_Half dbg_machine; /* ELF machine architecture. */
|
||||
Dwarf_Handler dbg_errhand; /* Error handler. */
|
||||
Dwarf_Ptr dbg_errarg; /* Argument to the error handler. */
|
||||
STAILQ_HEAD(, _Dwarf_CU) dbg_cu;/* List of compilation units. */
|
||||
STAILQ_HEAD(, _Dwarf_CU) dbg_tu;/* List of type units. */
|
||||
Dwarf_CU dbg_cu_current; /* Ptr to the current CU. */
|
||||
TAILQ_HEAD(, _Dwarf_Loclist) dbg_loclist; /* List of location list. */
|
||||
Dwarf_CU dbg_tu_current; /* Ptr to the current TU. */
|
||||
Dwarf_NameSec dbg_globals; /* Ptr to pubnames lookup section. */
|
||||
Dwarf_NameSec dbg_pubtypes; /* Ptr to pubtypes lookup section. */
|
||||
Dwarf_NameSec dbg_weaks; /* Ptr to weaknames lookup section. */
|
||||
@ -532,13 +534,15 @@ int _dwarf_elf_get_section_info(void *, Dwarf_Half,
|
||||
Dwarf_Obj_Access_Section *, int *);
|
||||
void _dwarf_expr_cleanup(Dwarf_P_Debug);
|
||||
int _dwarf_expr_into_block(Dwarf_P_Expr, Dwarf_Error *);
|
||||
Dwarf_Section *_dwarf_find_next_types_section(Dwarf_Debug, Dwarf_Section *);
|
||||
Dwarf_Section *_dwarf_find_section(Dwarf_Debug, const char *);
|
||||
void _dwarf_frame_cleanup(Dwarf_Debug);
|
||||
int _dwarf_frame_fde_add_inst(Dwarf_P_Fde, Dwarf_Small,
|
||||
Dwarf_Unsigned, Dwarf_Unsigned, Dwarf_Error *);
|
||||
int _dwarf_frame_gen(Dwarf_P_Debug, Dwarf_Error *);
|
||||
int _dwarf_frame_get_fop(Dwarf_Debug, uint8_t *, Dwarf_Unsigned,
|
||||
Dwarf_Frame_Op **, Dwarf_Signed *, Dwarf_Error *);
|
||||
int _dwarf_frame_get_fop(Dwarf_Debug, uint8_t, uint8_t *,
|
||||
Dwarf_Unsigned, Dwarf_Frame_Op **, Dwarf_Signed *,
|
||||
Dwarf_Error *);
|
||||
int _dwarf_frame_get_internal_table(Dwarf_Fde, Dwarf_Addr,
|
||||
Dwarf_Regtable3 **, Dwarf_Addr *, Dwarf_Error *);
|
||||
int _dwarf_frame_interal_table_init(Dwarf_Debug, Dwarf_Error *);
|
||||
@ -553,9 +557,12 @@ Dwarf_Unsigned _dwarf_get_reloc_type(Dwarf_P_Debug, int);
|
||||
int _dwarf_get_reloc_size(Dwarf_Debug, Dwarf_Unsigned);
|
||||
void _dwarf_info_cleanup(Dwarf_Debug);
|
||||
int _dwarf_info_first_cu(Dwarf_Debug, Dwarf_Error *);
|
||||
int _dwarf_info_first_tu(Dwarf_Debug, Dwarf_Error *);
|
||||
int _dwarf_info_gen(Dwarf_P_Debug, Dwarf_Error *);
|
||||
int _dwarf_info_load(Dwarf_Debug, int, Dwarf_Error *);
|
||||
int _dwarf_info_load(Dwarf_Debug, Dwarf_Bool, Dwarf_Bool,
|
||||
Dwarf_Error *);
|
||||
int _dwarf_info_next_cu(Dwarf_Debug, Dwarf_Error *);
|
||||
int _dwarf_info_next_tu(Dwarf_Debug, Dwarf_Error *);
|
||||
void _dwarf_info_pro_cleanup(Dwarf_P_Debug);
|
||||
int _dwarf_init(Dwarf_Debug, Dwarf_Unsigned, Dwarf_Handler,
|
||||
Dwarf_Ptr, Dwarf_Error *);
|
||||
@ -563,20 +570,19 @@ int _dwarf_lineno_gen(Dwarf_P_Debug, Dwarf_Error *);
|
||||
int _dwarf_lineno_init(Dwarf_Die, uint64_t, Dwarf_Error *);
|
||||
void _dwarf_lineno_cleanup(Dwarf_LineInfo);
|
||||
void _dwarf_lineno_pro_cleanup(Dwarf_P_Debug);
|
||||
int _dwarf_loc_fill_locdesc(Dwarf_Debug, Dwarf_Locdesc *, uint8_t *,
|
||||
uint64_t, uint8_t, Dwarf_Error *);
|
||||
int _dwarf_loc_fill_locdesc(Dwarf_Debug, Dwarf_Locdesc *,
|
||||
uint8_t *, uint64_t, uint8_t, uint8_t, uint8_t,
|
||||
Dwarf_Error *);
|
||||
int _dwarf_loc_fill_locexpr(Dwarf_Debug, Dwarf_Locdesc **,
|
||||
uint8_t *, uint64_t, uint8_t, Dwarf_Error *);
|
||||
uint8_t *, uint64_t, uint8_t, uint8_t, uint8_t,
|
||||
Dwarf_Error *);
|
||||
int _dwarf_loc_add(Dwarf_Die, Dwarf_Attribute, Dwarf_Error *);
|
||||
int _dwarf_loc_expr_add_atom(Dwarf_Debug, uint8_t *, uint8_t *,
|
||||
Dwarf_Small, Dwarf_Unsigned, Dwarf_Unsigned, int *,
|
||||
Dwarf_Error *);
|
||||
int _dwarf_loclist_find(Dwarf_Debug, Dwarf_CU, uint64_t,
|
||||
Dwarf_Loclist *, Dwarf_Error *);
|
||||
void _dwarf_loclist_cleanup(Dwarf_Debug);
|
||||
void _dwarf_loclist_free(Dwarf_Loclist);
|
||||
int _dwarf_loclist_add(Dwarf_Debug, Dwarf_CU, uint64_t,
|
||||
Dwarf_Loclist *, Dwarf_Error *);
|
||||
Dwarf_Locdesc ***, Dwarf_Signed *, Dwarf_Unsigned *,
|
||||
Dwarf_Error *);
|
||||
void _dwarf_macinfo_cleanup(Dwarf_Debug);
|
||||
int _dwarf_macinfo_gen(Dwarf_P_Debug, Dwarf_Error *);
|
||||
int _dwarf_macinfo_init(Dwarf_Debug, Dwarf_Error *);
|
||||
@ -633,6 +639,7 @@ void _dwarf_strtab_cleanup(Dwarf_Debug);
|
||||
int _dwarf_strtab_gen(Dwarf_P_Debug, Dwarf_Error *);
|
||||
char *_dwarf_strtab_get_table(Dwarf_Debug);
|
||||
int _dwarf_strtab_init(Dwarf_Debug, Dwarf_Error *);
|
||||
void _dwarf_type_unit_cleanup(Dwarf_Debug);
|
||||
void _dwarf_write_block(void *, uint64_t *, uint8_t *, uint64_t);
|
||||
int _dwarf_write_block_alloc(uint8_t **, uint64_t *, uint64_t *,
|
||||
uint8_t *, uint64_t, Dwarf_Error *);
|
||||
|
@ -21,9 +21,9 @@
|
||||
.\" out of the use of this software, even if advised of the possibility of
|
||||
.\" such damage.
|
||||
.\"
|
||||
.\" $Id: dwarf.3 2075 2011-10-27 03:47:28Z jkoshy $
|
||||
.\" $Id: dwarf.3 3130 2014-12-21 20:06:29Z jkoshy $
|
||||
.\"
|
||||
.Dd September 17, 2011
|
||||
.Dd December 21, 2014
|
||||
.Os
|
||||
.Dt DWARF 3
|
||||
.Sh NAME
|
||||
@ -217,6 +217,8 @@ attribute.
|
||||
Retrieve an attribute descriptor.
|
||||
.It Fn dwarf_attrlist
|
||||
Retrieve attribute descriptors for a debugging information entry.
|
||||
.It Fn dwarf_attroffset
|
||||
Retrieve the section-relative offset of an attribute descriptor.
|
||||
.It Fn dwarf_attrval_flag
|
||||
Retrieve a
|
||||
.Dv DW_AT_FORM_flag
|
||||
@ -309,10 +311,17 @@ Retrieve range information from an FDE descriptor.
|
||||
.El
|
||||
.It Compilation Units
|
||||
.Bl -tag -compact
|
||||
.It Fn dwarf_get_cu_die_offset_given_cu_header_offset
|
||||
.It Xo
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset ,
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset_b
|
||||
.Xc
|
||||
Retrieve the offset of the debugging information entry for a
|
||||
compilation unit.
|
||||
.It Fn dwarf_next_cu_header , Fn dwarf_next_cu_header_b
|
||||
compilation or type unit.
|
||||
.It Xo
|
||||
.Fn dwarf_next_cu_header ,
|
||||
.Fn dwarf_next_cu_header_b ,
|
||||
.Fn dwarf_next_cu_header_c
|
||||
.Xc
|
||||
Step through compilation units in a debug context.
|
||||
.El
|
||||
.It Debugging Information Entries
|
||||
@ -329,13 +338,15 @@ Returns the
|
||||
attribute for a debugging information entry.
|
||||
.It Fn dwarf_dieoffset
|
||||
Retrieves the offset for a debugging information entry.
|
||||
.It Fn dwarf_highpc
|
||||
.It Fn dwarf_get_die_infotypes_flag
|
||||
Indicate the originating section for a debugging information entry.
|
||||
.It Fn dwarf_highpc , Fn dwarf_highpc_b
|
||||
Return the highest PC value for a debugging information entry.
|
||||
.It Fn dwarf_lowpc
|
||||
Return the lowest PC value for a debugging information entry.
|
||||
.It Fn dwarf_offdie
|
||||
.It Fn dwarf_offdie , Fn dwarf_offdie_b
|
||||
Retrieve a debugging information entry given an offset.
|
||||
.It Fn dwarf_siblingof
|
||||
.It Fn dwarf_siblingof , Fn dwarf_siblingof_b
|
||||
Retrieve the sibling descriptor for a debugging information entry.
|
||||
.It Fn dwarf_srclang
|
||||
Retrive the source language attribute for a debugging information
|
||||
@ -416,7 +427,11 @@ Return line number information for a compilation unit.
|
||||
Retrieve a location list entry.
|
||||
.It Fn dwarf_loclist , Fn dwarf_loclist_n
|
||||
Retrieve location expressions.
|
||||
.It Fn dwarf_loclist_from_expr , Fn dwarf_loclist_from_expr_a
|
||||
.It Xo
|
||||
.Fn dwarf_loclist_from_expr ,
|
||||
.Fn dwarf_loclist_from_expr_a ,
|
||||
.Fn dwarf_loclist_from_expr_b
|
||||
.Xc
|
||||
Translate a location expression into a location descriptor.
|
||||
.El
|
||||
.It Error Handling
|
||||
@ -513,6 +528,10 @@ and
|
||||
.Bl -tag -compact
|
||||
.It Fn dwarf_get_pubtypes , Fn dwarf_get_types
|
||||
Retrieve descriptors for user-defined types.
|
||||
.It Fn dwarf_next_types_section
|
||||
Step through
|
||||
.Dq \&.debug_types
|
||||
sections in a debug context.
|
||||
.It Fn dwarf_pubtype_cu_offset , Fn dwarf_type_cu_offset
|
||||
Return the offset for the compilation unit for a type.
|
||||
.It Fn dwarf_pubtype_die_offset , Fn dwarf_type_die_offset
|
||||
@ -699,9 +718,16 @@ addition to the per-debug context handlers supported by the SGI/GNU
|
||||
API, see the subsection
|
||||
.Sx Error Handling
|
||||
above.
|
||||
.El
|
||||
.Ss Extensions
|
||||
The following APIs are extensions specific to this implementation:
|
||||
.Bl -bullet -compact
|
||||
.It
|
||||
The following API is an extension:
|
||||
.Fn dwarf_producer_set_isa .
|
||||
.Fn dwarf_attroffset
|
||||
.It
|
||||
.Fn dwarf_next_types_section
|
||||
.It
|
||||
.Fn dwarf_producer_set_isa
|
||||
.El
|
||||
.Sh SEE ALSO
|
||||
.Xr elf 3
|
||||
|
@ -23,7 +23,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: dwarf.h 2075 2011-10-27 03:47:28Z jkoshy $
|
||||
* $Id: dwarf.h 3052 2014-05-26 20:36:24Z kaiwang27 $
|
||||
*/
|
||||
|
||||
#ifndef _DWARF_H_
|
||||
@ -93,6 +93,19 @@
|
||||
#define DW_TAG_lo_user 0x4080
|
||||
#define DW_TAG_hi_user 0xffff
|
||||
|
||||
/* GNU extensions. */
|
||||
#define DW_TAG_format_label 0x4101
|
||||
#define DW_TAG_function_template 0x4102
|
||||
#define DW_TAG_class_template 0x4103
|
||||
#define DW_TAG_GNU_BINCL 0x4104
|
||||
#define DW_TAG_GNU_EINCL 0x4105
|
||||
#define DW_TAG_GNU_template_template_parameter 0x4106
|
||||
#define DW_TAG_GNU_template_template_param 0x4106
|
||||
#define DW_TAG_GNU_template_parameter_pack 0x4107
|
||||
#define DW_TAG_GNU_formal_parameter_pack 0x4108
|
||||
#define DW_TAG_GNU_call_site 0x4109
|
||||
#define DW_TAG_GNU_call_site_parameter 0x410a
|
||||
|
||||
#define DW_CHILDREN_no 0x00
|
||||
#define DW_CHILDREN_yes 0x01
|
||||
|
||||
@ -195,6 +208,32 @@
|
||||
#define DW_AT_lo_user 0x2000
|
||||
#define DW_AT_hi_user 0x3fff
|
||||
|
||||
/* GNU extensions. */
|
||||
#define DW_AT_sf_names 0x2101
|
||||
#define DW_AT_src_info 0x2102
|
||||
#define DW_AT_mac_info 0x2103
|
||||
#define DW_AT_src_coords 0x2104
|
||||
#define DW_AT_body_begin 0x2105
|
||||
#define DW_AT_body_end 0x2106
|
||||
#define DW_AT_GNU_vector 0x2107
|
||||
#define DW_AT_GNU_guarded_by 0x2108
|
||||
#define DW_AT_GNU_pt_guarded_by 0x2109
|
||||
#define DW_AT_GNU_guarded 0x210a
|
||||
#define DW_AT_GNU_pt_guarded 0x210b
|
||||
#define DW_AT_GNU_locks_excluded 0x210c
|
||||
#define DW_AT_GNU_exclusive_locks_required 0x210d
|
||||
#define DW_AT_GNU_shared_locks_required 0x210e
|
||||
#define DW_AT_GNU_odr_signature 0x210f
|
||||
#define DW_AT_GNU_template_name 0x2110
|
||||
#define DW_AT_GNU_call_site_value 0x2111
|
||||
#define DW_AT_GNU_call_site_data_value 0x2112
|
||||
#define DW_AT_GNU_call_site_target 0x2113
|
||||
#define DW_AT_GNU_call_site_target_clobbered 0x2114
|
||||
#define DW_AT_GNU_tail_call 0x2115
|
||||
#define DW_AT_GNU_all_tail_call_sites 0x2116
|
||||
#define DW_AT_GNU_all_call_sites 0x2117
|
||||
#define DW_AT_GNU_all_source_call_sites 0x2118
|
||||
|
||||
#define DW_FORM_addr 0x01
|
||||
#define DW_FORM_block2 0x03
|
||||
#define DW_FORM_block4 0x04
|
||||
@ -220,6 +259,8 @@
|
||||
#define DW_FORM_exprloc 0x18
|
||||
#define DW_FORM_flag_present 0x19
|
||||
#define DW_FORM_ref_sig8 0x20
|
||||
#define DW_FORM_GNU_ref_alt 0x1f20
|
||||
#define DW_FORM_GNU_strp_alt 0x1f21
|
||||
|
||||
#define DW_OP_addr 0x03
|
||||
#define DW_OP_deref 0x06
|
||||
@ -376,9 +417,23 @@
|
||||
#define DW_OP_implicit_value 0x9e
|
||||
#define DW_OP_stack_value 0x9f
|
||||
#define DW_OP_lo_user 0xe0
|
||||
#define DW_OP_GNU_push_tls_address 0xe0
|
||||
#define DW_OP_hi_user 0xff
|
||||
|
||||
/* GNU extensions. */
|
||||
#define DW_OP_GNU_push_tls_address 0xe0
|
||||
#define DW_OP_GNU_uninit 0xf0
|
||||
#define DW_OP_GNU_encoded_addr 0xf1
|
||||
#define DW_OP_GNU_implicit_pointer 0xf2
|
||||
#define DW_OP_GNU_entry_value 0xf3
|
||||
#define DW_OP_GNU_const_type 0xf4
|
||||
#define DW_OP_GNU_regval_type 0xf5
|
||||
#define DW_OP_GNU_deref_type 0xf6
|
||||
#define DW_OP_GNU_convert 0xf7
|
||||
#define DW_OP_GNU_reinterpret 0xf9
|
||||
#define DW_OP_GNU_parameter_ref 0xfa
|
||||
#define DW_OP_GNU_addr_index 0xfb
|
||||
#define DW_OP_GNU_const_index 0xfc
|
||||
|
||||
#define DW_ATE_address 0x1
|
||||
#define DW_ATE_boolean 0x2
|
||||
#define DW_ATE_complex_float 0x3
|
||||
|
@ -22,7 +22,7 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_attr.3 2072 2011-10-27 03:26:49Z jkoshy $
|
||||
.\" $Id: dwarf_attr.3 3093 2014-09-02 22:09:40Z kaiwang27 $
|
||||
.\"
|
||||
.Dd April 8, 2010
|
||||
.Os
|
||||
@ -113,6 +113,7 @@ in argument
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_attrlist 3 ,
|
||||
.Xr dwarf_attroffset 3 ,
|
||||
.Xr dwarf_hasattr 3 ,
|
||||
.Xr dwarf_hasform 3 ,
|
||||
.Xr dwarf_whatattr 3 ,
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_attr.c 2072 2011-10-27 03:26:49Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_attr.c 3064 2014-06-06 19:35:55Z kaiwang27 $");
|
||||
|
||||
int
|
||||
dwarf_attr(Dwarf_Die die, Dwarf_Half attr, Dwarf_Attribute *atp,
|
||||
@ -113,6 +113,23 @@ dwarf_hasattr(Dwarf_Die die, Dwarf_Half attr, Dwarf_Bool *ret_bool,
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_attroffset(Dwarf_Attribute at, Dwarf_Off *ret_off, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Debug dbg;
|
||||
|
||||
dbg = at != NULL ? at->at_die->die_dbg : NULL;
|
||||
|
||||
if (at == NULL || ret_off == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ARGUMENT);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
*ret_off = at->at_offset;
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_lowpc(Dwarf_Die die, Dwarf_Addr *ret_lowpc, Dwarf_Error *error)
|
||||
{
|
||||
@ -138,9 +155,18 @@ dwarf_lowpc(Dwarf_Die die, Dwarf_Addr *ret_lowpc, Dwarf_Error *error)
|
||||
|
||||
int
|
||||
dwarf_highpc(Dwarf_Die die, Dwarf_Addr *ret_highpc, Dwarf_Error *error)
|
||||
{
|
||||
|
||||
return (dwarf_highpc_b(die, ret_highpc, NULL, NULL, error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_highpc_b(Dwarf_Die die, Dwarf_Addr *ret_highpc, Dwarf_Half *ret_form,
|
||||
enum Dwarf_Form_Class *ret_class, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Attribute at;
|
||||
Dwarf_Debug dbg;
|
||||
Dwarf_CU cu;
|
||||
|
||||
dbg = die != NULL ? die->die_dbg : NULL;
|
||||
|
||||
@ -156,6 +182,17 @@ dwarf_highpc(Dwarf_Die die, Dwarf_Addr *ret_highpc, Dwarf_Error *error)
|
||||
|
||||
*ret_highpc = at->u[0].u64;
|
||||
|
||||
if (ret_form != NULL) {
|
||||
*ret_form = at->at_form;
|
||||
}
|
||||
|
||||
if (ret_class != NULL) {
|
||||
cu = die->die_cu;
|
||||
*ret_class = dwarf_get_form_class(cu->cu_version,
|
||||
DW_AT_high_pc, cu->cu_length_size == 4 ? 4 : 8,
|
||||
at->at_form);
|
||||
}
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
|
86
contrib/elftoolchain/libdwarf/dwarf_attroffset.3
Normal file
86
contrib/elftoolchain/libdwarf/dwarf_attroffset.3
Normal file
@ -0,0 +1,86 @@
|
||||
.\" Copyright (c) 2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
.\" modification, are permitted provided that the following conditions
|
||||
.\" are met:
|
||||
.\" 1. Redistributions of source code must retain the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer.
|
||||
.\" 2. Redistributions in binary form must reproduce the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer in the
|
||||
.\" documentation and/or other materials provided with the distribution.
|
||||
.\"
|
||||
.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_attroffset.3 3115 2014-12-20 18:26:46Z jkoshy $
|
||||
.\"
|
||||
.Dd December 20, 2014
|
||||
.Os
|
||||
.Dt DWARF_ATTROFFSET 3
|
||||
.Sh NAME
|
||||
.Nm dwarf_attroffset
|
||||
.Nd retrieve the section-relative offset of an attribute descriptor
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
.Sh SYNOPSIS
|
||||
.In libdwarf.h
|
||||
.Ft int
|
||||
.Fo dwarf_attroffset
|
||||
.Fa "Dwarf_Attribute at"
|
||||
.Fa "Dwarf_Off *ret_off"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
Function
|
||||
.Fn dwarf_attroffset
|
||||
retrieves the section-relative offset of the attribute descriptor
|
||||
referenced by argument
|
||||
.Ar at .
|
||||
.Pp
|
||||
Argument
|
||||
.Ar ret_off
|
||||
should point to a location that is to hold the returned
|
||||
section-relative offset.
|
||||
If argument
|
||||
.Ar err
|
||||
is non-NULL, it is used to return an error descriptor in case of an
|
||||
error.
|
||||
.Sh RETURN VALUES
|
||||
On success, function
|
||||
.Fn dwarf_attroffset
|
||||
returns
|
||||
.Dv DW_DLV_OK .
|
||||
.Pp
|
||||
In case of an error, it returns
|
||||
.Dv DW_DLV_ERROR
|
||||
and sets argument
|
||||
.Ar err .
|
||||
.Sh COMPATIBILITY
|
||||
This function is an extension to the
|
||||
.Xr DWARF 3
|
||||
API.
|
||||
.Sh ERRORS
|
||||
The
|
||||
.Fn dwarf_attroffset
|
||||
function may fail with the following errors:
|
||||
.Bl -tag -width ".Bq Er DW_DLE_ARGUMENT"
|
||||
.It Bq Er DW_DLE_ARGUMENT
|
||||
Either of the arguments
|
||||
.Ar at
|
||||
or
|
||||
.Ar ret_off
|
||||
was NULL.
|
||||
.El
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_attr 3
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_attrval.c 2072 2011-10-27 03:26:49Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_attrval.c 2977 2014-01-21 20:13:31Z kaiwang27 $");
|
||||
|
||||
int
|
||||
dwarf_attrval_flag(Dwarf_Die die, Dwarf_Half attr, Dwarf_Bool *valp, Dwarf_Error *err)
|
||||
|
@ -22,7 +22,7 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_attrval_signed.3 2072 2011-10-27 03:26:49Z jkoshy $
|
||||
.\" $Id: dwarf_attrval_signed.3 2980 2014-01-21 20:15:54Z kaiwang27 $
|
||||
.\"
|
||||
.Dd January 18, 2014
|
||||
.Os
|
||||
|
@ -1,4 +1,4 @@
|
||||
.\" Copyright (c) 2010 Kai Wang
|
||||
.\" Copyright (c) 2010,2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
@ -22,15 +22,17 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_child.3 2122 2011-11-09 15:35:14Z jkoshy $
|
||||
.\" $Id: dwarf_child.3 3127 2014-12-21 19:09:19Z jkoshy $
|
||||
.\"
|
||||
.Dd November 9, 2011
|
||||
.Dd December 21, 2014
|
||||
.Os
|
||||
.Dt DWARF_CHILD 3
|
||||
.Sh NAME
|
||||
.Nm dwarf_child ,
|
||||
.Nm dwarf_offdie ,
|
||||
.Nm dwarf_offdie_b ,
|
||||
.Nm dwarf_siblingof ,
|
||||
.Nm dwarf_offdie
|
||||
.Nm dwarf_siblingof_b
|
||||
.Nd retrieve DWARF Debugging Information Entry descriptors
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
@ -39,6 +41,21 @@
|
||||
.Ft int
|
||||
.Fn dwarf_child "Dwarf_Die die" "Dwarf_Die *ret_die" "Dwarf_Error *err"
|
||||
.Ft int
|
||||
.Fo dwarf_offdie
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Off offset"
|
||||
.Fa "Dwarf_Die *ret_die"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_offdie_b
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Off offset"
|
||||
.Fa "Dwarf_Bool is_info"
|
||||
.Fa "Dwarf_Die *ret_die"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_siblingof
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Die die"
|
||||
@ -46,10 +63,11 @@
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_offdie
|
||||
.Fo dwarf_siblingof_b
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Off offset"
|
||||
.Fa "Dwarf_Die die"
|
||||
.Fa "Dwarf_Die *ret_die"
|
||||
.Fa "Dwarf_Bool is_info"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
@ -92,6 +110,34 @@ may be used together to traverse the tree of debugging information
|
||||
entry descriptors for a compilation unit.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_siblingof_b
|
||||
is identical to the function
|
||||
.Fn dwarf_siblingof
|
||||
except that it can retrieve the sibling descriptor from either the
|
||||
current compilation unit or type unit.
|
||||
If argument
|
||||
.Ar is_info
|
||||
is non-zero, the function behaves identically to function
|
||||
.Fn dwarf_siblingof .
|
||||
If argument
|
||||
.Ar is_info
|
||||
is zero, the descriptor referred by argument
|
||||
.Ar die
|
||||
should be associated with a debugging information entry in the
|
||||
type unit.
|
||||
The function will store the sibling of the descriptor in the location
|
||||
pointed to by argument
|
||||
.Ar ret_die .
|
||||
If argument
|
||||
.Ar is_info
|
||||
is zero and argument
|
||||
.Ar die
|
||||
is
|
||||
.Dv NULL ,
|
||||
the first debugging information entry descriptor for the
|
||||
current type unit will be returned.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_offdie
|
||||
retrieves the debugging information entry descriptor at global offset
|
||||
.Ar offset
|
||||
@ -101,6 +147,31 @@ section of the object associated with argument
|
||||
.Ar dbg .
|
||||
The returned descriptor is written to the location pointed to by argument
|
||||
.Ar ret_die .
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_offdie_b
|
||||
is identical to the function
|
||||
.Fn dwarf_offdie
|
||||
except that it can retrieve the debugging information entry descriptor at
|
||||
global offset
|
||||
.Ar offset
|
||||
from either of the
|
||||
.Dq .debug_info
|
||||
and
|
||||
.Dq .debug_types
|
||||
sections of the object associated with argument
|
||||
.Ar dbg .
|
||||
If argument
|
||||
.Ar is_info
|
||||
is non-zero, the function will retrieve the debugging information
|
||||
entry from the
|
||||
.Dq .debug_info
|
||||
section, otherwise the function will retrieve the debugging
|
||||
information entry from the
|
||||
.Dq .debug_types
|
||||
section.
|
||||
The returned descriptor is written to the location pointed to by argument
|
||||
.Ar ret_die .
|
||||
.Ss Memory Management
|
||||
The memory area used for the
|
||||
.Vt Dwarf_Die
|
||||
@ -128,14 +199,18 @@ argument
|
||||
if it is not NULL.
|
||||
.It Bq Er DW_DLV_NO_ENTRY
|
||||
For functions
|
||||
.Fn dwarf_child
|
||||
.Fn dwarf_child ,
|
||||
.Fn dwarf_siblingof
|
||||
and
|
||||
.Fn dwarf_siblingof ,
|
||||
.Fn dwarf_siblingof_b ,
|
||||
the descriptor denoted by argument
|
||||
.Ar die
|
||||
did not have a child or sibling.
|
||||
For function
|
||||
.Fn dwarf_offdie ,
|
||||
.Pp
|
||||
For functions
|
||||
.Fn dwarf_offdie
|
||||
and
|
||||
.Fn dwarf_offdie_b ,
|
||||
there was no debugging information entry at the offset specified by
|
||||
argument
|
||||
.Ar offset .
|
||||
@ -199,4 +274,5 @@ do {
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_errmsg 3 ,
|
||||
.Xr dwarf_get_die_infotypes_flag.3 ,
|
||||
.Xr dwarf_next_cu_header 3
|
||||
|
@ -1,5 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 2007 John Birrell (jb@freebsd.org)
|
||||
* Copyright (c) 2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -26,14 +27,15 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_cu.c 2072 2011-10-27 03:26:49Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_cu.c 3041 2014-05-18 15:11:03Z kaiwang27 $");
|
||||
|
||||
int
|
||||
dwarf_next_cu_header_b(Dwarf_Debug dbg, Dwarf_Unsigned *cu_length,
|
||||
Dwarf_Half *cu_version, Dwarf_Off *cu_abbrev_offset,
|
||||
Dwarf_Half *cu_pointer_size, Dwarf_Half *cu_offset_size,
|
||||
Dwarf_Half *cu_extension_size, Dwarf_Unsigned *cu_next_offset,
|
||||
Dwarf_Error *error)
|
||||
dwarf_next_cu_header_c(Dwarf_Debug dbg, Dwarf_Bool is_info,
|
||||
Dwarf_Unsigned *cu_length, Dwarf_Half *cu_version,
|
||||
Dwarf_Off *cu_abbrev_offset, Dwarf_Half *cu_pointer_size,
|
||||
Dwarf_Half *cu_offset_size, Dwarf_Half *cu_extension_size,
|
||||
Dwarf_Sig8 *type_signature, Dwarf_Unsigned *type_offset,
|
||||
Dwarf_Unsigned *cu_next_offset, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_CU cu;
|
||||
int ret;
|
||||
@ -43,10 +45,17 @@ dwarf_next_cu_header_b(Dwarf_Debug dbg, Dwarf_Unsigned *cu_length,
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
if (dbg->dbg_cu_current == NULL)
|
||||
ret = _dwarf_info_first_cu(dbg, error);
|
||||
else
|
||||
ret = _dwarf_info_next_cu(dbg, error);
|
||||
if (is_info) {
|
||||
if (dbg->dbg_cu_current == NULL)
|
||||
ret = _dwarf_info_first_cu(dbg, error);
|
||||
else
|
||||
ret = _dwarf_info_next_cu(dbg, error);
|
||||
} else {
|
||||
if (dbg->dbg_tu_current == NULL)
|
||||
ret = _dwarf_info_first_tu(dbg, error);
|
||||
else
|
||||
ret = _dwarf_info_next_tu(dbg, error);
|
||||
}
|
||||
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
@ -54,11 +63,19 @@ dwarf_next_cu_header_b(Dwarf_Debug dbg, Dwarf_Unsigned *cu_length,
|
||||
} else if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
|
||||
if (dbg->dbg_cu_current == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
if (is_info) {
|
||||
if (dbg->dbg_cu_current == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
cu = dbg->dbg_cu_current;
|
||||
} else {
|
||||
if (dbg->dbg_tu_current == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
cu = dbg->dbg_tu_current;
|
||||
}
|
||||
cu = dbg->dbg_cu_current;
|
||||
|
||||
if (cu_length)
|
||||
*cu_length = cu->cu_length;
|
||||
@ -81,11 +98,32 @@ dwarf_next_cu_header_b(Dwarf_Debug dbg, Dwarf_Unsigned *cu_length,
|
||||
*cu_extension_size = 4;
|
||||
}
|
||||
if (cu_next_offset)
|
||||
*cu_next_offset = dbg->dbg_cu_current->cu_next_offset;
|
||||
*cu_next_offset = cu->cu_next_offset;
|
||||
|
||||
if (!is_info) {
|
||||
if (type_signature)
|
||||
*type_signature = cu->cu_type_sig;
|
||||
if (type_offset)
|
||||
*type_offset = cu->cu_type_offset;
|
||||
}
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
dwarf_next_cu_header_b(Dwarf_Debug dbg, Dwarf_Unsigned *cu_length,
|
||||
Dwarf_Half *cu_version, Dwarf_Off *cu_abbrev_offset,
|
||||
Dwarf_Half *cu_pointer_size, Dwarf_Half *cu_offset_size,
|
||||
Dwarf_Half *cu_extension_size, Dwarf_Unsigned *cu_next_offset,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
|
||||
return (dwarf_next_cu_header_c(dbg, 1, cu_length, cu_version,
|
||||
cu_abbrev_offset, cu_pointer_size, cu_offset_size,
|
||||
cu_extension_size, NULL, NULL, cu_next_offset, error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_next_cu_header(Dwarf_Debug dbg, Dwarf_Unsigned *cu_length,
|
||||
Dwarf_Half *cu_version, Dwarf_Off *cu_abbrev_offset,
|
||||
@ -97,3 +135,27 @@ dwarf_next_cu_header(Dwarf_Debug dbg, Dwarf_Unsigned *cu_length,
|
||||
cu_abbrev_offset, cu_pointer_size, NULL, NULL, cu_next_offset,
|
||||
error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_next_types_section(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
{
|
||||
|
||||
/* Free resource allocated for current .debug_types section. */
|
||||
_dwarf_type_unit_cleanup(dbg);
|
||||
dbg->dbg_types_loaded = 0;
|
||||
dbg->dbg_types_off = 0;
|
||||
|
||||
/* Reset type unit pointer. */
|
||||
dbg->dbg_tu_current = NULL;
|
||||
|
||||
/* Search for the next .debug_types section. */
|
||||
dbg->dbg_types_sec = _dwarf_find_next_types_section(dbg,
|
||||
dbg->dbg_types_sec);
|
||||
|
||||
if (dbg->dbg_types_sec == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 2007 John Birrell (jb@freebsd.org)
|
||||
* Copyright (c) 2009,2011 Kai Wang
|
||||
* Copyright (c) 2009,2011,2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -27,12 +27,13 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_die.c 2073 2011-10-27 03:30:47Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_die.c 3039 2014-05-18 15:10:56Z kaiwang27 $");
|
||||
|
||||
int
|
||||
dwarf_child(Dwarf_Die die, Dwarf_Die *ret_die, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Debug dbg;
|
||||
Dwarf_Section *ds;
|
||||
Dwarf_CU cu;
|
||||
int ret;
|
||||
|
||||
@ -48,9 +49,9 @@ dwarf_child(Dwarf_Die die, Dwarf_Die *ret_die, Dwarf_Error *error)
|
||||
|
||||
dbg = die->die_dbg;
|
||||
cu = die->die_cu;
|
||||
ret = _dwarf_die_parse(die->die_dbg, dbg->dbg_info_sec, cu,
|
||||
cu->cu_dwarf_size, die->die_next_off, cu->cu_next_offset,
|
||||
ret_die, 0, error);
|
||||
ds = cu->cu_is_info ? dbg->dbg_info_sec : dbg->dbg_types_sec;
|
||||
ret = _dwarf_die_parse(die->die_dbg, ds, cu, cu->cu_dwarf_size,
|
||||
die->die_next_off, cu->cu_next_offset, ret_die, 0, error);
|
||||
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
@ -62,11 +63,12 @@ dwarf_child(Dwarf_Die die, Dwarf_Die *ret_die, Dwarf_Error *error)
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_siblingof(Dwarf_Debug dbg, Dwarf_Die die, Dwarf_Die *ret_die,
|
||||
Dwarf_Error *error)
|
||||
dwarf_siblingof_b(Dwarf_Debug dbg, Dwarf_Die die, Dwarf_Die *ret_die,
|
||||
Dwarf_Bool is_info, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_CU cu;
|
||||
Dwarf_Attribute at;
|
||||
Dwarf_Section *ds;
|
||||
uint64_t offset;
|
||||
int ret, search_sibling;
|
||||
|
||||
@ -75,15 +77,27 @@ dwarf_siblingof(Dwarf_Debug dbg, Dwarf_Die die, Dwarf_Die *ret_die,
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
if ((cu = dbg->dbg_cu_current) == NULL) {
|
||||
ds = is_info ? dbg->dbg_info_sec : dbg->dbg_types_sec;
|
||||
cu = is_info ? dbg->dbg_cu_current : dbg->dbg_tu_current;
|
||||
|
||||
if (cu == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_DIE_NO_CU_CONTEXT);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
/* Application requests the first DIE in this CU. */
|
||||
if (die == NULL)
|
||||
return (dwarf_offdie(dbg, cu->cu_1st_offset, ret_die,
|
||||
error));
|
||||
return (dwarf_offdie_b(dbg, cu->cu_1st_offset, is_info,
|
||||
ret_die, error));
|
||||
|
||||
/*
|
||||
* Check if the `is_info' flag matches the debug section the
|
||||
* DIE belongs to.
|
||||
*/
|
||||
if (is_info != die->die_cu->cu_is_info) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ARGUMENT);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
/*
|
||||
* If the DIE doesn't have any children, its sibling sits next
|
||||
@ -108,9 +122,8 @@ dwarf_siblingof(Dwarf_Debug dbg, Dwarf_Die die, Dwarf_Die *ret_die,
|
||||
}
|
||||
}
|
||||
|
||||
ret = _dwarf_die_parse(die->die_dbg, dbg->dbg_info_sec, cu,
|
||||
cu->cu_dwarf_size, offset, cu->cu_next_offset, ret_die,
|
||||
search_sibling, error);
|
||||
ret = _dwarf_die_parse(die->die_dbg, ds, cu, cu->cu_dwarf_size, offset,
|
||||
cu->cu_next_offset, ret_die, search_sibling, error);
|
||||
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
@ -121,21 +134,31 @@ dwarf_siblingof(Dwarf_Debug dbg, Dwarf_Die die, Dwarf_Die *ret_die,
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
dwarf_siblingof(Dwarf_Debug dbg, Dwarf_Die die, Dwarf_Die *ret_die,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
|
||||
return (dwarf_siblingof_b(dbg, die, ret_die, 1, error));
|
||||
}
|
||||
|
||||
static int
|
||||
_dwarf_search_die_within_cu(Dwarf_Debug dbg, Dwarf_CU cu, Dwarf_Off offset,
|
||||
Dwarf_Die *ret_die, Dwarf_Error *error)
|
||||
_dwarf_search_die_within_cu(Dwarf_Debug dbg, Dwarf_Section *s, Dwarf_CU cu,
|
||||
Dwarf_Off offset, Dwarf_Die *ret_die, Dwarf_Error *error)
|
||||
{
|
||||
|
||||
assert(dbg != NULL && cu != NULL && ret_die != NULL);
|
||||
|
||||
return (_dwarf_die_parse(dbg, dbg->dbg_info_sec, cu, cu->cu_dwarf_size,
|
||||
return (_dwarf_die_parse(dbg, s, cu, cu->cu_dwarf_size,
|
||||
offset, cu->cu_next_offset, ret_die, 0, error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_offdie(Dwarf_Debug dbg, Dwarf_Off offset, Dwarf_Die *ret_die,
|
||||
Dwarf_Error *error)
|
||||
dwarf_offdie_b(Dwarf_Debug dbg, Dwarf_Off offset, Dwarf_Bool is_info,
|
||||
Dwarf_Die *ret_die, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Section *ds;
|
||||
Dwarf_CU cu;
|
||||
int ret;
|
||||
|
||||
@ -144,11 +167,13 @@ dwarf_offdie(Dwarf_Debug dbg, Dwarf_Off offset, Dwarf_Die *ret_die,
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
ds = is_info ? dbg->dbg_info_sec : dbg->dbg_types_sec;
|
||||
cu = is_info ? dbg->dbg_cu_current : dbg->dbg_tu_current;
|
||||
|
||||
/* First search the current CU. */
|
||||
if (dbg->dbg_cu_current != NULL) {
|
||||
cu = dbg->dbg_cu_current;
|
||||
if (cu != NULL) {
|
||||
if (offset > cu->cu_offset && offset < cu->cu_next_offset) {
|
||||
ret = _dwarf_search_die_within_cu(dbg, cu, offset,
|
||||
ret = _dwarf_search_die_within_cu(dbg, ds, cu, offset,
|
||||
ret_die, error);
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
@ -160,27 +185,52 @@ dwarf_offdie(Dwarf_Debug dbg, Dwarf_Off offset, Dwarf_Die *ret_die,
|
||||
}
|
||||
|
||||
/* Search other CUs. */
|
||||
ret = _dwarf_info_load(dbg, 1, error);
|
||||
ret = _dwarf_info_load(dbg, 1, is_info, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
|
||||
STAILQ_FOREACH(cu, &dbg->dbg_cu, cu_next) {
|
||||
if (offset < cu->cu_offset || offset > cu->cu_next_offset)
|
||||
continue;
|
||||
ret = _dwarf_search_die_within_cu(dbg, cu, offset,
|
||||
ret_die, error);
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
} else if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
return (DW_DLV_OK);
|
||||
if (is_info) {
|
||||
STAILQ_FOREACH(cu, &dbg->dbg_cu, cu_next) {
|
||||
if (offset < cu->cu_offset ||
|
||||
offset > cu->cu_next_offset)
|
||||
continue;
|
||||
ret = _dwarf_search_die_within_cu(dbg, ds, cu, offset,
|
||||
ret_die, error);
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
} else if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
} else {
|
||||
STAILQ_FOREACH(cu, &dbg->dbg_tu, cu_next) {
|
||||
if (offset < cu->cu_offset ||
|
||||
offset > cu->cu_next_offset)
|
||||
continue;
|
||||
ret = _dwarf_search_die_within_cu(dbg, ds, cu, offset,
|
||||
ret_die, error);
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
} else if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
}
|
||||
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_offdie(Dwarf_Debug dbg, Dwarf_Off offset, Dwarf_Die *ret_die,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
|
||||
return (dwarf_offdie_b(dbg, offset, 1, ret_die, error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_tag(Dwarf_Die die, Dwarf_Half *tag, Dwarf_Error *error)
|
||||
{
|
||||
@ -293,9 +343,9 @@ dwarf_die_abbrev_code(Dwarf_Die die)
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_get_cu_die_offset_given_cu_header_offset(Dwarf_Debug dbg,
|
||||
Dwarf_Off in_cu_header_offset, Dwarf_Off *out_cu_die_offset,
|
||||
Dwarf_Error *error)
|
||||
dwarf_get_cu_die_offset_given_cu_header_offset_b(Dwarf_Debug dbg,
|
||||
Dwarf_Off in_cu_header_offset, Dwarf_Bool is_info,
|
||||
Dwarf_Off *out_cu_die_offset, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_CU cu;
|
||||
|
||||
@ -304,10 +354,19 @@ dwarf_get_cu_die_offset_given_cu_header_offset(Dwarf_Debug dbg,
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
STAILQ_FOREACH(cu, &dbg->dbg_cu, cu_next) {
|
||||
if (cu->cu_offset == in_cu_header_offset) {
|
||||
*out_cu_die_offset = cu->cu_1st_offset;
|
||||
break;
|
||||
if (is_info) {
|
||||
STAILQ_FOREACH(cu, &dbg->dbg_cu, cu_next) {
|
||||
if (cu->cu_offset == in_cu_header_offset) {
|
||||
*out_cu_die_offset = cu->cu_1st_offset;
|
||||
break;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
STAILQ_FOREACH(cu, &dbg->dbg_tu, cu_next) {
|
||||
if (cu->cu_offset == in_cu_header_offset) {
|
||||
*out_cu_die_offset = cu->cu_1st_offset;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -319,6 +378,16 @@ dwarf_get_cu_die_offset_given_cu_header_offset(Dwarf_Debug dbg,
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_get_cu_die_offset_given_cu_header_offset(Dwarf_Debug dbg,
|
||||
Dwarf_Off in_cu_header_offset, Dwarf_Off *out_cu_die_offset,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
|
||||
return (dwarf_get_cu_die_offset_given_cu_header_offset_b(dbg,
|
||||
in_cu_header_offset, 1, out_cu_die_offset, error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_get_address_size(Dwarf_Debug dbg, Dwarf_Half *addr_size,
|
||||
Dwarf_Error *error)
|
||||
@ -333,3 +402,12 @@ dwarf_get_address_size(Dwarf_Debug dbg, Dwarf_Half *addr_size,
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
Dwarf_Bool
|
||||
dwarf_get_die_infotypes_flag(Dwarf_Die die)
|
||||
{
|
||||
|
||||
assert(die != NULL);
|
||||
|
||||
return (die->die_cu->cu_is_info);
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
.\" Copyright (c) 2010 Kai Wang
|
||||
.\" Copyright (c) 2010,2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
@ -22,16 +22,17 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_dieoffset.3 2073 2011-10-27 03:30:47Z jkoshy $
|
||||
.\" $Id: dwarf_dieoffset.3 3129 2014-12-21 20:06:26Z jkoshy $
|
||||
.\"
|
||||
.Dd April 17, 2010
|
||||
.Dd December 21, 2014
|
||||
.Os
|
||||
.Dt DWARF_DIEOFFSET 3
|
||||
.Sh NAME
|
||||
.Nm dwarf_die_CU_offset ,
|
||||
.Nm dwarf_die_CU_offset_range ,
|
||||
.Nm dwarf_dieoffset ,
|
||||
.Nm dwarf_get_cu_die_offset_given_cu_header_offset
|
||||
.Nm dwarf_get_cu_die_offset_given_cu_header_offset ,
|
||||
.Nm dwarf_get_cu_die_offset_given_cu_header_offset_b
|
||||
.Nd return offsets of DWARF debugging information entries
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
@ -63,6 +64,14 @@
|
||||
.Fa "Dwarf_Off *out_cu_die_offset"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_get_cu_die_offset_given_cu_header_offset_b
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Off in_cu_header_offset"
|
||||
.Fa "Dwarf_Bool is_info"
|
||||
.Fa "Dwarf_Off *out_cu_die_offset"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
These functions are used to retrieve offsets for DWARF debugging
|
||||
information entries.
|
||||
@ -114,7 +123,7 @@ an error.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset
|
||||
returns the offset for the debugging information entry for a
|
||||
returns the offset for the first debugging information entry for a
|
||||
compilation unit, given an offset to the header of the compilation
|
||||
unit.
|
||||
Argument
|
||||
@ -131,8 +140,30 @@ If argument
|
||||
.Ar err
|
||||
is non-NULL, it will be used to return an error descriptor in case of
|
||||
an error.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset_b
|
||||
behaves identically to the function
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset
|
||||
when the argument
|
||||
.Ar is_info
|
||||
is non-zero.
|
||||
When the argument
|
||||
.Ar is_info
|
||||
is zero, function
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset_b
|
||||
returns the offset for the first debugging information entry for a
|
||||
type unit, given an offset to the header of the type unit in argument
|
||||
.Ar in_cu_header_offset .
|
||||
Argument
|
||||
.Ar out_cu_die_offset
|
||||
points to a location that will hold the returned offset.
|
||||
If the argument
|
||||
.Ar err
|
||||
is non-NULL, it will be used to return an error descriptor in case of
|
||||
an error.
|
||||
.Sh RETURN VALUES
|
||||
On success, these functions returns
|
||||
On success, these functions return
|
||||
.Dv DW_DLV_OK .
|
||||
In case of an error, these functions return
|
||||
.Dv DW_DLV_ERROR
|
||||
@ -141,11 +172,13 @@ and set argument
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset
|
||||
and
|
||||
.Fn dwarf_get_cu_die_offset_given_cu_header_offset_b
|
||||
returns
|
||||
.Dv DW_DLV_NO_ENTRY
|
||||
and sets argument
|
||||
.Ar err
|
||||
if there is no compilation unit located at the
|
||||
if there is no compilation or type unit located at the
|
||||
offset specified in argument
|
||||
.Ar in_cu_header_offset .
|
||||
.Sh ERRORS
|
||||
@ -169,4 +202,5 @@ specified an unknown offset.
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_next_cu_header 3 ,
|
||||
.Xr dwarf_offdie 3
|
||||
.Xr dwarf_offdie 3 ,
|
||||
.Xr dwarf_offdie_b 3
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_dump.c 2073 2011-10-27 03:30:47Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_dump.c 3052 2014-05-26 20:36:24Z kaiwang27 $");
|
||||
|
||||
int
|
||||
dwarf_get_ACCESS_name(unsigned access, const char **s)
|
||||
@ -250,6 +250,54 @@ dwarf_get_AT_name(unsigned attr, const char **s)
|
||||
*s = "DW_AT_visibility"; break;
|
||||
case DW_AT_vtable_elem_location:
|
||||
*s = "DW_AT_vtable_elem_location"; break;
|
||||
case DW_AT_sf_names:
|
||||
*s = "DW_AT_sf_names"; break;
|
||||
case DW_AT_src_info:
|
||||
*s = "DW_AT_src_info"; break;
|
||||
case DW_AT_mac_info:
|
||||
*s = "DW_AT_mac_info"; break;
|
||||
case DW_AT_src_coords:
|
||||
*s = "DW_AT_src_coords"; break;
|
||||
case DW_AT_body_begin:
|
||||
*s = "DW_AT_body_begin"; break;
|
||||
case DW_AT_body_end:
|
||||
*s = "DW_AT_body_end"; break;
|
||||
case DW_AT_GNU_vector:
|
||||
*s = "DW_AT_GNU_vector"; break;
|
||||
case DW_AT_GNU_guarded_by:
|
||||
*s = "DW_AT_GNU_guarded_by"; break;
|
||||
case DW_AT_GNU_pt_guarded_by:
|
||||
*s = "DW_AT_GNU_pt_guarded_by"; break;
|
||||
case DW_AT_GNU_guarded:
|
||||
*s = "DW_AT_GNU_guarded"; break;
|
||||
case DW_AT_GNU_pt_guarded:
|
||||
*s = "DW_AT_GNU_pt_guarded"; break;
|
||||
case DW_AT_GNU_locks_excluded:
|
||||
*s = "DW_AT_GNU_locks_excluded"; break;
|
||||
case DW_AT_GNU_exclusive_locks_required:
|
||||
*s = "DW_AT_GNU_exclusive_locks_required"; break;
|
||||
case DW_AT_GNU_shared_locks_required:
|
||||
*s = "DW_AT_GNU_shared_locks_required"; break;
|
||||
case DW_AT_GNU_odr_signature:
|
||||
*s = "DW_AT_GNU_odr_signature"; break;
|
||||
case DW_AT_GNU_template_name:
|
||||
*s = "DW_AT_GNU_template_name"; break;
|
||||
case DW_AT_GNU_call_site_value:
|
||||
*s = "DW_AT_GNU_call_site_value"; break;
|
||||
case DW_AT_GNU_call_site_data_value:
|
||||
*s = "DW_AT_GNU_call_site_data_value"; break;
|
||||
case DW_AT_GNU_call_site_target:
|
||||
*s = "DW_AT_GNU_call_site_target"; break;
|
||||
case DW_AT_GNU_call_site_target_clobbered:
|
||||
*s = "DW_AT_GNU_call_site_target_clobbered"; break;
|
||||
case DW_AT_GNU_tail_call:
|
||||
*s = "DW_AT_GNU_tail_call"; break;
|
||||
case DW_AT_GNU_all_tail_call_sites:
|
||||
*s = "DW_AT_GNU_all_tail_call_sites"; break;
|
||||
case DW_AT_GNU_all_call_sites:
|
||||
*s = "DW_AT_GNU_all_call_sites"; break;
|
||||
case DW_AT_GNU_all_source_call_sites:
|
||||
*s = "DW_AT_GNU_all_source_call_sites"; break;
|
||||
default:
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
@ -1094,6 +1142,30 @@ dwarf_get_OP_name(unsigned op, const char **s)
|
||||
*s = "DW_OP_stack_value"; break;
|
||||
case DW_OP_GNU_push_tls_address:
|
||||
*s = "DW_OP_GNU_push_tls_address"; break;
|
||||
case DW_OP_GNU_uninit:
|
||||
*s = "DW_OP_GNU_uninit"; break;
|
||||
case DW_OP_GNU_encoded_addr:
|
||||
*s = "DW_OP_GNU_encoded_addr"; break;
|
||||
case DW_OP_GNU_implicit_pointer:
|
||||
*s = "DW_OP_GNU_implicit_pointer"; break;
|
||||
case DW_OP_GNU_entry_value:
|
||||
*s = "DW_OP_GNU_entry_value"; break;
|
||||
case DW_OP_GNU_const_type:
|
||||
*s = "DW_OP_GNU_const_type"; break;
|
||||
case DW_OP_GNU_regval_type:
|
||||
*s = "DW_OP_GNU_regval_type"; break;
|
||||
case DW_OP_GNU_deref_type:
|
||||
*s = "DW_OP_GNU_deref_type"; break;
|
||||
case DW_OP_GNU_convert:
|
||||
*s = "DW_OP_GNU_convert"; break;
|
||||
case DW_OP_GNU_reinterpret:
|
||||
*s = "DW_OP_GNU_reinterpret"; break;
|
||||
case DW_OP_GNU_parameter_ref:
|
||||
*s = "DW_OP_GNU_parameter_ref"; break;
|
||||
case DW_OP_GNU_addr_index:
|
||||
*s = "DW_OP_GNU_addr_index"; break;
|
||||
case DW_OP_GNU_const_index:
|
||||
*s = "DW_OP_GNU_const_index"; break;
|
||||
default:
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
@ -1244,6 +1316,26 @@ dwarf_get_TAG_name(unsigned tag, const char **s)
|
||||
*s = "DW_TAG_volatile_type"; break;
|
||||
case DW_TAG_with_stmt:
|
||||
*s = "DW_TAG_with_stmt"; break;
|
||||
case DW_TAG_format_label:
|
||||
*s = "DW_TAG_format_label"; break;
|
||||
case DW_TAG_function_template:
|
||||
*s = "DW_TAG_function_template"; break;
|
||||
case DW_TAG_class_template:
|
||||
*s = "DW_TAG_class_template"; break;
|
||||
case DW_TAG_GNU_BINCL:
|
||||
*s = "DW_TAG_GNU_BINCL"; break;
|
||||
case DW_TAG_GNU_EINCL:
|
||||
*s = "DW_TAG_GNU_EINCL"; break;
|
||||
case DW_TAG_GNU_template_template_param:
|
||||
*s = "DW_TAG_GNU_template_template_param"; break;
|
||||
case DW_TAG_GNU_template_parameter_pack:
|
||||
*s = "DW_TAG_GNU_template_parameter_pack"; break;
|
||||
case DW_TAG_GNU_formal_parameter_pack:
|
||||
*s = "DW_TAG_GNU_formal_parameter_pack"; break;
|
||||
case DW_TAG_GNU_call_site:
|
||||
*s = "DW_TAG_GNU_call_site"; break;
|
||||
case DW_TAG_GNU_call_site_parameter:
|
||||
*s = "DW_TAG_GNU_call_site_parameter"; break;
|
||||
default:
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_errmsg.c 2576 2012-09-13 09:16:11Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_errmsg.c 2975 2014-01-21 20:08:04Z kaiwang27 $");
|
||||
|
||||
static const char *_libdwarf_errors[] = {
|
||||
#define DEFINE_ERROR(N,S) [DW_DLE_##N] = S
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_frame.c 2073 2011-10-27 03:30:47Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_frame.c 3106 2014-12-19 16:00:58Z kaiwang27 $");
|
||||
|
||||
int
|
||||
dwarf_get_fde_list(Dwarf_Debug dbg, Dwarf_Cie **cie_list,
|
||||
@ -539,8 +539,8 @@ dwarf_expand_frame_instructions(Dwarf_Cie cie, Dwarf_Ptr instruction,
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
ret = _dwarf_frame_get_fop(dbg, instruction, len, ret_oplist, ret_opcnt,
|
||||
error);
|
||||
ret = _dwarf_frame_get_fop(dbg, cie->cie_addrsize, instruction, len,
|
||||
ret_oplist, ret_opcnt, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
|
||||
|
73
contrib/elftoolchain/libdwarf/dwarf_get_die_infotypes_flag.3
Normal file
73
contrib/elftoolchain/libdwarf/dwarf_get_die_infotypes_flag.3
Normal file
@ -0,0 +1,73 @@
|
||||
.\" Copyright (c) 2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
.\" modification, are permitted provided that the following conditions
|
||||
.\" are met:
|
||||
.\" 1. Redistributions of source code must retain the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer.
|
||||
.\" 2. Redistributions in binary form must reproduce the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer in the
|
||||
.\" documentation and/or other materials provided with the distribution.
|
||||
.\"
|
||||
.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_get_die_infotypes_flag.3 3118 2014-12-20 20:30:06Z jkoshy $
|
||||
.\"
|
||||
.Dd December 20, 2014
|
||||
.Os
|
||||
.Dt DWARF_GET_DIE_INFOTYPES_FLAG 3
|
||||
.Sh NAME
|
||||
.Nm dwarf_get_die_infotypes_flag
|
||||
.Nd indicate the originating DWARF section for a DIE
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
.Sh SYNOPSIS
|
||||
.In libdwarf.h
|
||||
.Ft Dwarf_Bool
|
||||
.Fo dwarf_get_die_infotypes_flag
|
||||
.Fa "Dwarf_Die die"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
Function
|
||||
.Fn dwarf_get_die_infotypes_flag
|
||||
returns a flag indicating the originating DWARF section for the
|
||||
debugging information entry referenced by argument
|
||||
.Ar die .
|
||||
.Pp
|
||||
Argument
|
||||
.Ar die
|
||||
should reference a valid debugging information entry descriptor.
|
||||
.Sh RETURN VALUES
|
||||
Function
|
||||
.Fn dwarf_get_die_infotypes_flag
|
||||
returns a non-zero value if argument
|
||||
.Ar die
|
||||
originates in the
|
||||
.Dq .debug_info
|
||||
section.
|
||||
.Pp
|
||||
It returns zero if argument
|
||||
.Ar die
|
||||
originates in the
|
||||
.Dq .debug_types
|
||||
section.
|
||||
.Sh ERRORS
|
||||
Function
|
||||
.Fn dwarf_get_die_infotypes_flag
|
||||
always succeeds.
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_next_cu_header_c 3 ,
|
||||
.Xr dwarf_offdie_b 3 ,
|
||||
.Xr dwarf_siblingof_b 3
|
116
contrib/elftoolchain/libdwarf/dwarf_get_section_max_offsets.3
Normal file
116
contrib/elftoolchain/libdwarf/dwarf_get_section_max_offsets.3
Normal file
@ -0,0 +1,116 @@
|
||||
.\" Copyright (c) 2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
.\" modification, are permitted provided that the following conditions
|
||||
.\" are met:
|
||||
.\" 1. Redistributions of source code must retain the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer.
|
||||
.\" 2. Redistributions in binary form must reproduce the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer in the
|
||||
.\" documentation and/or other materials provided with the distribution.
|
||||
.\"
|
||||
.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_get_section_max_offsets.3 3098 2014-09-02 22:18:29Z kaiwang27 $
|
||||
.\"
|
||||
.Dd July 27, 2014
|
||||
.Os
|
||||
.Dt DWARF_GET_SECTION_MAX_OFFSETS
|
||||
.Sh NAME
|
||||
.Nm dwarf_get_section_max_offsets ,
|
||||
.Nm dwarf_get_section_max_offsets_b
|
||||
.Nd return the size of DWARF sections
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
.Sh SYNOPSIS
|
||||
.In libdwarf.h
|
||||
.Ft int
|
||||
.Fo dwarf_get_section_max_offsets
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Unsigned *debug_info"
|
||||
.Fa "Dwarf_Unsigned *debug_abbrev"
|
||||
.Fa "Dwarf_Unsigned *debug_line"
|
||||
.Fa "Dwarf_Unsigned *debug_loc"
|
||||
.Fa "Dwarf_Unsigned *debug_aranges"
|
||||
.Fa "Dwarf_Unsigned *debug_macinfo"
|
||||
.Fa "Dwarf_Unsigned *debug_pubnames"
|
||||
.Fa "Dwarf_Unsigned *debug_str"
|
||||
.Fa "Dwarf_Unsigned *debug_frame"
|
||||
.Fa "Dwarf_Unsigned *debug_ranges"
|
||||
.Fa "Dwarf_Unsigned *debug_pubtypes"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_get_section_max_offsets_b
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Unsigned *debug_info"
|
||||
.Fa "Dwarf_Unsigned *debug_abbrev"
|
||||
.Fa "Dwarf_Unsigned *debug_line"
|
||||
.Fa "Dwarf_Unsigned *debug_loc"
|
||||
.Fa "Dwarf_Unsigned *debug_aranges"
|
||||
.Fa "Dwarf_Unsigned *debug_macinfo"
|
||||
.Fa "Dwarf_Unsigned *debug_pubnames"
|
||||
.Fa "Dwarf_Unsigned *debug_str"
|
||||
.Fa "Dwarf_Unsigned *debug_frame"
|
||||
.Fa "Dwarf_Unsigned *debug_ranges"
|
||||
.Fa "Dwarf_Unsigned *debug_pubtypes"
|
||||
.Fa "Dwarf_Unsigned *debug_types"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
Function
|
||||
.Fn dwarf_get_section_max_offsets_b
|
||||
retrieves the sizes of the DWARF sections in a DWARF debug context.
|
||||
Argument
|
||||
.Ar dbg
|
||||
should reference a DWARF debug context allocated using
|
||||
.Xr dwarf_init 3 .
|
||||
The function stores the size of each DWARF section to the location
|
||||
pointed to by the argument corresponding to the section name.
|
||||
If a DWARF section does not exist, the location pointed to by the
|
||||
argument corresponding to that section will be set to zero.
|
||||
.Pp
|
||||
A value of NULL may be used for any of the arguments
|
||||
.Ar debug_info ,
|
||||
.Ar debug_abbrev ,
|
||||
.Ar debug_line ,
|
||||
.Ar debug_loc ,
|
||||
.Ar debug_aranges ,
|
||||
.Ar debug_macinfo ,
|
||||
.Ar debug_pubnames ,
|
||||
.Ar debug_str ,
|
||||
.Ar debug_frame ,
|
||||
.Ar debug_ranges ,
|
||||
.Ar debug_pubtypes
|
||||
and
|
||||
.Ar debug_types
|
||||
if the caller is not interested in the respective section size.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_get_section_max_offsets
|
||||
is identical to function
|
||||
.Fn dwarf_get_section_max_offsets_b
|
||||
except that it does not provide argument
|
||||
.Ar debug_types ,
|
||||
thus it can not retrieve the size of the
|
||||
.Dq \&.debug_types
|
||||
section.
|
||||
.Sh RETURN VALUES
|
||||
On success, these functions return
|
||||
.Dv DW_DLV_OK .
|
||||
If argument
|
||||
.Ar dbg
|
||||
is NULL, they return
|
||||
.Dv DW_DLV_ERROR .
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_init 3
|
@ -1,4 +1,4 @@
|
||||
.\" Copyright (c) 2010 Kai Wang
|
||||
.\" Copyright (c) 2010,2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
@ -22,9 +22,9 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_highpc.3 2073 2011-10-27 03:30:47Z jkoshy $
|
||||
.\" $Id: dwarf_highpc.3 3092 2014-09-02 22:09:30Z kaiwang27 $
|
||||
.\"
|
||||
.Dd April 7, 2010
|
||||
.Dd July 22, 2014
|
||||
.Os
|
||||
.Dt DWARF_HIGHPC 3
|
||||
.Sh NAME
|
||||
@ -33,6 +33,7 @@
|
||||
.Nm dwarf_bitsize ,
|
||||
.Nm dwarf_bytesize ,
|
||||
.Nm dwarf_highpc ,
|
||||
.Nm dwarf_highpc_b ,
|
||||
.Nm dwarf_lowpc ,
|
||||
.Nm dwarf_srclang
|
||||
.Nd retrieve the value of a DWARF attribute
|
||||
@ -71,6 +72,14 @@
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_highpc_b
|
||||
.Fa "Dwarf_Die die"
|
||||
.Fa "Dwarf_Addr *ret_highpc"
|
||||
.Fa "Dwarf_Half *ret_form"
|
||||
.Fa "enum Dwarf_Form_Class *ret_class"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_lowpc
|
||||
.Fa "Dwarf_Die die"
|
||||
.Fa "Dwarf_Addr *ret_lowpc"
|
||||
@ -114,6 +123,10 @@ attribute value.
|
||||
Retrieve the
|
||||
.Dv DW_AT_high_pc
|
||||
attribute value.
|
||||
.It Fn dwarf_highpc_b
|
||||
Retrieve the
|
||||
.Dv DW_AT_high_pc
|
||||
attribute value.
|
||||
.It Fn dwarf_lowpc
|
||||
Retrieve the
|
||||
.Dv DW_AT_low_pc
|
||||
@ -123,6 +136,23 @@ Retrieve the
|
||||
.Dv DW_AT_language
|
||||
attribute value.
|
||||
.El
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_highpc_b
|
||||
is an enhanced version of function
|
||||
.Fn dwarf_highpc .
|
||||
It sets the location specified by argument
|
||||
.Ar ret_form
|
||||
to the form code of the attribute
|
||||
.Dv DW_AT_high_pc ,
|
||||
and sets the location specified by argument
|
||||
.Ar ret_class
|
||||
to the class of that form.
|
||||
A value of NULL may be used for either of the arguments
|
||||
.Ar ret_form
|
||||
or
|
||||
.Ar ret_class
|
||||
if the caller is not interested in the respective value.
|
||||
.Sh RETURN VALUES
|
||||
These functions return
|
||||
.Dv DW_DLV_OK on success.
|
||||
@ -159,4 +189,5 @@ had no requested attribute.
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_attr 3 ,
|
||||
.Xr dwarf_attrlist 3 ,
|
||||
.Xr dwarf_hasattr 3
|
||||
.Xr dwarf_hasattr 3 ,
|
||||
.Xr dwarf_get_form_class 3
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_lineno.c 2074 2011-10-27 03:34:33Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_lineno.c 2983 2014-02-09 00:24:31Z kaiwang27 $");
|
||||
|
||||
int
|
||||
dwarf_srclines(Dwarf_Die die, Dwarf_Line **linebuf, Dwarf_Signed *linecount,
|
||||
@ -75,8 +75,8 @@ dwarf_srclines(Dwarf_Die die, Dwarf_Line **linebuf, Dwarf_Signed *linecount,
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
if ((li->li_lnarray = malloc(*linecount *
|
||||
sizeof(struct _Dwarf_Line))) == NULL) {
|
||||
if ((li->li_lnarray = malloc(*linecount * sizeof(Dwarf_Line))) ==
|
||||
NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*-
|
||||
* Copyright (c) 2009 Kai Wang
|
||||
* Copyright (c) 2009,2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -26,13 +26,37 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_loclist.c 2074 2011-10-27 03:34:33Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_loclist.c 3066 2014-06-06 19:36:06Z kaiwang27 $");
|
||||
|
||||
static int
|
||||
copy_locdesc(Dwarf_Debug dbg, Dwarf_Locdesc *dst, Dwarf_Locdesc *src,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
|
||||
assert(src != NULL && dst != NULL);
|
||||
|
||||
dst->ld_lopc = src->ld_lopc;
|
||||
dst->ld_hipc = src->ld_hipc;
|
||||
dst->ld_cents = src->ld_cents;
|
||||
|
||||
if (dst->ld_cents > 0) {
|
||||
dst->ld_s = calloc(dst->ld_cents, sizeof(Dwarf_Loc));
|
||||
if (dst->ld_s == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
return (DW_DLE_MEMORY);
|
||||
}
|
||||
memcpy(dst->ld_s, src->ld_s, src->ld_cents *
|
||||
sizeof(Dwarf_Loc));
|
||||
} else
|
||||
dst->ld_s = NULL;
|
||||
|
||||
return (DW_DLE_NONE);
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_loclist_n(Dwarf_Attribute at, Dwarf_Locdesc ***llbuf,
|
||||
Dwarf_Signed *listlen, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Loclist ll;
|
||||
Dwarf_Debug dbg;
|
||||
int ret;
|
||||
|
||||
@ -69,26 +93,41 @@ dwarf_loclist_n(Dwarf_Attribute at, Dwarf_Locdesc ***llbuf,
|
||||
/* FALLTHROUGH */
|
||||
case DW_FORM_sec_offset:
|
||||
ret = _dwarf_loclist_find(dbg, at->at_die->die_cu,
|
||||
at->u[0].u64, &ll, error);
|
||||
at->u[0].u64, llbuf, listlen, NULL, error);
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, ret);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
*llbuf = ll->ll_ldlist;
|
||||
*listlen = ll->ll_ldlen;
|
||||
return (DW_DLV_OK);
|
||||
case DW_FORM_block:
|
||||
case DW_FORM_block1:
|
||||
case DW_FORM_block2:
|
||||
case DW_FORM_block4:
|
||||
case DW_FORM_exprloc:
|
||||
if (at->at_ld == NULL) {
|
||||
ret = _dwarf_loc_add(at->at_die, at, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
*llbuf = &at->at_ld;
|
||||
*llbuf = calloc(1, sizeof(Dwarf_Locdesc *));
|
||||
if (*llbuf == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
(*llbuf)[0] = calloc(1, sizeof(Dwarf_Locdesc));
|
||||
if ((*llbuf)[0] == NULL) {
|
||||
free(*llbuf);
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
if (copy_locdesc(dbg, (*llbuf)[0], at->at_ld, error) !=
|
||||
DW_DLE_NONE) {
|
||||
free((*llbuf)[0]);
|
||||
free(*llbuf);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
*listlen = 1;
|
||||
return (DW_DLV_OK);
|
||||
default:
|
||||
@ -107,75 +146,27 @@ int
|
||||
dwarf_loclist(Dwarf_Attribute at, Dwarf_Locdesc **llbuf,
|
||||
Dwarf_Signed *listlen, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Loclist ll;
|
||||
Dwarf_Debug dbg;
|
||||
int ret;
|
||||
Dwarf_Locdesc **_llbuf;
|
||||
int i, ret;
|
||||
|
||||
dbg = at != NULL ? at->at_die->die_dbg : NULL;
|
||||
ret = dwarf_loclist_n(at, &_llbuf, listlen, error);
|
||||
if (ret != DW_DLV_OK)
|
||||
return (ret);
|
||||
|
||||
if (at == NULL || llbuf == NULL || listlen == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ARGUMENT);
|
||||
return (DW_DLV_ERROR);
|
||||
/* Only return the first location description of the list. */
|
||||
*llbuf = _llbuf[0];
|
||||
|
||||
/* Free the rest of the list. */
|
||||
for (i = 1; i < *listlen; i++) {
|
||||
if (_llbuf[i]->ld_s)
|
||||
free(_llbuf[i]->ld_s);
|
||||
free(_llbuf[i]);
|
||||
}
|
||||
free(_llbuf);
|
||||
|
||||
switch (at->at_attrib) {
|
||||
case DW_AT_location:
|
||||
case DW_AT_string_length:
|
||||
case DW_AT_return_addr:
|
||||
case DW_AT_data_member_location:
|
||||
case DW_AT_frame_base:
|
||||
case DW_AT_segment:
|
||||
case DW_AT_static_link:
|
||||
case DW_AT_use_location:
|
||||
case DW_AT_vtable_elem_location:
|
||||
switch (at->at_form) {
|
||||
case DW_FORM_data4:
|
||||
case DW_FORM_data8:
|
||||
/*
|
||||
* DW_FORM_data[48] can not be used as section offset
|
||||
* since DWARF4. For DWARF[23], the application needs
|
||||
* to determine if DW_FORM_data[48] is representing
|
||||
* a constant or a section offset.
|
||||
*/
|
||||
if (at->at_die->die_cu->cu_version >= 4) {
|
||||
printf("called cu_version >= 4\n");
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
/* FALLTHROUGH */
|
||||
case DW_FORM_sec_offset:
|
||||
ret = _dwarf_loclist_find(at->at_die->die_dbg,
|
||||
at->at_die->die_cu, at->u[0].u64, &ll, error);
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLV_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
}
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
*llbuf = ll->ll_ldlist[0];
|
||||
*listlen = 1;
|
||||
return (DW_DLV_OK);
|
||||
case DW_FORM_block:
|
||||
case DW_FORM_block1:
|
||||
case DW_FORM_block2:
|
||||
case DW_FORM_block4:
|
||||
if (at->at_ld == NULL) {
|
||||
ret = _dwarf_loc_add(at->at_die, at, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
*llbuf = at->at_ld;
|
||||
*listlen = 1;
|
||||
return (DW_DLV_OK);
|
||||
default:
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ATTR_FORM_BAD);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
default:
|
||||
/* Wrong attr supplied. */
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ARGUMENT);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
*listlen = 1;
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
int
|
||||
@ -184,19 +175,25 @@ dwarf_get_loclist_entry(Dwarf_Debug dbg, Dwarf_Unsigned offset,
|
||||
Dwarf_Unsigned *entry_len, Dwarf_Unsigned *next_entry,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Loclist ll, next_ll;
|
||||
Dwarf_Locdesc *ld;
|
||||
Dwarf_Locdesc *ld, **llbuf;
|
||||
Dwarf_Section *ds;
|
||||
Dwarf_Signed listlen;
|
||||
int i, ret;
|
||||
|
||||
/*
|
||||
* Note that this API sometimes will not work correctly because
|
||||
* it assumes that all units have the same pointer size and offset
|
||||
* size.
|
||||
*/
|
||||
|
||||
if (dbg == NULL || hipc == NULL || lopc == NULL || data == NULL ||
|
||||
entry_len == NULL || next_entry == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ARGUMENT);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
ret = _dwarf_loclist_find(dbg, STAILQ_FIRST(&dbg->dbg_cu), offset, &ll,
|
||||
error);
|
||||
ret = _dwarf_loclist_find(dbg, STAILQ_FIRST(&dbg->dbg_cu), offset,
|
||||
&llbuf, &listlen, entry_len, error);
|
||||
if (ret == DW_DLE_NO_ENTRY) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLV_NO_ENTRY);
|
||||
return (DW_DLV_NO_ENTRY);
|
||||
@ -204,8 +201,8 @@ dwarf_get_loclist_entry(Dwarf_Debug dbg, Dwarf_Unsigned offset,
|
||||
return (DW_DLV_ERROR);
|
||||
|
||||
*hipc = *lopc = 0;
|
||||
for (i = 0; i < ll->ll_ldlen; i++) {
|
||||
ld = ll->ll_ldlist[i];
|
||||
for (i = 0; i < listlen; i++) {
|
||||
ld = llbuf[i];
|
||||
if (i == 0) {
|
||||
*hipc = ld->ld_hipc;
|
||||
*lopc = ld->ld_lopc;
|
||||
@ -219,14 +216,8 @@ dwarf_get_loclist_entry(Dwarf_Debug dbg, Dwarf_Unsigned offset,
|
||||
|
||||
ds = _dwarf_find_section(dbg, ".debug_loc");
|
||||
assert(ds != NULL);
|
||||
*data = (uint8_t *) ds->ds_data + ll->ll_offset;
|
||||
*entry_len = ll->ll_length;
|
||||
|
||||
next_ll = TAILQ_NEXT(ll, ll_next);
|
||||
if (next_ll != NULL)
|
||||
*next_entry = next_ll->ll_offset;
|
||||
else
|
||||
*next_entry = ds->ds_size;
|
||||
*data = (uint8_t *) ds->ds_data + offset;
|
||||
*next_entry = offset + *entry_len;
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
@ -236,30 +227,49 @@ dwarf_loclist_from_expr(Dwarf_Debug dbg, Dwarf_Ptr bytes_in,
|
||||
Dwarf_Unsigned bytes_len, Dwarf_Locdesc **llbuf, Dwarf_Signed *listlen,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Locdesc *ld;
|
||||
int ret;
|
||||
|
||||
if (dbg == NULL || bytes_in == NULL || bytes_len == 0 ||
|
||||
llbuf == NULL || listlen == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ARGUMENT);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
ret = _dwarf_loc_fill_locexpr(dbg, &ld, bytes_in, bytes_len,
|
||||
dbg->dbg_pointer_size, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
|
||||
*llbuf = ld;
|
||||
*listlen = 1;
|
||||
|
||||
return (DW_DLV_OK);
|
||||
return (dwarf_loclist_from_expr_a(dbg, bytes_in, bytes_len,
|
||||
dbg->dbg_pointer_size, llbuf, listlen, error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_loclist_from_expr_a(Dwarf_Debug dbg, Dwarf_Ptr bytes_in,
|
||||
Dwarf_Unsigned bytes_len, Dwarf_Half addr_size, Dwarf_Locdesc **llbuf,
|
||||
Dwarf_Signed *listlen, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Half offset_size;
|
||||
Dwarf_Small version;
|
||||
|
||||
/*
|
||||
* Obtain offset size and DWARF version from the current
|
||||
* Compilation Unit or Type Unit. These values are needed
|
||||
* for correctly parsing DW_OP_GNU_implicit_pointer operator.
|
||||
*
|
||||
* Note that dwarf_loclist_from_expr_b() should be used instead
|
||||
* if the application knows correct values for offset size
|
||||
* and DWARF version.
|
||||
*/
|
||||
if (dbg->dbg_cu_current) {
|
||||
offset_size = dbg->dbg_cu_current->cu_length_size == 4 ? 4 : 8;
|
||||
version = dbg->dbg_cu_current->cu_version;
|
||||
} else if (dbg->dbg_tu_current) {
|
||||
offset_size = dbg->dbg_tu_current->cu_length_size == 4 ? 4 : 8;
|
||||
version = dbg->dbg_tu_current->cu_version;
|
||||
} else {
|
||||
/* Default values if no CU/TU context. */
|
||||
offset_size = 4;
|
||||
version = 2; /* DWARF2 */
|
||||
}
|
||||
|
||||
return (dwarf_loclist_from_expr_b(dbg, bytes_in, bytes_len, addr_size,
|
||||
offset_size, version, llbuf, listlen, error));
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_loclist_from_expr_b(Dwarf_Debug dbg, Dwarf_Ptr bytes_in,
|
||||
Dwarf_Unsigned bytes_len, Dwarf_Half addr_size, Dwarf_Half offset_size,
|
||||
Dwarf_Small version, Dwarf_Locdesc **llbuf, Dwarf_Signed *listlen,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Locdesc *ld;
|
||||
int ret;
|
||||
@ -275,8 +285,13 @@ dwarf_loclist_from_expr_a(Dwarf_Debug dbg, Dwarf_Ptr bytes_in,
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
if (offset_size != 4 && offset_size != 8) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_ARGUMENT);
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
ret = _dwarf_loc_fill_locexpr(dbg, &ld, bytes_in, bytes_len, addr_size,
|
||||
error);
|
||||
offset_size, version, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
.\" Copyright (c) 2011 Kai Wang
|
||||
.\" Copyright (c) 2011,2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
@ -22,14 +22,15 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_loclist_from_expr.3 2074 2011-10-27 03:34:33Z jkoshy $
|
||||
.\" $Id: dwarf_loclist_from_expr.3 3129 2014-12-21 20:06:26Z jkoshy $
|
||||
.\"
|
||||
.Dd July 6, 2011
|
||||
.Dd December 21, 2014
|
||||
.Os
|
||||
.Dt DWARF_LOCLIST_FROM_EXPR 3
|
||||
.Sh NAME
|
||||
.Nm dwarf_loclist_from_expr ,
|
||||
.Nm dwarf_loclist_from_expr_a
|
||||
.Nm dwarf_loclist_from_expr_a ,
|
||||
.Nm dwarf_loclist_from_expr_b
|
||||
.Nd translate DWARF location expression bytes
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
@ -54,6 +55,18 @@
|
||||
.Fa "Dwarf_Signed *listlen"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_loclist_from_expr_b
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Ptr bytes_in"
|
||||
.Fa "Dwarf_Unsigned bytes_len"
|
||||
.Fa "Dwarf_Half addr_size"
|
||||
.Fa "Dwarf_Half offset_size"
|
||||
.Fa "Dwarf_Small version"
|
||||
.Fa "Dwarf_Locdesc **llbuf"
|
||||
.Fa "Dwarf_Signed *listlen"
|
||||
.Fa "Dwarf_Error *error"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
Function
|
||||
.Fn dwarf_loclist_from_expr
|
||||
@ -104,6 +117,21 @@ except that it requires one additional argument
|
||||
.Ar addr_size ,
|
||||
which specifies the address size to use when translating the location
|
||||
expression bytes.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_loclist_from_expr_b
|
||||
is identical to function
|
||||
.Fn dwarf_loclist_from_expr_a
|
||||
except that it requires two additional arguments for translating the
|
||||
location expression bytes.
|
||||
Argument
|
||||
.Ar offset_size
|
||||
specifies the offset size, and argument
|
||||
.Ar version
|
||||
specifies the DWARF version.
|
||||
These values are required to correctly translate the
|
||||
.Dv DW_OP_GNU_implicit_pointer
|
||||
opcode.
|
||||
.Ss Memory Management
|
||||
The memory area used for the descriptor returned in argument
|
||||
.Ar llbuf
|
||||
|
@ -1,4 +1,4 @@
|
||||
.\" Copyright (c) 2010 Kai Wang
|
||||
.\" Copyright (c) 2010,2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
@ -22,14 +22,15 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_next_cu_header.3 2074 2011-10-27 03:34:33Z jkoshy $
|
||||
.\" $Id: dwarf_next_cu_header.3 3128 2014-12-21 20:06:22Z jkoshy $
|
||||
.\"
|
||||
.Dd July 24, 2010
|
||||
.Dd December 21, 2014
|
||||
.Os
|
||||
.Dt DWARF_NEXT_CU_HEADER 3
|
||||
.Sh NAME
|
||||
.Nm dwarf_next_cu_header ,
|
||||
.Nm dwarf_next_cu_header_b
|
||||
.Nm dwarf_next_cu_header_b ,
|
||||
.Nm dwarf_next_cu_header_c
|
||||
.Nd step through compilation units in a DWARF debug context
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
@ -57,33 +58,71 @@
|
||||
.Fa "Dwarf_Unsigned *cu_next_offset"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Ft int
|
||||
.Fo dwarf_next_cu_header_c
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Bool is_info"
|
||||
.Fa "Dwarf_Unsigned *cu_length"
|
||||
.Fa "Dwarf_Half *cu_version"
|
||||
.Fa "Dwarf_Off *cu_abbrev_offset"
|
||||
.Fa "Dwarf_Half *cu_pointer_size"
|
||||
.Fa "Dwarf_Half *cu_offset_size"
|
||||
.Fa "Dwarf_Half *cu_extension_size"
|
||||
.Fa "Dwarf_Sig8 *type_signature"
|
||||
.Fa "Dwarf_Unsigned *type_offset"
|
||||
.Fa "Dwarf_Unsigned *cu_next_offset"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
These functions are used to step through compilation unit contexts
|
||||
These functions are used to step through compilation or type units
|
||||
associated with a DWARF debug context, optionally returning information
|
||||
about the unit.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_next_cu_header_b
|
||||
.Fn dwarf_next_cu_header_c
|
||||
is the API recommended for new application code.
|
||||
Function
|
||||
.Fn dwarf_next_cu_header
|
||||
and
|
||||
.Fn dwarf_next_cu_header_b
|
||||
can only operate on compilation units associated with the
|
||||
.Dq \&.debug_info
|
||||
section.
|
||||
They are less general than function
|
||||
.Fn dwarf_next_cu_header_c ,
|
||||
and are deprecated for use by new application code.
|
||||
.Pp
|
||||
Argument
|
||||
.Ar dbg
|
||||
should reference a DWARF debug context allocated using
|
||||
.Xr dwarf_init 3 .
|
||||
If argument
|
||||
.Ar is_info
|
||||
is set to 1,
|
||||
the function returns information for compilation units found in the
|
||||
.Dq \&.debug_info
|
||||
section.
|
||||
If argument
|
||||
.Ar is_info
|
||||
is set to 0,
|
||||
the function returns information for type units found in the
|
||||
.Dq \&.debug_types
|
||||
sections.
|
||||
Argument
|
||||
.Ar cu_length
|
||||
should point to a location that will be set to the
|
||||
length of the compilation unit.
|
||||
length of the compilation or type unit.
|
||||
Argument
|
||||
.Ar cu_version
|
||||
should point to a location that will be set to the
|
||||
version number for the compilation unit.
|
||||
version number for the compilation or type unit.
|
||||
Argument
|
||||
.Ar cu_abbrev_offset
|
||||
should point to a location that will be set to the
|
||||
starting offset (in the
|
||||
.Dq .debug_abbrev
|
||||
section) of the set of debugging information entry abbreviations
|
||||
associated with this compilation unit.
|
||||
associated with this compilation or type unit.
|
||||
Argument
|
||||
.Ar cu_pointer_size
|
||||
should point to a location that will be set to the
|
||||
@ -92,7 +131,7 @@ underlying object being debugged.
|
||||
Argument
|
||||
.Ar cu_offset_size
|
||||
should point to a location that will be set to the
|
||||
size in bytes for a DWARF offset in the compilation unit.
|
||||
size in bytes for a DWARF offset in the compilation or type unit.
|
||||
Argument
|
||||
.Ar cu_extension_size
|
||||
is only needed for processing MIPS/IRIX objects that use
|
||||
@ -100,10 +139,26 @@ a non-standard DWARF format.
|
||||
It should point to a location that will be set to 4 for normal
|
||||
objects and to 0 for non-standard ones.
|
||||
Argument
|
||||
.Ar type_signature
|
||||
and
|
||||
.Ar type_offset
|
||||
is only needed for processing type units.
|
||||
Argument
|
||||
.Ar type_signature
|
||||
should point to a location that will be set to the 64-bit unique signature
|
||||
of the type described in the type unit.
|
||||
Argument
|
||||
.Ar type_offset
|
||||
should point to a location that will be set to the offset of the debugging
|
||||
information entry that describes the type.
|
||||
Argument
|
||||
.Ar cu_next_offset
|
||||
should point to a location that will be set to the
|
||||
offset of the next compilation unit header in the
|
||||
.Dq \&.debug_info
|
||||
section,
|
||||
or the offset of the next type unit header in the
|
||||
.Dq \&.debug_types
|
||||
section.
|
||||
Argument
|
||||
.Ar err
|
||||
@ -111,42 +166,23 @@ should point to a location that will hold an error descriptor in case
|
||||
of an error.
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_next_cu_header_b
|
||||
is identical to function
|
||||
.Fn dwarf_next_cu_header_c
|
||||
except that it does not provide arguments
|
||||
.Ar is_info ,
|
||||
.Ar type_signature
|
||||
and
|
||||
.Ar type_offset .
|
||||
.Pp
|
||||
Function
|
||||
.Fn dwarf_next_cu_header
|
||||
is less general than
|
||||
.Fn dwarf_next_cu_header_b ,
|
||||
and is deprecated for use by new application code.
|
||||
Argument
|
||||
.Ar dbg
|
||||
should reference a DWARF debug context allocated using
|
||||
.Xr dwarf_init 3 .
|
||||
Argument
|
||||
.Ar cu_length
|
||||
should point to a location that will be set to the
|
||||
length of the compilation unit.
|
||||
Argument
|
||||
.Ar cu_version
|
||||
should point to a location that will be set to the
|
||||
version number for the compilation unit.
|
||||
Argument
|
||||
.Ar cu_abbrev_offset
|
||||
should point to a location that will be set to the
|
||||
starting offset in the
|
||||
.Dq .debug_abbrev
|
||||
section of the set of debugging information entry abbreviations
|
||||
associated with this compilation unit.
|
||||
Argument
|
||||
.Ar cu_pointer_size
|
||||
should point to a location that will be set to the
|
||||
size of an address in bytes for the machine architecture of the
|
||||
underlying debugging object.
|
||||
Argument
|
||||
.Ar cu_next_offset
|
||||
should point to a location that will be set to the
|
||||
offset of the next compilation unit.
|
||||
Argument
|
||||
.Ar err
|
||||
should point to a location that will hold an error descriptor in case
|
||||
of an error.
|
||||
is identical to function
|
||||
.Fn dwarf_next_cu_header_b
|
||||
except that it does not provide arguments
|
||||
.Ar cu_offset_size
|
||||
and
|
||||
.Ar cu_extension_size .
|
||||
.Pp
|
||||
A value of NULL may be used for any of the arguments
|
||||
.Ar cu_length ,
|
||||
@ -155,30 +191,79 @@ A value of NULL may be used for any of the arguments
|
||||
.Ar cu_pointer_size ,
|
||||
.Ar cu_offset_size ,
|
||||
.Ar cu_extension_size ,
|
||||
.Ar type_signature ,
|
||||
.Ar type_offset ,
|
||||
.Ar cu_next_offset
|
||||
and
|
||||
.Ar err
|
||||
if the caller is not interested in the respective value.
|
||||
.Ss Iterating Through Compilation Units in a Debug Context
|
||||
.Pp
|
||||
The first call to functions
|
||||
.Fn dwarf_next_cu_header_b
|
||||
and
|
||||
.Fn dwarf_next_cu_header
|
||||
for a given debug context will return information about the first
|
||||
compilation unit in the debug context.
|
||||
Subsequent calls to these functions will iterate through the remaining
|
||||
compilation units in the debug context.
|
||||
On stepping past the last compilation unit in the debug context,
|
||||
functions
|
||||
.Fn dwarf_next_cu_header
|
||||
and
|
||||
.Fn dwarf_next_cu_header_b
|
||||
return
|
||||
The first call to function
|
||||
.Fn dwarf_next_cu_header_c
|
||||
for a given debug context with argument
|
||||
.Ar is_info
|
||||
set to 1 will return information about the first
|
||||
compilation unit in the
|
||||
.Dq \&.debug_info
|
||||
section.
|
||||
Subsequent calls to the function will iterate through the remaining
|
||||
compilation units in the section.
|
||||
On stepping past the last compilation unit in the section,
|
||||
function
|
||||
.Fn dwarf_next_cu_header_c
|
||||
returns
|
||||
.Dv DW_DLV_NO_ENTRY
|
||||
and reset their internal state.
|
||||
The next call to these functions will restart from the first compilation
|
||||
unit in the debug context.
|
||||
and resets its internal state.
|
||||
The next call to the function will restart from the first compilation
|
||||
unit in the section.
|
||||
.Ss Iterating Through Type Units in a Debug Context
|
||||
When a DWARF debug context is allocated using
|
||||
.Xr dwarf_init 3 ,
|
||||
an internal pointer assoicated with the context will point to the
|
||||
fisrt
|
||||
.Dq \&.debug_types
|
||||
section found in the debug object.
|
||||
The first call to function
|
||||
.Fn dwarf_next_cu_header_c
|
||||
for the debug context with argument
|
||||
.Ar is_info
|
||||
set to 0 will return information about the first
|
||||
type unit in that
|
||||
.Dq \&.debug_types
|
||||
section.
|
||||
Subsequent calls to the function will iterate through the remaining
|
||||
type units in the section.
|
||||
On stepping past the last type unit in the debug context,
|
||||
function
|
||||
.Fn dwarf_next_cu_header_c
|
||||
returns
|
||||
.Dv DW_DLV_NO_ENTRY
|
||||
and resets its internal state.
|
||||
The next call to the function will restart from the first type
|
||||
unit in the
|
||||
.Dq \&.debug_types
|
||||
section.
|
||||
.Pp
|
||||
If the debug object contains multiple
|
||||
.Dq \&.debug_types
|
||||
sections, the function
|
||||
.Fn dwarf_next_types_section
|
||||
can be called to move the internal pointer to the next
|
||||
.Dq \&.debug_types
|
||||
section.
|
||||
As a result, subsequent calls of the function
|
||||
.Fn dwarf_next_cu_header_c
|
||||
will operate on the new
|
||||
.Dq \&.debug_types
|
||||
section.
|
||||
Function
|
||||
.Fn dwarf_next_types_section
|
||||
returns
|
||||
.Dv DW_DLV_NO_ENTRY
|
||||
when there are no more
|
||||
.Dq \&.debug_types
|
||||
sections left in the debug object.
|
||||
.Sh RETURN VALUES
|
||||
On success, these functions return
|
||||
.Dv DW_DLV_OK .
|
||||
@ -200,4 +285,5 @@ was NULL.
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_get_cu_die_offset_given_cu_header_offset 3 ,
|
||||
.Xr dwarf_init 3 ,
|
||||
.Xr dwarf_next_types_section 3 ,
|
||||
.Xr dwarf_siblingof 3
|
||||
|
134
contrib/elftoolchain/libdwarf/dwarf_next_types_section.3
Normal file
134
contrib/elftoolchain/libdwarf/dwarf_next_types_section.3
Normal file
@ -0,0 +1,134 @@
|
||||
.\" Copyright (c) 2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
.\" modification, are permitted provided that the following conditions
|
||||
.\" are met:
|
||||
.\" 1. Redistributions of source code must retain the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer.
|
||||
.\" 2. Redistributions in binary form must reproduce the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer in the
|
||||
.\" documentation and/or other materials provided with the distribution.
|
||||
.\"
|
||||
.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: dwarf_next_types_section.3 3116 2014-12-20 18:26:55Z jkoshy $
|
||||
.\"
|
||||
.Dd December 20, 2014
|
||||
.Os
|
||||
.Dt DWARF_NEXT_TYPES_SECTION 3
|
||||
.Sh NAME
|
||||
.Nm dwarf_next_types_section
|
||||
.Nd step through .debug_types sections in a debug context
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
.Sh SYNOPSIS
|
||||
.In libdwarf.h
|
||||
.Ft int
|
||||
.Fo dwarf_next_types_section
|
||||
.Fa "Dwarf_Debug dbg"
|
||||
.Fa "Dwarf_Error *err"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
Function
|
||||
.Fn dwarf_next_types_section
|
||||
steps through the
|
||||
.Dq \&.debug_types
|
||||
sections found in a debug context.
|
||||
.Pp
|
||||
Argument
|
||||
.Ar dbg
|
||||
should reference a DWARF debug context allocated using
|
||||
.Xr dwarf_init 3 .
|
||||
Argument
|
||||
.Ar err
|
||||
should point to a location that will hold an error descriptor in case
|
||||
of an error.
|
||||
.Pp
|
||||
When a DWARF debug context is allocated using
|
||||
.Xr dwarf_init 3 ,
|
||||
an internal pointer associated with the context will point to the
|
||||
first
|
||||
.Dq \&.debug_types
|
||||
section present in the debug object.
|
||||
When the application calls function
|
||||
.Fn dwarf_next_types_section ,
|
||||
this internal pointer will move to the next
|
||||
.Dq \&.debug_types
|
||||
section present.
|
||||
On stepping past the last
|
||||
.Dq \&.debug_types
|
||||
section left in the debug context, function
|
||||
.Fn dwarf_next_types_section
|
||||
returns
|
||||
.Dv DW_DLV_NO_ENTRY .
|
||||
The next call to the function will restart from the first
|
||||
.Dq \&.debug_types
|
||||
section in the debug context.
|
||||
.Pp
|
||||
Application code should call function
|
||||
.Xr dwarf_next_cu_header_c 3
|
||||
to iterate though the type units associated with the current
|
||||
.Dq \&.debug_types
|
||||
section.
|
||||
.Sh RETURN VALUES
|
||||
On success, function
|
||||
.Fn dwarf_next_types_section
|
||||
returns
|
||||
.Dv DW_DLV_OK .
|
||||
.Pp
|
||||
In case of an error, it returns
|
||||
.Dv DW_DLV_ERROR
|
||||
and sets argument
|
||||
.Ar err .
|
||||
When there are no more
|
||||
.Dq \&.debug_types
|
||||
sections left to traverse, it returns
|
||||
.Dv DW_DLV_NO_ENTRY .
|
||||
.Sh COMPATIBILITY
|
||||
This function is an extension to the
|
||||
.Xr DWARF 3
|
||||
API.
|
||||
.Sh ERRORS
|
||||
The
|
||||
.Fn dwarf_next_types_section
|
||||
function may fail with the following errors:
|
||||
.Bl -tag -width ".Bq Er DW_DLE_ARGUMENT"
|
||||
.It Bq Er DW_DLE_ARGUMENT
|
||||
Argument
|
||||
.Va dbg
|
||||
was NULL.
|
||||
.El
|
||||
.Sh EXAMPLES
|
||||
To iterate though every type unit in all the
|
||||
.Dq \&.debug_types
|
||||
sections found in a debug context:
|
||||
.Bd -literal -offset indent
|
||||
Dwarf_Debug dbg;
|
||||
Dwarf_Sig8 sig8;
|
||||
Dwarf_Unsigned typeoff;
|
||||
Dwarf_Error de;
|
||||
|
||||
\&... allocate dbg using dwarf_init() etc ...
|
||||
|
||||
do {
|
||||
while ((ret = dwarf_next_cu_header_c(dbg, 0, NULL, NULL, NULL,
|
||||
NULL, NULL, NULL, &sig8, &typeoff, NULL, &de)) == DW_DLV_OK) {
|
||||
/* Access DIEs etc ... */
|
||||
}
|
||||
} while (dwarf_next_types_section(dbg, &de) == DW_DLV_OK);
|
||||
.Ed
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_init 3 ,
|
||||
.Xr dwarf_next_cu_header_c 3
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_ranges.c 2075 2011-10-27 03:47:28Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: dwarf_ranges.c 3029 2014-04-21 23:26:02Z kaiwang27 $");
|
||||
|
||||
static int
|
||||
_dwarf_get_ranges(Dwarf_Debug dbg, Dwarf_CU cu, Dwarf_Off off,
|
||||
@ -63,7 +63,7 @@ dwarf_get_ranges(Dwarf_Debug dbg, Dwarf_Off offset, Dwarf_Ranges **ranges,
|
||||
}
|
||||
|
||||
if (!dbg->dbg_info_loaded) {
|
||||
if (_dwarf_info_load(dbg, 1, error) != DW_DLE_NONE)
|
||||
if (_dwarf_info_load(dbg, 1, 1, error) != DW_DLE_NONE)
|
||||
return (DW_DLV_ERROR);
|
||||
}
|
||||
|
||||
|
111
contrib/elftoolchain/libdwarf/dwarf_sections.c
Normal file
111
contrib/elftoolchain/libdwarf/dwarf_sections.c
Normal file
@ -0,0 +1,111 @@
|
||||
/*-
|
||||
* Copyright (c) 2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: dwarf_sections.c 3036 2014-05-05 19:19:31Z kaiwang27 $");
|
||||
|
||||
#define SET(N, V) \
|
||||
do { \
|
||||
if ((N) != NULL) \
|
||||
*(N) = (V); \
|
||||
} while (0)
|
||||
|
||||
int
|
||||
dwarf_get_section_max_offsets_b(Dwarf_Debug dbg, Dwarf_Unsigned *debug_info,
|
||||
Dwarf_Unsigned *debug_abbrev, Dwarf_Unsigned *debug_line,
|
||||
Dwarf_Unsigned *debug_loc, Dwarf_Unsigned *debug_aranges,
|
||||
Dwarf_Unsigned *debug_macinfo, Dwarf_Unsigned *debug_pubnames,
|
||||
Dwarf_Unsigned *debug_str, Dwarf_Unsigned *debug_frame,
|
||||
Dwarf_Unsigned *debug_ranges, Dwarf_Unsigned *debug_pubtypes,
|
||||
Dwarf_Unsigned *debug_types)
|
||||
{
|
||||
const char *n;
|
||||
Dwarf_Unsigned sz;
|
||||
int i;
|
||||
|
||||
if (dbg == NULL)
|
||||
return (DW_DLV_ERROR);
|
||||
|
||||
SET(debug_info, 0);
|
||||
SET(debug_abbrev, 0);
|
||||
SET(debug_line, 0);
|
||||
SET(debug_loc, 0);
|
||||
SET(debug_aranges, 0);
|
||||
SET(debug_macinfo, 0);
|
||||
SET(debug_pubnames, 0);
|
||||
SET(debug_str, 0);
|
||||
SET(debug_frame, 0);
|
||||
SET(debug_ranges, 0);
|
||||
SET(debug_pubtypes, 0);
|
||||
SET(debug_types, 0);
|
||||
|
||||
for (i = 0; (Dwarf_Unsigned) i < dbg->dbg_seccnt; i++) {
|
||||
n = dbg->dbg_section[i].ds_name;
|
||||
sz = dbg->dbg_section[i].ds_size;
|
||||
if (!strcmp(n, ".debug_info"))
|
||||
SET(debug_info, sz);
|
||||
else if (!strcmp(n, ".debug_abbrev"))
|
||||
SET(debug_abbrev, sz);
|
||||
else if (!strcmp(n, ".debug_line"))
|
||||
SET(debug_line, sz);
|
||||
else if (!strcmp(n, ".debug_loc"))
|
||||
SET(debug_loc, sz);
|
||||
else if (!strcmp(n, ".debug_aranges"))
|
||||
SET(debug_aranges, sz);
|
||||
else if (!strcmp(n, ".debug_macinfo"))
|
||||
SET(debug_macinfo, sz);
|
||||
else if (!strcmp(n, ".debug_pubnames"))
|
||||
SET(debug_pubnames, sz);
|
||||
else if (!strcmp(n, ".debug_str"))
|
||||
SET(debug_str, sz);
|
||||
else if (!strcmp(n, ".debug_frame"))
|
||||
SET(debug_frame, sz);
|
||||
else if (!strcmp(n, ".debug_ranges"))
|
||||
SET(debug_ranges, sz);
|
||||
else if (!strcmp(n, ".debug_pubtypes"))
|
||||
SET(debug_pubtypes, sz);
|
||||
else if (!strcmp(n, ".debug_types"))
|
||||
SET(debug_types, sz);
|
||||
}
|
||||
|
||||
return (DW_DLV_OK);
|
||||
}
|
||||
|
||||
int
|
||||
dwarf_get_section_max_offsets(Dwarf_Debug dbg, Dwarf_Unsigned *debug_info,
|
||||
Dwarf_Unsigned *debug_abbrev, Dwarf_Unsigned *debug_line,
|
||||
Dwarf_Unsigned *debug_loc, Dwarf_Unsigned *debug_aranges,
|
||||
Dwarf_Unsigned *debug_macinfo, Dwarf_Unsigned *debug_pubnames,
|
||||
Dwarf_Unsigned *debug_str, Dwarf_Unsigned *debug_frame,
|
||||
Dwarf_Unsigned *debug_ranges, Dwarf_Unsigned *debug_pubtypes)
|
||||
{
|
||||
|
||||
return (dwarf_get_section_max_offsets(dbg, debug_info, debug_abbrev,
|
||||
debug_line, debug_loc, debug_aranges, debug_macinfo,
|
||||
debug_pubnames, debug_str, debug_frame, debug_ranges,
|
||||
debug_pubtypes));
|
||||
}
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 2007 John Birrell (jb@freebsd.org)
|
||||
* Copyright (c) 2009-2011 Kai Wang
|
||||
* Copyright (c) 2009-2011,2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -24,7 +24,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: libdwarf.h 2576 2012-09-13 09:16:11Z jkoshy $
|
||||
* $Id: libdwarf.h 3064 2014-06-06 19:35:55Z kaiwang27 $
|
||||
*/
|
||||
|
||||
#ifndef _LIBDWARF_H_
|
||||
@ -47,7 +47,6 @@ typedef struct _Dwarf_ArangeSet *Dwarf_ArangeSet;
|
||||
typedef struct _Dwarf_Attribute *Dwarf_Attribute;
|
||||
typedef struct _Dwarf_Attribute *Dwarf_P_Attribute;
|
||||
typedef struct _Dwarf_AttrDef *Dwarf_AttrDef;
|
||||
typedef struct _Dwarf_CU *Dwarf_CU;
|
||||
typedef struct _Dwarf_Cie *Dwarf_Cie;
|
||||
typedef struct _Dwarf_Cie *Dwarf_P_Cie;
|
||||
typedef struct _Dwarf_Debug *Dwarf_Debug;
|
||||
@ -60,7 +59,6 @@ typedef struct _Dwarf_FrameSec *Dwarf_FrameSec;
|
||||
typedef struct _Dwarf_Line *Dwarf_Line;
|
||||
typedef struct _Dwarf_LineFile *Dwarf_LineFile;
|
||||
typedef struct _Dwarf_LineInfo *Dwarf_LineInfo;
|
||||
typedef struct _Dwarf_Loclist *Dwarf_Loclist;
|
||||
typedef struct _Dwarf_MacroSet *Dwarf_MacroSet;
|
||||
typedef struct _Dwarf_NamePair *Dwarf_NamePair;
|
||||
typedef struct _Dwarf_NamePair *Dwarf_Func;
|
||||
@ -519,6 +517,7 @@ int dwarf_attr(Dwarf_Die, Dwarf_Half, Dwarf_Attribute *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_attrlist(Dwarf_Die, Dwarf_Attribute **,
|
||||
Dwarf_Signed *, Dwarf_Error *);
|
||||
int dwarf_attroffset(Dwarf_Attribute, Dwarf_Off *, Dwarf_Error *);
|
||||
int dwarf_attrval_flag(Dwarf_Die, Dwarf_Half, Dwarf_Bool *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_attrval_signed(Dwarf_Die, Dwarf_Half, Dwarf_Signed *,
|
||||
@ -626,6 +625,9 @@ int dwarf_get_cu_die_offset(Dwarf_Arange, Dwarf_Off *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_get_cu_die_offset_given_cu_header_offset(Dwarf_Debug,
|
||||
Dwarf_Off, Dwarf_Off *, Dwarf_Error *);
|
||||
int dwarf_get_cu_die_offset_given_cu_header_offset_b(Dwarf_Debug,
|
||||
Dwarf_Off, Dwarf_Bool, Dwarf_Off *, Dwarf_Error *);
|
||||
Dwarf_Bool dwarf_get_die_infotypes_flag(Dwarf_Die);
|
||||
int dwarf_get_elf(Dwarf_Debug, Elf **, Dwarf_Error *);
|
||||
int dwarf_get_fde_at_pc(Dwarf_Fde *, Dwarf_Addr, Dwarf_Fde *,
|
||||
Dwarf_Addr *, Dwarf_Addr *, Dwarf_Error *);
|
||||
@ -678,6 +680,16 @@ int dwarf_get_relocation_info_count(Dwarf_P_Debug, Dwarf_Unsigned *,
|
||||
int *, Dwarf_Error *);
|
||||
Dwarf_Ptr dwarf_get_section_bytes(Dwarf_P_Debug, Dwarf_Signed,
|
||||
Dwarf_Signed *, Dwarf_Unsigned *, Dwarf_Error *);
|
||||
int dwarf_get_section_max_offsets(Dwarf_Debug, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Unsigned *, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Unsigned *, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Unsigned *, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *);
|
||||
int dwarf_get_section_max_offsets_b(Dwarf_Debug, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Unsigned *, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Unsigned *, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Unsigned *, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Unsigned *);
|
||||
int dwarf_get_str(Dwarf_Debug, Dwarf_Off, char **, Dwarf_Signed *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_get_types(Dwarf_Debug, Dwarf_Type **, Dwarf_Signed *,
|
||||
@ -700,6 +712,8 @@ int dwarf_hasattr(Dwarf_Die, Dwarf_Half, Dwarf_Bool *,
|
||||
int dwarf_hasform(Dwarf_Attribute, Dwarf_Half, Dwarf_Bool *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_highpc(Dwarf_Die, Dwarf_Addr *, Dwarf_Error *);
|
||||
int dwarf_highpc_b(Dwarf_Die, Dwarf_Addr *, Dwarf_Half *,
|
||||
enum Dwarf_Form_Class *, Dwarf_Error *);
|
||||
int dwarf_init(int, int, Dwarf_Handler, Dwarf_Ptr, Dwarf_Debug *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_line_srcfileno(Dwarf_Line, Dwarf_Unsigned *,
|
||||
@ -722,6 +736,10 @@ int dwarf_loclist_from_expr(Dwarf_Debug, Dwarf_Ptr, Dwarf_Unsigned,
|
||||
int dwarf_loclist_from_expr_a(Dwarf_Debug, Dwarf_Ptr,
|
||||
Dwarf_Unsigned, Dwarf_Half, Dwarf_Locdesc **,
|
||||
Dwarf_Signed *, Dwarf_Error *);
|
||||
int dwarf_loclist_from_expr_b(Dwarf_Debug, Dwarf_Ptr,
|
||||
Dwarf_Unsigned, Dwarf_Half, Dwarf_Half,
|
||||
Dwarf_Small, Dwarf_Locdesc **, Dwarf_Signed *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_loclist_n(Dwarf_Attribute, Dwarf_Locdesc ***,
|
||||
Dwarf_Signed *, Dwarf_Error *);
|
||||
int dwarf_lowpc(Dwarf_Die, Dwarf_Addr *, Dwarf_Error *);
|
||||
@ -735,11 +753,18 @@ int dwarf_next_cu_header(Dwarf_Debug, Dwarf_Unsigned *,
|
||||
int dwarf_next_cu_header_b(Dwarf_Debug, Dwarf_Unsigned *,
|
||||
Dwarf_Half *, Dwarf_Off *, Dwarf_Half *, Dwarf_Half *,
|
||||
Dwarf_Half *, Dwarf_Unsigned *, Dwarf_Error *);
|
||||
int dwarf_next_cu_header_c(Dwarf_Debug, Dwarf_Bool,
|
||||
Dwarf_Unsigned *, Dwarf_Half *, Dwarf_Off *, Dwarf_Half *,
|
||||
Dwarf_Half *, Dwarf_Half *, Dwarf_Sig8 *, Dwarf_Unsigned *,
|
||||
Dwarf_Unsigned *, Dwarf_Error *);
|
||||
int dwarf_next_types_section(Dwarf_Debug, Dwarf_Error *);
|
||||
int dwarf_object_finish(Dwarf_Debug, Dwarf_Error *);
|
||||
int dwarf_object_init(Dwarf_Obj_Access_Interface *, Dwarf_Handler,
|
||||
Dwarf_Ptr, Dwarf_Debug *, Dwarf_Error *);
|
||||
int dwarf_offdie(Dwarf_Debug, Dwarf_Off, Dwarf_Die *,
|
||||
Dwarf_Error *);
|
||||
int dwarf_offdie_b(Dwarf_Debug, Dwarf_Off, Dwarf_Bool, Dwarf_Die *,
|
||||
Dwarf_Error *);
|
||||
Dwarf_Unsigned dwarf_producer_finish(Dwarf_P_Debug, Dwarf_Error *);
|
||||
Dwarf_P_Debug dwarf_producer_init(Dwarf_Unsigned, Dwarf_Callback_Func,
|
||||
Dwarf_Handler, Dwarf_Ptr, Dwarf_Error *);
|
||||
@ -765,6 +790,8 @@ int dwarf_set_reloc_application(int);
|
||||
Dwarf_Ptr dwarf_seterrarg(Dwarf_Debug, Dwarf_Ptr);
|
||||
Dwarf_Handler dwarf_seterrhand(Dwarf_Debug, Dwarf_Handler);
|
||||
int dwarf_siblingof(Dwarf_Debug, Dwarf_Die, Dwarf_Die *, Dwarf_Error *);
|
||||
int dwarf_siblingof_b(Dwarf_Debug, Dwarf_Die, Dwarf_Die *, Dwarf_Bool,
|
||||
Dwarf_Error *);
|
||||
int dwarf_srcfiles(Dwarf_Die, char ***, Dwarf_Signed *, Dwarf_Error *);
|
||||
int dwarf_srclang(Dwarf_Die, Dwarf_Unsigned *, Dwarf_Error *);
|
||||
int dwarf_srclines(Dwarf_Die, Dwarf_Line **, Dwarf_Signed *,
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_arange.c 2070 2011-10-27 03:05:32Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libdwarf_arange.c 3029 2014-04-21 23:26:02Z kaiwang27 $");
|
||||
|
||||
void
|
||||
_dwarf_arange_cleanup(Dwarf_Debug dbg)
|
||||
@ -67,7 +67,7 @@ _dwarf_arange_init(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
return (DW_DLE_NONE);
|
||||
|
||||
if (!dbg->dbg_info_loaded) {
|
||||
ret = _dwarf_info_load(dbg, 1, error);
|
||||
ret = _dwarf_info_load(dbg, 1, 1, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
}
|
||||
@ -137,8 +137,8 @@ _dwarf_arange_init(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
|
||||
/* Build arange array. */
|
||||
if (dbg->dbg_arange_cnt > 0) {
|
||||
if ((dbg->dbg_arange_array = malloc(dbg->dbg_arange_cnt *
|
||||
sizeof(struct _Dwarf_Arange))) == NULL) {
|
||||
if ((dbg->dbg_arange_array = malloc(dbg->dbg_arange_cnt *
|
||||
sizeof(Dwarf_Arange))) == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
ret = DW_DLE_MEMORY;
|
||||
goto fail_cleanup;
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_attr.c 2966 2013-09-21 14:40:14Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: libdwarf_attr.c 3064 2014-06-06 19:35:55Z kaiwang27 $");
|
||||
|
||||
int
|
||||
_dwarf_attr_alloc(Dwarf_Die die, Dwarf_Attribute *atp, Dwarf_Error *error)
|
||||
@ -106,6 +106,7 @@ _dwarf_attr_init(Dwarf_Debug dbg, Dwarf_Section *ds, uint64_t *offsetp,
|
||||
ret = DW_DLE_NONE;
|
||||
memset(&atref, 0, sizeof(atref));
|
||||
atref.at_die = die;
|
||||
atref.at_offset = *offsetp;
|
||||
atref.at_attrib = ad->ad_attrib;
|
||||
atref.at_form = indirect ? form : ad->ad_form;
|
||||
atref.at_indirect = indirect;
|
||||
@ -162,7 +163,7 @@ _dwarf_attr_init(Dwarf_Debug dbg, Dwarf_Section *ds, uint64_t *offsetp,
|
||||
if (cu->cu_version == 2)
|
||||
atref.u[0].u64 = dbg->read(ds->ds_data, offsetp,
|
||||
cu->cu_pointer_size);
|
||||
else if (cu->cu_version == 3)
|
||||
else
|
||||
atref.u[0].u64 = dbg->read(ds->ds_data, offsetp,
|
||||
dwarf_size);
|
||||
break;
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_die.c 2948 2013-05-30 21:25:52Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: libdwarf_die.c 3039 2014-05-18 15:10:56Z kaiwang27 $");
|
||||
|
||||
int
|
||||
_dwarf_die_alloc(Dwarf_Debug dbg, Dwarf_Die *ret_die, Dwarf_Error *error)
|
||||
@ -81,6 +81,7 @@ Dwarf_Die
|
||||
_dwarf_die_find(Dwarf_Die die, Dwarf_Unsigned off)
|
||||
{
|
||||
Dwarf_Debug dbg;
|
||||
Dwarf_Section *ds;
|
||||
Dwarf_CU cu;
|
||||
Dwarf_Die die1;
|
||||
Dwarf_Error de;
|
||||
@ -88,9 +89,10 @@ _dwarf_die_find(Dwarf_Die die, Dwarf_Unsigned off)
|
||||
|
||||
cu = die->die_cu;
|
||||
dbg = die->die_dbg;
|
||||
ds = cu->cu_is_info ? dbg->dbg_info_sec : dbg->dbg_types_sec;
|
||||
|
||||
ret = _dwarf_die_parse(dbg, dbg->dbg_info_sec, cu, cu->cu_dwarf_size,
|
||||
off, cu->cu_next_offset, &die1, 0, &de);
|
||||
ret = _dwarf_die_parse(dbg, ds, cu, cu->cu_dwarf_size, off,
|
||||
cu->cu_next_offset, &die1, 0, &de);
|
||||
|
||||
if (ret == DW_DLE_NONE)
|
||||
return (die1);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*-
|
||||
* Copyright (c) 2009-2011 Kai Wang
|
||||
* Copyright (c) 2009-2011,2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_frame.c 2529 2012-07-29 23:31:12Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: libdwarf_frame.c 3106 2014-12-19 16:00:58Z kaiwang27 $");
|
||||
|
||||
static int
|
||||
_dwarf_frame_find_cie(Dwarf_FrameSec fs, Dwarf_Unsigned offset,
|
||||
@ -49,8 +49,9 @@ _dwarf_frame_find_cie(Dwarf_FrameSec fs, Dwarf_Unsigned offset,
|
||||
}
|
||||
|
||||
static int
|
||||
_dwarf_frame_read_lsb_encoded(Dwarf_Debug dbg, uint64_t *val, uint8_t *data,
|
||||
uint64_t *offsetp, uint8_t encode, Dwarf_Addr pc, Dwarf_Error *error)
|
||||
_dwarf_frame_read_lsb_encoded(Dwarf_Debug dbg, Dwarf_Cie cie, uint64_t *val,
|
||||
uint8_t *data, uint64_t *offsetp, uint8_t encode, Dwarf_Addr pc,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
uint8_t application;
|
||||
|
||||
@ -62,7 +63,7 @@ _dwarf_frame_read_lsb_encoded(Dwarf_Debug dbg, uint64_t *val, uint8_t *data,
|
||||
|
||||
switch (encode) {
|
||||
case DW_EH_PE_absptr:
|
||||
*val = dbg->read(data, offsetp, dbg->dbg_pointer_size);
|
||||
*val = dbg->read(data, offsetp, cie->cie_addrsize);
|
||||
break;
|
||||
case DW_EH_PE_uleb128:
|
||||
*val = _dwarf_read_uleb128(data, offsetp);
|
||||
@ -149,7 +150,7 @@ _dwarf_frame_parse_lsb_cie_augment(Dwarf_Debug dbg, Dwarf_Cie cie,
|
||||
/* Skip two augments in augment data. */
|
||||
encode = *augdata_p++;
|
||||
offset = 0;
|
||||
ret = _dwarf_frame_read_lsb_encoded(dbg, &val,
|
||||
ret = _dwarf_frame_read_lsb_encoded(dbg, cie, &val,
|
||||
augdata_p, &offset, encode, 0, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
@ -233,6 +234,18 @@ _dwarf_frame_add_cie(Dwarf_Debug dbg, Dwarf_FrameSec fs, Dwarf_Section *ds,
|
||||
cie->cie_ehdata = dbg->read(ds->ds_data, off,
|
||||
dbg->dbg_pointer_size);
|
||||
|
||||
/* DWARF4 added "address_size" and "segment_size". */
|
||||
if (cie->cie_version == 4) {
|
||||
cie->cie_addrsize = dbg->read(ds->ds_data, off, 1);
|
||||
cie->cie_segmentsize = dbg->read(ds->ds_data, off, 1);
|
||||
} else {
|
||||
/*
|
||||
* Otherwise (DWARF[23]) we just set CIE addrsize to the
|
||||
* debug context pointer size.
|
||||
*/
|
||||
cie->cie_addrsize = dbg->dbg_pointer_size;
|
||||
}
|
||||
|
||||
cie->cie_caf = _dwarf_read_uleb128(ds->ds_data, off);
|
||||
cie->cie_daf = _dwarf_read_sleb128(ds->ds_data, off);
|
||||
|
||||
@ -345,8 +358,9 @@ _dwarf_frame_add_fde(Dwarf_Debug dbg, Dwarf_FrameSec fs, Dwarf_Section *ds,
|
||||
* The FDE PC start/range for .eh_frame is encoded according
|
||||
* to the LSB spec's extension to DWARF2.
|
||||
*/
|
||||
ret = _dwarf_frame_read_lsb_encoded(dbg, &val, ds->ds_data,
|
||||
off, cie->cie_fde_encode, ds->ds_addr + *off, error);
|
||||
ret = _dwarf_frame_read_lsb_encoded(dbg, cie, &val,
|
||||
ds->ds_data, off, cie->cie_fde_encode, ds->ds_addr + *off,
|
||||
error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
fde->fde_initloc = val;
|
||||
@ -354,16 +368,16 @@ _dwarf_frame_add_fde(Dwarf_Debug dbg, Dwarf_FrameSec fs, Dwarf_Section *ds,
|
||||
* FDE PC range should not be relative value to anything.
|
||||
* So pass 0 for pc value.
|
||||
*/
|
||||
ret = _dwarf_frame_read_lsb_encoded(dbg, &val, ds->ds_data,
|
||||
off, cie->cie_fde_encode, 0, error);
|
||||
ret = _dwarf_frame_read_lsb_encoded(dbg, cie, &val,
|
||||
ds->ds_data, off, cie->cie_fde_encode, 0, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
fde->fde_adrange = val;
|
||||
} else {
|
||||
fde->fde_initloc = dbg->read(ds->ds_data, off,
|
||||
dbg->dbg_pointer_size);
|
||||
cie->cie_addrsize);
|
||||
fde->fde_adrange = dbg->read(ds->ds_data, off,
|
||||
dbg->dbg_pointer_size);
|
||||
cie->cie_addrsize);
|
||||
}
|
||||
|
||||
/* Optional FDE augmentation data for .eh_frame section. (ignored) */
|
||||
@ -530,9 +544,9 @@ fail_cleanup:
|
||||
}
|
||||
|
||||
static int
|
||||
_dwarf_frame_run_inst(Dwarf_Debug dbg, Dwarf_Regtable3 *rt, uint8_t *insts,
|
||||
Dwarf_Unsigned len, Dwarf_Unsigned caf, Dwarf_Signed daf, Dwarf_Addr pc,
|
||||
Dwarf_Addr pc_req, Dwarf_Addr *row_pc, Dwarf_Error *error)
|
||||
_dwarf_frame_run_inst(Dwarf_Debug dbg, Dwarf_Regtable3 *rt, uint8_t addr_size,
|
||||
uint8_t *insts, Dwarf_Unsigned len, Dwarf_Unsigned caf, Dwarf_Signed daf,
|
||||
Dwarf_Addr pc, Dwarf_Addr pc_req, Dwarf_Addr *row_pc, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Regtable3 *init_rt, *saved_rt;
|
||||
uint8_t *p, *pe;
|
||||
@ -632,7 +646,7 @@ _dwarf_frame_run_inst(Dwarf_Debug dbg, Dwarf_Regtable3 *rt, uint8_t *insts,
|
||||
|
||||
switch (low6) {
|
||||
case DW_CFA_set_loc:
|
||||
pc = dbg->decode(&p, dbg->dbg_pointer_size);
|
||||
pc = dbg->decode(&p, addr_size);
|
||||
#ifdef FRAME_DEBUG
|
||||
printf("DW_CFA_set_loc(pc=%#jx)\n", pc);
|
||||
#endif
|
||||
@ -898,14 +912,13 @@ program_done:
|
||||
}
|
||||
|
||||
static int
|
||||
_dwarf_frame_convert_inst(Dwarf_Debug dbg, uint8_t *insts, Dwarf_Unsigned len,
|
||||
Dwarf_Unsigned *count, Dwarf_Frame_Op *fop, Dwarf_Frame_Op3 *fop3,
|
||||
Dwarf_Error *error)
|
||||
_dwarf_frame_convert_inst(Dwarf_Debug dbg, uint8_t addr_size, uint8_t *insts,
|
||||
Dwarf_Unsigned len, Dwarf_Unsigned *count, Dwarf_Frame_Op *fop,
|
||||
Dwarf_Frame_Op3 *fop3, Dwarf_Error *error)
|
||||
{
|
||||
uint8_t *p, *pe;
|
||||
uint8_t high2, low6;
|
||||
uint64_t reg, reg2, uoff, soff, blen;
|
||||
int ret;
|
||||
|
||||
#define SET_BASE_OP(x) \
|
||||
do { \
|
||||
@ -970,7 +983,6 @@ _dwarf_frame_convert_inst(Dwarf_Debug dbg, uint8_t *insts, Dwarf_Unsigned len,
|
||||
} \
|
||||
} while(0)
|
||||
|
||||
ret = DW_DLE_NONE;
|
||||
*count = 0;
|
||||
|
||||
p = insts;
|
||||
@ -1020,7 +1032,7 @@ _dwarf_frame_convert_inst(Dwarf_Debug dbg, uint8_t *insts, Dwarf_Unsigned len,
|
||||
|
||||
switch (low6) {
|
||||
case DW_CFA_set_loc:
|
||||
uoff = dbg->decode(&p, dbg->dbg_pointer_size);
|
||||
uoff = dbg->decode(&p, addr_size);
|
||||
SET_OFFSET(uoff);
|
||||
break;
|
||||
case DW_CFA_advance_loc1:
|
||||
@ -1103,15 +1115,16 @@ _dwarf_frame_convert_inst(Dwarf_Debug dbg, uint8_t *insts, Dwarf_Unsigned len,
|
||||
}
|
||||
|
||||
int
|
||||
_dwarf_frame_get_fop(Dwarf_Debug dbg, uint8_t *insts, Dwarf_Unsigned len,
|
||||
Dwarf_Frame_Op **ret_oplist, Dwarf_Signed *ret_opcnt, Dwarf_Error *error)
|
||||
_dwarf_frame_get_fop(Dwarf_Debug dbg, uint8_t addr_size, uint8_t *insts,
|
||||
Dwarf_Unsigned len, Dwarf_Frame_Op **ret_oplist, Dwarf_Signed *ret_opcnt,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Frame_Op *oplist;
|
||||
Dwarf_Unsigned count;
|
||||
int ret;
|
||||
|
||||
ret = _dwarf_frame_convert_inst(dbg, insts, len, &count, NULL, NULL,
|
||||
error);
|
||||
ret = _dwarf_frame_convert_inst(dbg, addr_size, insts, len, &count,
|
||||
NULL, NULL, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
|
||||
@ -1120,8 +1133,8 @@ _dwarf_frame_get_fop(Dwarf_Debug dbg, uint8_t *insts, Dwarf_Unsigned len,
|
||||
return (DW_DLE_MEMORY);
|
||||
}
|
||||
|
||||
ret = _dwarf_frame_convert_inst(dbg, insts, len, &count, oplist, NULL,
|
||||
error);
|
||||
ret = _dwarf_frame_convert_inst(dbg, addr_size, insts, len, &count,
|
||||
oplist, NULL, error);
|
||||
if (ret != DW_DLE_NONE) {
|
||||
free(oplist);
|
||||
return (ret);
|
||||
@ -1201,17 +1214,17 @@ _dwarf_frame_get_internal_table(Dwarf_Fde fde, Dwarf_Addr pc_req,
|
||||
/* Run initial instructions in CIE. */
|
||||
cie = fde->fde_cie;
|
||||
assert(cie != NULL);
|
||||
ret = _dwarf_frame_run_inst(dbg, rt, cie->cie_initinst,
|
||||
cie->cie_instlen, cie->cie_caf, cie->cie_daf, 0, ~0ULL,
|
||||
&row_pc, error);
|
||||
ret = _dwarf_frame_run_inst(dbg, rt, cie->cie_addrsize,
|
||||
cie->cie_initinst, cie->cie_instlen, cie->cie_caf, cie->cie_daf, 0,
|
||||
~0ULL, &row_pc, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
|
||||
/* Run instructions in FDE. */
|
||||
if (pc_req >= fde->fde_initloc) {
|
||||
ret = _dwarf_frame_run_inst(dbg, rt, fde->fde_inst,
|
||||
fde->fde_instlen, cie->cie_caf, cie->cie_daf,
|
||||
fde->fde_initloc, pc_req, &row_pc, error);
|
||||
ret = _dwarf_frame_run_inst(dbg, rt, cie->cie_addrsize,
|
||||
fde->fde_inst, fde->fde_instlen, cie->cie_caf,
|
||||
cie->cie_daf, fde->fde_initloc, pc_req, &row_pc, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 2007 John Birrell (jb@freebsd.org)
|
||||
* Copyright (c) 2010,2011 Kai Wang
|
||||
* Copyright (c) 2010,2011,2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -27,7 +27,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_info.c 2942 2013-05-04 23:03:54Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: libdwarf_info.c 3041 2014-05-18 15:11:03Z kaiwang27 $");
|
||||
|
||||
int
|
||||
_dwarf_info_first_cu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
@ -46,7 +46,7 @@ _dwarf_info_first_cu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
|
||||
dbg->dbg_info_off = 0;
|
||||
ret = _dwarf_info_load(dbg, 0, error);
|
||||
ret = _dwarf_info_load(dbg, 0, 1, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
|
||||
@ -55,6 +55,32 @@ _dwarf_info_first_cu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
return (DW_DLE_NONE);
|
||||
}
|
||||
|
||||
int
|
||||
_dwarf_info_first_tu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_CU tu;
|
||||
int ret;
|
||||
|
||||
assert(dbg->dbg_tu_current == NULL);
|
||||
tu = STAILQ_FIRST(&dbg->dbg_tu);
|
||||
if (tu != NULL) {
|
||||
dbg->dbg_tu_current = tu;
|
||||
return (DW_DLE_NONE);
|
||||
}
|
||||
|
||||
if (dbg->dbg_types_loaded)
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
|
||||
dbg->dbg_types_off = 0;
|
||||
ret = _dwarf_info_load(dbg, 0, 0, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
|
||||
dbg->dbg_tu_current = STAILQ_FIRST(&dbg->dbg_tu);
|
||||
|
||||
return (DW_DLE_NONE);
|
||||
}
|
||||
|
||||
int
|
||||
_dwarf_info_next_cu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
{
|
||||
@ -73,7 +99,7 @@ _dwarf_info_next_cu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
}
|
||||
|
||||
ret = _dwarf_info_load(dbg, 0, error);
|
||||
ret = _dwarf_info_load(dbg, 0, 1, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
|
||||
@ -83,7 +109,35 @@ _dwarf_info_next_cu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
}
|
||||
|
||||
int
|
||||
_dwarf_info_load(Dwarf_Debug dbg, int load_all, Dwarf_Error *error)
|
||||
_dwarf_info_next_tu(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_CU cu;
|
||||
int ret;
|
||||
|
||||
assert(dbg->dbg_tu_current != NULL);
|
||||
cu = STAILQ_NEXT(dbg->dbg_tu_current, cu_next);
|
||||
if (cu != NULL) {
|
||||
dbg->dbg_tu_current = cu;
|
||||
return (DW_DLE_NONE);
|
||||
}
|
||||
|
||||
if (dbg->dbg_types_loaded) {
|
||||
dbg->dbg_tu_current = NULL;
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
}
|
||||
|
||||
ret = _dwarf_info_load(dbg, 0, 0, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
|
||||
dbg->dbg_tu_current = STAILQ_NEXT(dbg->dbg_tu_current, cu_next);
|
||||
|
||||
return (DW_DLE_NONE);
|
||||
}
|
||||
|
||||
int
|
||||
_dwarf_info_load(Dwarf_Debug dbg, Dwarf_Bool load_all, Dwarf_Bool is_info,
|
||||
Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_CU cu;
|
||||
Dwarf_Section *ds;
|
||||
@ -93,12 +147,22 @@ _dwarf_info_load(Dwarf_Debug dbg, int load_all, Dwarf_Error *error)
|
||||
uint64_t offset;
|
||||
|
||||
ret = DW_DLE_NONE;
|
||||
if (dbg->dbg_info_loaded)
|
||||
return (DW_DLE_NONE);
|
||||
|
||||
offset = dbg->dbg_info_off;
|
||||
ds = dbg->dbg_info_sec;
|
||||
assert(ds != NULL);
|
||||
if (is_info) {
|
||||
if (dbg->dbg_info_loaded)
|
||||
return (ret);
|
||||
offset = dbg->dbg_info_off;
|
||||
ds = dbg->dbg_info_sec;
|
||||
assert(ds != NULL);
|
||||
} else {
|
||||
if (dbg->dbg_types_loaded)
|
||||
return (ret);
|
||||
offset = dbg->dbg_types_off;
|
||||
ds = dbg->dbg_types_sec;
|
||||
if (ds == NULL)
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
}
|
||||
|
||||
while (offset < ds->ds_size) {
|
||||
if ((cu = calloc(1, sizeof(struct _Dwarf_CU))) == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
@ -106,6 +170,7 @@ _dwarf_info_load(Dwarf_Debug dbg, int load_all, Dwarf_Error *error)
|
||||
}
|
||||
|
||||
cu->cu_dbg = dbg;
|
||||
cu->cu_is_info = is_info;
|
||||
cu->cu_offset = offset;
|
||||
|
||||
length = dbg->read(ds->ds_data, &offset, 4);
|
||||
@ -129,7 +194,10 @@ _dwarf_info_load(Dwarf_Debug dbg, int load_all, Dwarf_Error *error)
|
||||
|
||||
/* Compute the offset to the next compilation unit: */
|
||||
next_offset = offset + length;
|
||||
dbg->dbg_info_off = next_offset;
|
||||
if (is_info)
|
||||
dbg->dbg_info_off = next_offset;
|
||||
else
|
||||
dbg->dbg_types_off = next_offset;
|
||||
|
||||
/* Initialise the compilation unit. */
|
||||
cu->cu_length = length;
|
||||
@ -141,8 +209,20 @@ _dwarf_info_load(Dwarf_Debug dbg, int load_all, Dwarf_Error *error)
|
||||
cu->cu_pointer_size = dbg->read(ds->ds_data, &offset, 1);
|
||||
cu->cu_next_offset = next_offset;
|
||||
|
||||
/* .debug_types extra fields. */
|
||||
if (!is_info) {
|
||||
memcpy(cu->cu_type_sig.signature,
|
||||
(char *) ds->ds_data + offset, 8);
|
||||
offset += 8;
|
||||
cu->cu_type_offset = dbg->read(ds->ds_data, &offset,
|
||||
dwarf_size);
|
||||
}
|
||||
|
||||
/* Add the compilation unit to the list. */
|
||||
STAILQ_INSERT_TAIL(&dbg->dbg_cu, cu, cu_next);
|
||||
if (is_info)
|
||||
STAILQ_INSERT_TAIL(&dbg->dbg_cu, cu, cu_next);
|
||||
else
|
||||
STAILQ_INSERT_TAIL(&dbg->dbg_tu, cu, cu_next);
|
||||
|
||||
if (cu->cu_version < 2 || cu->cu_version > 4) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_VERSION_STAMP_ERROR);
|
||||
@ -158,8 +238,13 @@ _dwarf_info_load(Dwarf_Debug dbg, int load_all, Dwarf_Error *error)
|
||||
break;
|
||||
}
|
||||
|
||||
if ((Dwarf_Unsigned) dbg->dbg_info_off >= ds->ds_size)
|
||||
dbg->dbg_info_loaded = 1;
|
||||
if (is_info) {
|
||||
if ((Dwarf_Unsigned) dbg->dbg_info_off >= ds->ds_size)
|
||||
dbg->dbg_info_loaded = 1;
|
||||
} else {
|
||||
if ((Dwarf_Unsigned) dbg->dbg_types_off >= ds->ds_size)
|
||||
dbg->dbg_types_loaded = 1;
|
||||
}
|
||||
|
||||
return (ret);
|
||||
}
|
||||
@ -180,6 +265,22 @@ _dwarf_info_cleanup(Dwarf_Debug dbg)
|
||||
}
|
||||
free(cu);
|
||||
}
|
||||
|
||||
_dwarf_type_unit_cleanup(dbg);
|
||||
}
|
||||
|
||||
void
|
||||
_dwarf_type_unit_cleanup(Dwarf_Debug dbg)
|
||||
{
|
||||
Dwarf_CU cu, tcu;
|
||||
|
||||
assert(dbg != NULL && dbg->dbg_mode == DW_DLC_READ);
|
||||
|
||||
STAILQ_FOREACH_SAFE(cu, &dbg->dbg_tu, cu_next, tcu) {
|
||||
STAILQ_REMOVE(&dbg->dbg_tu, cu, _Dwarf_CU, cu_next);
|
||||
_dwarf_abbrev_cleanup(cu);
|
||||
free(cu);
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_init.c 2948 2013-05-30 21:25:52Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: libdwarf_init.c 3061 2014-06-02 00:42:41Z kaiwang27 $");
|
||||
|
||||
static int
|
||||
_dwarf_consumer_init(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
@ -69,7 +69,8 @@ _dwarf_consumer_init(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
|
||||
dbg->dbg_seccnt = cnt;
|
||||
|
||||
if ((dbg->dbg_section = calloc(cnt, sizeof(Dwarf_Section))) == NULL) {
|
||||
if ((dbg->dbg_section = calloc(cnt + 1, sizeof(Dwarf_Section))) ==
|
||||
NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
return (DW_DLE_MEMORY);
|
||||
}
|
||||
@ -90,6 +91,7 @@ _dwarf_consumer_init(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
return (ret);
|
||||
}
|
||||
}
|
||||
dbg->dbg_section[cnt].ds_name = NULL;
|
||||
|
||||
if (_dwarf_find_section(dbg, ".debug_abbrev") == NULL ||
|
||||
((dbg->dbg_info_sec = _dwarf_find_section(dbg, ".debug_info")) ==
|
||||
@ -98,6 +100,9 @@ _dwarf_consumer_init(Dwarf_Debug dbg, Dwarf_Error *error)
|
||||
return (DW_DLE_DEBUG_INFO_NULL);
|
||||
}
|
||||
|
||||
/* Try to find the optional DWARF4 .debug_types section. */
|
||||
dbg->dbg_types_sec = _dwarf_find_next_types_section(dbg, NULL);
|
||||
|
||||
/* Initialise call frame API related parameters. */
|
||||
_dwarf_frame_params_init(dbg);
|
||||
|
||||
@ -210,10 +215,10 @@ _dwarf_init(Dwarf_Debug dbg, Dwarf_Unsigned pro_flags, Dwarf_Handler errhand,
|
||||
dbg->dbg_errarg = errarg;
|
||||
|
||||
STAILQ_INIT(&dbg->dbg_cu);
|
||||
STAILQ_INIT(&dbg->dbg_tu);
|
||||
STAILQ_INIT(&dbg->dbg_rllist);
|
||||
STAILQ_INIT(&dbg->dbg_aslist);
|
||||
STAILQ_INIT(&dbg->dbg_mslist);
|
||||
TAILQ_INIT(&dbg->dbg_loclist);
|
||||
|
||||
if (dbg->dbg_mode == DW_DLC_READ || dbg->dbg_mode == DW_DLC_RDWR) {
|
||||
ret = _dwarf_consumer_init(dbg, error);
|
||||
@ -270,7 +275,6 @@ _dwarf_consumer_deinit(Dwarf_Debug dbg)
|
||||
assert(dbg != NULL && dbg->dbg_mode == DW_DLC_READ);
|
||||
|
||||
_dwarf_info_cleanup(dbg);
|
||||
_dwarf_loclist_cleanup(dbg);
|
||||
_dwarf_ranges_cleanup(dbg);
|
||||
_dwarf_frame_cleanup(dbg);
|
||||
_dwarf_arange_cleanup(dbg);
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_lineno.c 2972 2013-12-23 06:46:04Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: libdwarf_lineno.c 3100 2014-10-25 20:34:29Z jkoshy $");
|
||||
|
||||
static int
|
||||
_dwarf_lineno_add_file(Dwarf_LineInfo li, uint8_t **p, const char *compdir,
|
||||
@ -87,9 +87,8 @@ _dwarf_lineno_run_program(Dwarf_CU cu, Dwarf_LineInfo li, uint8_t *p,
|
||||
{
|
||||
Dwarf_Debug dbg;
|
||||
Dwarf_Line ln, tln;
|
||||
uint64_t address, file, line, column, isa, opsize;
|
||||
uint64_t address, file, line, column, opsize;
|
||||
int is_stmt, basic_block, end_sequence;
|
||||
int prologue_end, epilogue_begin;
|
||||
int ret;
|
||||
|
||||
#define RESET_REGISTERS \
|
||||
@ -101,8 +100,6 @@ _dwarf_lineno_run_program(Dwarf_CU cu, Dwarf_LineInfo li, uint8_t *p,
|
||||
is_stmt = li->li_defstmt; \
|
||||
basic_block = 0; \
|
||||
end_sequence = 0; \
|
||||
prologue_end = 0; \
|
||||
epilogue_begin = 0; \
|
||||
} while(0)
|
||||
|
||||
#define APPEND_ROW \
|
||||
@ -181,8 +178,6 @@ _dwarf_lineno_run_program(Dwarf_CU cu, Dwarf_LineInfo li, uint8_t *p,
|
||||
case DW_LNS_copy:
|
||||
APPEND_ROW;
|
||||
basic_block = 0;
|
||||
prologue_end = 0;
|
||||
epilogue_begin = 0;
|
||||
break;
|
||||
case DW_LNS_advance_pc:
|
||||
address += _dwarf_decode_uleb128(&p) *
|
||||
@ -210,13 +205,11 @@ _dwarf_lineno_run_program(Dwarf_CU cu, Dwarf_LineInfo li, uint8_t *p,
|
||||
address += dbg->decode(&p, 2);
|
||||
break;
|
||||
case DW_LNS_set_prologue_end:
|
||||
prologue_end = 1;
|
||||
break;
|
||||
case DW_LNS_set_epilogue_begin:
|
||||
epilogue_begin = 1;
|
||||
break;
|
||||
case DW_LNS_set_isa:
|
||||
isa = _dwarf_decode_uleb128(&p);
|
||||
(void) _dwarf_decode_uleb128(&p);
|
||||
break;
|
||||
default:
|
||||
/* Unrecognized extened opcodes. What to do? */
|
||||
@ -233,8 +226,6 @@ _dwarf_lineno_run_program(Dwarf_CU cu, Dwarf_LineInfo li, uint8_t *p,
|
||||
address += ADDRESS(*p);
|
||||
APPEND_ROW;
|
||||
basic_block = 0;
|
||||
prologue_end = 0;
|
||||
epilogue_begin = 0;
|
||||
p++;
|
||||
}
|
||||
}
|
||||
@ -482,7 +473,7 @@ _dwarf_lineno_gen_program(Dwarf_P_Debug dbg, Dwarf_P_Section ds,
|
||||
Dwarf_Unsigned address, file, line, spc;
|
||||
Dwarf_Unsigned addr0, maddr;
|
||||
Dwarf_Signed line0, column;
|
||||
int is_stmt, basic_block, end_sequence;
|
||||
int is_stmt, basic_block;
|
||||
int need_copy;
|
||||
int ret;
|
||||
|
||||
@ -494,7 +485,6 @@ _dwarf_lineno_gen_program(Dwarf_P_Debug dbg, Dwarf_P_Section ds,
|
||||
column = 0; \
|
||||
is_stmt = li->li_defstmt; \
|
||||
basic_block = 0; \
|
||||
end_sequence = 0; \
|
||||
} while(0)
|
||||
|
||||
li = dbg->dbgp_lineinfo;
|
||||
|
@ -1,5 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 2007 John Birrell (jb@freebsd.org)
|
||||
* Copyright (c) 2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -26,7 +27,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_loc.c 2070 2011-10-27 03:05:32Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libdwarf_loc.c 3070 2014-06-23 03:08:33Z kaiwang27 $");
|
||||
|
||||
/*
|
||||
* Given an array of bytes of length 'len' representing a
|
||||
@ -38,12 +39,12 @@ ELFTC_VCSID("$Id: libdwarf_loc.c 2070 2011-10-27 03:05:32Z jkoshy $");
|
||||
*/
|
||||
static int
|
||||
_dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
|
||||
uint8_t *p, int len)
|
||||
uint8_t offset_size, uint8_t version, uint8_t *p, int len)
|
||||
{
|
||||
int count;
|
||||
uint64_t operand1;
|
||||
uint64_t operand2;
|
||||
uint8_t *ps, *pe;
|
||||
uint8_t *ps, *pe, s;
|
||||
|
||||
count = 0;
|
||||
ps = p;
|
||||
@ -165,37 +166,49 @@ _dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
|
||||
case DW_OP_ne:
|
||||
|
||||
case DW_OP_nop:
|
||||
case DW_OP_push_object_address:
|
||||
case DW_OP_form_tls_address:
|
||||
case DW_OP_call_frame_cfa:
|
||||
case DW_OP_stack_value:
|
||||
case DW_OP_GNU_push_tls_address:
|
||||
case DW_OP_GNU_uninit:
|
||||
break;
|
||||
|
||||
/* Operations with 1-byte operands. */
|
||||
case DW_OP_const1u:
|
||||
case DW_OP_const1s:
|
||||
case DW_OP_pick:
|
||||
case DW_OP_deref_size:
|
||||
case DW_OP_xderef_size:
|
||||
operand1 = *p++;
|
||||
break;
|
||||
|
||||
case DW_OP_const1s:
|
||||
operand1 = (int8_t) *p++;
|
||||
break;
|
||||
|
||||
/* Operations with 2-byte operands. */
|
||||
case DW_OP_call2:
|
||||
case DW_OP_const2u:
|
||||
case DW_OP_const2s:
|
||||
case DW_OP_bra:
|
||||
case DW_OP_skip:
|
||||
operand1 = dbg->decode(&p, 2);
|
||||
break;
|
||||
|
||||
case DW_OP_const2s:
|
||||
operand1 = (int16_t) dbg->decode(&p, 2);
|
||||
break;
|
||||
|
||||
/* Operations with 4-byte operands. */
|
||||
case DW_OP_call4:
|
||||
case DW_OP_const4u:
|
||||
case DW_OP_const4s:
|
||||
case DW_OP_GNU_parameter_ref:
|
||||
operand1 = dbg->decode(&p, 4);
|
||||
break;
|
||||
|
||||
case DW_OP_const4s:
|
||||
operand1 = (int32_t) dbg->decode(&p, 4);
|
||||
break;
|
||||
|
||||
/* Operations with 8-byte operands. */
|
||||
case DW_OP_const8u:
|
||||
case DW_OP_const8s:
|
||||
@ -207,6 +220,9 @@ _dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
|
||||
case DW_OP_plus_uconst:
|
||||
case DW_OP_regx:
|
||||
case DW_OP_piece:
|
||||
case DW_OP_GNU_deref_type:
|
||||
case DW_OP_GNU_convert:
|
||||
case DW_OP_GNU_reinterpret:
|
||||
operand1 = _dwarf_decode_uleb128(&p);
|
||||
break;
|
||||
|
||||
@ -252,6 +268,7 @@ _dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
|
||||
* Oeration with two unsigned LEB128 operands.
|
||||
*/
|
||||
case DW_OP_bit_piece:
|
||||
case DW_OP_GNU_regval_type:
|
||||
operand1 = _dwarf_decode_uleb128(&p);
|
||||
operand2 = _dwarf_decode_uleb128(&p);
|
||||
break;
|
||||
@ -267,10 +284,14 @@ _dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
|
||||
|
||||
/*
|
||||
* Operation with an unsigned LEB128 operand
|
||||
* followed by a block. Store a pointer to the
|
||||
* block in the operand2.
|
||||
* representing the size of a block, followed
|
||||
* by the block content.
|
||||
*
|
||||
* Store the size of the block in the operand1
|
||||
* and a pointer to the block in the operand2.
|
||||
*/
|
||||
case DW_OP_implicit_value:
|
||||
case DW_OP_GNU_entry_value:
|
||||
operand1 = _dwarf_decode_uleb128(&p);
|
||||
operand2 = (Dwarf_Unsigned) (uintptr_t) p;
|
||||
p += operand1;
|
||||
@ -278,25 +299,59 @@ _dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
|
||||
|
||||
/* Target address size operand. */
|
||||
case DW_OP_addr:
|
||||
case DW_OP_GNU_addr_index:
|
||||
case DW_OP_GNU_const_index:
|
||||
operand1 = dbg->decode(&p, pointer_size);
|
||||
break;
|
||||
|
||||
/*
|
||||
* XXX Opcode DW_OP_call_ref has an operand with size
|
||||
* "dwarf_size". Here we use dbg->dbg_offset_size
|
||||
* as "dwarf_size" to be compatible with SGI libdwarf.
|
||||
* However note that dbg->dbg_offset_size is just
|
||||
* a "guess" value so the parsing result of
|
||||
* DW_OP_call_ref might not be correct at all. XXX
|
||||
*/
|
||||
/* Offset size operand. */
|
||||
case DW_OP_call_ref:
|
||||
operand1 = dbg->decode(&p, dbg->dbg_offset_size);
|
||||
operand1 = dbg->decode(&p, offset_size);
|
||||
break;
|
||||
|
||||
/*
|
||||
* The first byte is address byte length, followed by
|
||||
* the address value. If the length is 0, the address
|
||||
* size is the same as target pointer size.
|
||||
*/
|
||||
case DW_OP_GNU_encoded_addr:
|
||||
s = *p++;
|
||||
if (s == 0)
|
||||
s = pointer_size;
|
||||
operand1 = dbg->decode(&p, s);
|
||||
break;
|
||||
|
||||
/*
|
||||
* Operand1: DIE offset (size depending on DWARF version)
|
||||
* DWARF2: pointer size
|
||||
* DWARF{3,4}: offset size
|
||||
*
|
||||
* Operand2: SLEB128
|
||||
*/
|
||||
case DW_OP_GNU_implicit_pointer:
|
||||
if (version == 2)
|
||||
operand1 = dbg->decode(&p, pointer_size);
|
||||
else
|
||||
operand1 = dbg->decode(&p, offset_size);
|
||||
operand2 = _dwarf_decode_sleb128(&p);
|
||||
break;
|
||||
|
||||
/*
|
||||
* Operand1: DIE offset (ULEB128)
|
||||
* Operand2: pointer to a block. The block's first byte
|
||||
* is its size.
|
||||
*/
|
||||
case DW_OP_GNU_const_type:
|
||||
operand1 = _dwarf_decode_uleb128(&p);
|
||||
operand2 = (Dwarf_Unsigned) (uintptr_t) p;
|
||||
s = *p++;
|
||||
p += s;
|
||||
break;
|
||||
|
||||
/* All other operations cause an error. */
|
||||
default:
|
||||
count = -1;
|
||||
break;
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (lbuf != NULL) {
|
||||
@ -307,6 +362,7 @@ _dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
|
||||
count++;
|
||||
}
|
||||
|
||||
done:
|
||||
return (count);
|
||||
}
|
||||
|
||||
@ -561,7 +617,8 @@ _dwarf_loc_expr_add_atom(Dwarf_Debug dbg, uint8_t *out, uint8_t *end,
|
||||
|
||||
int
|
||||
_dwarf_loc_fill_locdesc(Dwarf_Debug dbg, Dwarf_Locdesc *llbuf, uint8_t *in,
|
||||
uint64_t in_len, uint8_t pointer_size, Dwarf_Error *error)
|
||||
uint64_t in_len, uint8_t pointer_size, uint8_t offset_size,
|
||||
uint8_t version, Dwarf_Error *error)
|
||||
{
|
||||
int num;
|
||||
|
||||
@ -570,8 +627,8 @@ _dwarf_loc_fill_locdesc(Dwarf_Debug dbg, Dwarf_Locdesc *llbuf, uint8_t *in,
|
||||
assert(in_len > 0);
|
||||
|
||||
/* Compute the number of locations. */
|
||||
if ((num = _dwarf_loc_fill_loc(dbg, NULL, pointer_size, in, in_len)) <
|
||||
0) {
|
||||
if ((num = _dwarf_loc_fill_loc(dbg, NULL, pointer_size, offset_size,
|
||||
version, in, in_len)) < 0) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_LOC_EXPR_BAD);
|
||||
return (DW_DLE_LOC_EXPR_BAD);
|
||||
}
|
||||
@ -585,14 +642,16 @@ _dwarf_loc_fill_locdesc(Dwarf_Debug dbg, Dwarf_Locdesc *llbuf, uint8_t *in,
|
||||
return (DW_DLE_MEMORY);
|
||||
}
|
||||
|
||||
(void) _dwarf_loc_fill_loc(dbg, llbuf, pointer_size, in, in_len);
|
||||
(void) _dwarf_loc_fill_loc(dbg, llbuf, pointer_size, offset_size,
|
||||
version, in, in_len);
|
||||
|
||||
return (DW_DLE_NONE);
|
||||
}
|
||||
|
||||
int
|
||||
_dwarf_loc_fill_locexpr(Dwarf_Debug dbg, Dwarf_Locdesc **ret_llbuf, uint8_t *in,
|
||||
uint64_t in_len, uint8_t pointer_size, Dwarf_Error *error)
|
||||
uint64_t in_len, uint8_t pointer_size, uint8_t offset_size,
|
||||
uint8_t version, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Locdesc *llbuf;
|
||||
int ret;
|
||||
@ -606,7 +665,7 @@ _dwarf_loc_fill_locexpr(Dwarf_Debug dbg, Dwarf_Locdesc **ret_llbuf, uint8_t *in,
|
||||
llbuf->ld_s = NULL;
|
||||
|
||||
ret = _dwarf_loc_fill_locdesc(dbg, llbuf, in, in_len, pointer_size,
|
||||
error);
|
||||
offset_size, version, error);
|
||||
if (ret != DW_DLE_NONE) {
|
||||
free(llbuf);
|
||||
return (ret);
|
||||
@ -635,7 +694,8 @@ _dwarf_loc_add(Dwarf_Die die, Dwarf_Attribute at, Dwarf_Error *error)
|
||||
assert(dbg != NULL);
|
||||
|
||||
ret = _dwarf_loc_fill_locexpr(dbg, &at->at_ld, at->u[1].u8p,
|
||||
at->u[0].u64, cu->cu_pointer_size, error);
|
||||
at->u[0].u64, cu->cu_pointer_size, cu->cu_length_size == 4 ? 4 : 8,
|
||||
cu->cu_version, error);
|
||||
|
||||
return (ret);
|
||||
}
|
||||
|
@ -26,11 +26,11 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_loclist.c 2972 2013-12-23 06:46:04Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: libdwarf_loclist.c 3061 2014-06-02 00:42:41Z kaiwang27 $");
|
||||
|
||||
static int
|
||||
_dwarf_loclist_add_locdesc(Dwarf_Debug dbg, Dwarf_CU cu, Dwarf_Section *ds,
|
||||
uint64_t *off, Dwarf_Locdesc **ld, uint64_t *ldlen,
|
||||
Dwarf_Unsigned *off, Dwarf_Locdesc **ld, Dwarf_Signed *ldlen,
|
||||
Dwarf_Unsigned *total_len, Dwarf_Error *error)
|
||||
{
|
||||
uint64_t start, end;
|
||||
@ -75,6 +75,7 @@ _dwarf_loclist_add_locdesc(Dwarf_Debug dbg, Dwarf_CU cu, Dwarf_Section *ds,
|
||||
if (ld != NULL) {
|
||||
ret = _dwarf_loc_fill_locdesc(dbg, ld[i],
|
||||
ds->ds_data + *off, len, cu->cu_pointer_size,
|
||||
cu->cu_length_size == 4 ? 4 : 8, cu->cu_version,
|
||||
error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
return (ret);
|
||||
@ -91,37 +92,15 @@ _dwarf_loclist_add_locdesc(Dwarf_Debug dbg, Dwarf_CU cu, Dwarf_Section *ds,
|
||||
|
||||
int
|
||||
_dwarf_loclist_find(Dwarf_Debug dbg, Dwarf_CU cu, uint64_t lloff,
|
||||
Dwarf_Loclist *ret_ll, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Loclist ll;
|
||||
int ret;
|
||||
|
||||
assert(ret_ll != NULL);
|
||||
ret = DW_DLE_NONE;
|
||||
|
||||
TAILQ_FOREACH(ll, &dbg->dbg_loclist, ll_next)
|
||||
if (ll->ll_offset == lloff)
|
||||
break;
|
||||
|
||||
if (ll == NULL)
|
||||
ret = _dwarf_loclist_add(dbg, cu, lloff, ret_ll, error);
|
||||
else
|
||||
*ret_ll = ll;
|
||||
|
||||
return (ret);
|
||||
}
|
||||
|
||||
int
|
||||
_dwarf_loclist_add(Dwarf_Debug dbg, Dwarf_CU cu, uint64_t lloff,
|
||||
Dwarf_Loclist *ret_ll, Dwarf_Error *error)
|
||||
Dwarf_Locdesc ***ret_llbuf, Dwarf_Signed *listlen,
|
||||
Dwarf_Unsigned *entry_len, Dwarf_Error *error)
|
||||
{
|
||||
Dwarf_Locdesc **llbuf;
|
||||
Dwarf_Section *ds;
|
||||
Dwarf_Loclist ll, tll;
|
||||
uint64_t ldlen;
|
||||
Dwarf_Signed ldlen;
|
||||
Dwarf_Unsigned off;
|
||||
int i, ret;
|
||||
|
||||
ret = DW_DLE_NONE;
|
||||
|
||||
if ((ds = _dwarf_find_section(dbg, ".debug_loc")) == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_NO_ENTRY);
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
@ -132,98 +111,55 @@ _dwarf_loclist_add(Dwarf_Debug dbg, Dwarf_CU cu, uint64_t lloff,
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
}
|
||||
|
||||
if ((ll = malloc(sizeof(struct _Dwarf_Loclist))) == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
return (DW_DLE_MEMORY);
|
||||
}
|
||||
|
||||
ll->ll_offset = lloff;
|
||||
|
||||
/* Get the number of locdesc the first round. */
|
||||
ret = _dwarf_loclist_add_locdesc(dbg, cu, ds, &lloff, NULL, &ldlen,
|
||||
off = lloff;
|
||||
ret = _dwarf_loclist_add_locdesc(dbg, cu, ds, &off, NULL, &ldlen,
|
||||
NULL, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
goto fail_cleanup;
|
||||
return (ret);
|
||||
|
||||
if (ldlen == 0)
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
|
||||
/*
|
||||
* Dwarf_Locdesc list memory is allocated in this way (one more level
|
||||
* of indirect) to make the loclist API be compatible with SGI libdwarf.
|
||||
*/
|
||||
ll->ll_ldlen = ldlen;
|
||||
if (ldlen != 0) {
|
||||
if ((ll->ll_ldlist = calloc(ldlen, sizeof(Dwarf_Locdesc *))) ==
|
||||
NULL) {
|
||||
if ((llbuf = calloc(ldlen, sizeof(Dwarf_Locdesc *))) == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
return (DW_DLE_MEMORY);
|
||||
}
|
||||
for (i = 0; i < ldlen; i++) {
|
||||
if ((llbuf[i] = calloc(1, sizeof(Dwarf_Locdesc))) == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
ret = DW_DLE_MEMORY;
|
||||
goto fail_cleanup;
|
||||
}
|
||||
for (i = 0; (uint64_t) i < ldlen; i++) {
|
||||
if ((ll->ll_ldlist[i] =
|
||||
calloc(1, sizeof(Dwarf_Locdesc))) == NULL) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
|
||||
ret = DW_DLE_MEMORY;
|
||||
goto fail_cleanup;
|
||||
}
|
||||
}
|
||||
} else
|
||||
ll->ll_ldlist = NULL;
|
||||
}
|
||||
|
||||
lloff = ll->ll_offset;
|
||||
off = lloff;
|
||||
|
||||
/* Fill in locdesc. */
|
||||
ret = _dwarf_loclist_add_locdesc(dbg, cu, ds, &lloff, ll->ll_ldlist,
|
||||
NULL, &ll->ll_length, error);
|
||||
ret = _dwarf_loclist_add_locdesc(dbg, cu, ds, &off, llbuf, NULL,
|
||||
entry_len, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
goto fail_cleanup;
|
||||
|
||||
/* Insert to the queue. Sort by offset. */
|
||||
TAILQ_FOREACH(tll, &dbg->dbg_loclist, ll_next)
|
||||
if (tll->ll_offset > ll->ll_offset) {
|
||||
TAILQ_INSERT_BEFORE(tll, ll, ll_next);
|
||||
break;
|
||||
}
|
||||
*ret_llbuf = llbuf;
|
||||
*listlen = ldlen;
|
||||
|
||||
if (tll == NULL)
|
||||
TAILQ_INSERT_TAIL(&dbg->dbg_loclist, ll, ll_next);
|
||||
|
||||
*ret_ll = ll;
|
||||
return (DW_DLE_NONE);
|
||||
|
||||
fail_cleanup:
|
||||
|
||||
_dwarf_loclist_free(ll);
|
||||
if (llbuf != NULL) {
|
||||
for (i = 0; i < ldlen; i++) {
|
||||
if (llbuf[i]->ld_s)
|
||||
free(llbuf[i]->ld_s);
|
||||
free(llbuf[i]);
|
||||
}
|
||||
free(llbuf);
|
||||
}
|
||||
|
||||
return (ret);
|
||||
}
|
||||
|
||||
void
|
||||
_dwarf_loclist_free(Dwarf_Loclist ll)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (ll == NULL)
|
||||
return;
|
||||
|
||||
if (ll->ll_ldlist != NULL) {
|
||||
for (i = 0; i < ll->ll_ldlen; i++) {
|
||||
if (ll->ll_ldlist[i]->ld_s)
|
||||
free(ll->ll_ldlist[i]->ld_s);
|
||||
free(ll->ll_ldlist[i]);
|
||||
}
|
||||
free(ll->ll_ldlist);
|
||||
}
|
||||
free(ll);
|
||||
}
|
||||
|
||||
void
|
||||
_dwarf_loclist_cleanup(Dwarf_Debug dbg)
|
||||
{
|
||||
Dwarf_Loclist ll, tll;
|
||||
|
||||
assert(dbg != NULL && dbg->dbg_mode == DW_DLC_READ);
|
||||
|
||||
TAILQ_FOREACH_SAFE(ll, &dbg->dbg_loclist, ll_next, tll) {
|
||||
TAILQ_REMOVE(&dbg->dbg_loclist, ll, ll_next);
|
||||
_dwarf_loclist_free(ll);
|
||||
}
|
||||
}
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_nametbl.c 2070 2011-10-27 03:05:32Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libdwarf_nametbl.c 3029 2014-04-21 23:26:02Z kaiwang27 $");
|
||||
|
||||
void
|
||||
_dwarf_nametbl_cleanup(Dwarf_NameSec *nsp)
|
||||
@ -103,7 +103,7 @@ _dwarf_nametbl_init(Dwarf_Debug dbg, Dwarf_NameSec *namesec, Dwarf_Section *ds,
|
||||
nt->nt_cu_length = dbg->read(ds->ds_data, &offset, dwarf_size);
|
||||
|
||||
if (!dbg->dbg_info_loaded) {
|
||||
ret = _dwarf_info_load(dbg, 1, error);
|
||||
ret = _dwarf_info_load(dbg, 1, 1, error);
|
||||
if (ret != DW_DLE_NONE)
|
||||
goto fail_cleanup;
|
||||
}
|
||||
|
@ -26,7 +26,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_sections.c 2379 2012-01-05 02:08:20Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libdwarf_sections.c 3041 2014-05-18 15:11:03Z kaiwang27 $");
|
||||
|
||||
#define _SECTION_INIT_SIZE 128
|
||||
|
||||
@ -212,7 +212,7 @@ _dwarf_find_section(Dwarf_Debug dbg, const char *name)
|
||||
Dwarf_Section *ds;
|
||||
Dwarf_Half i;
|
||||
|
||||
assert(name != NULL);
|
||||
assert(dbg != NULL && name != NULL);
|
||||
|
||||
for (i = 0; i < dbg->dbg_seccnt; i++) {
|
||||
ds = &dbg->dbg_section[i];
|
||||
@ -223,6 +223,27 @@ _dwarf_find_section(Dwarf_Debug dbg, const char *name)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
Dwarf_Section *
|
||||
_dwarf_find_next_types_section(Dwarf_Debug dbg, Dwarf_Section *ds)
|
||||
{
|
||||
|
||||
assert(dbg != NULL);
|
||||
|
||||
if (ds == NULL)
|
||||
return (_dwarf_find_section(dbg, ".debug_types"));
|
||||
|
||||
assert(ds->ds_name != NULL);
|
||||
|
||||
do {
|
||||
ds++;
|
||||
if (ds->ds_name != NULL &&
|
||||
!strcmp(ds->ds_name, ".debug_types"))
|
||||
return (ds);
|
||||
} while (ds->ds_name != NULL);
|
||||
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
Dwarf_P_Section
|
||||
_dwarf_pro_find_section(Dwarf_P_Debug dbg, const char *name)
|
||||
{
|
||||
|
@ -23,7 +23,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: _libelf.h 2365 2011-12-29 04:36:44Z jkoshy $
|
||||
* $Id: _libelf.h 3011 2014-03-23 03:32:42Z jkoshy $
|
||||
*/
|
||||
|
||||
#ifndef __LIBELF_H_
|
||||
@ -48,7 +48,7 @@ struct _libelf_globals {
|
||||
int libelf_error;
|
||||
int libelf_fillchar;
|
||||
unsigned int libelf_version;
|
||||
char libelf_msg[LIBELF_MSG_SIZE];
|
||||
unsigned char libelf_msg[LIBELF_MSG_SIZE];
|
||||
};
|
||||
|
||||
extern struct _libelf_globals _libelf;
|
||||
@ -71,14 +71,14 @@ extern struct _libelf_globals _libelf;
|
||||
* Flags for library internal use. These use the upper 16 bits of the
|
||||
* `e_flags' field.
|
||||
*/
|
||||
#define LIBELF_F_API_MASK 0x00FFFF /* Flags defined by the API. */
|
||||
#define LIBELF_F_AR_HEADER 0x010000 /* translated header available */
|
||||
#define LIBELF_F_AR_VARIANT_SVR4 0x020000 /* BSD style ar(1) archive */
|
||||
#define LIBELF_F_DATA_MALLOCED 0x040000 /* whether data was malloc'ed */
|
||||
#define LIBELF_F_RAWFILE_MALLOC 0x080000 /* whether e_rawfile was malloc'ed */
|
||||
#define LIBELF_F_RAWFILE_MMAP 0x100000 /* whether e_rawfile was mmap'ed */
|
||||
#define LIBELF_F_SHDRS_LOADED 0x200000 /* whether all shdrs were read in */
|
||||
#define LIBELF_F_SPECIAL_FILE 0x400000 /* non-regular file */
|
||||
#define LIBELF_F_API_MASK 0x00FFFFU /* Flags defined by the API. */
|
||||
#define LIBELF_F_AR_HEADER 0x010000U /* translated header available */
|
||||
#define LIBELF_F_AR_VARIANT_SVR4 0x020000U /* BSD style ar(1) archive */
|
||||
#define LIBELF_F_DATA_MALLOCED 0x040000U /* whether data was malloc'ed */
|
||||
#define LIBELF_F_RAWFILE_MALLOC 0x080000U /* whether e_rawfile was malloc'ed */
|
||||
#define LIBELF_F_RAWFILE_MMAP 0x100000U /* whether e_rawfile was mmap'ed */
|
||||
#define LIBELF_F_SHDRS_LOADED 0x200000U /* whether all shdrs were read in */
|
||||
#define LIBELF_F_SPECIAL_FILE 0x400000U /* non-regular file */
|
||||
|
||||
struct _Elf {
|
||||
int e_activations; /* activation count */
|
||||
@ -89,7 +89,7 @@ struct _Elf {
|
||||
unsigned int e_flags; /* ELF_F_* & LIBELF_F_* flags */
|
||||
Elf_Kind e_kind; /* ELF_K_* */
|
||||
Elf *e_parent; /* non-NULL for archive members */
|
||||
char *e_rawfile; /* uninterpreted bytes */
|
||||
unsigned char *e_rawfile; /* uninterpreted bytes */
|
||||
size_t e_rawsize; /* size of uninterpreted bytes */
|
||||
unsigned int e_version; /* file version */
|
||||
|
||||
@ -99,16 +99,16 @@ struct _Elf {
|
||||
*/
|
||||
union {
|
||||
Elf_Arhdr *e_arhdr; /* translated header */
|
||||
char *e_rawhdr; /* untranslated header */
|
||||
unsigned char *e_rawhdr; /* untranslated header */
|
||||
} e_hdr;
|
||||
|
||||
union {
|
||||
struct { /* ar(1) archives */
|
||||
off_t e_next; /* set by elf_rand()/elf_next() */
|
||||
int e_nchildren;
|
||||
char *e_rawstrtab; /* file name strings */
|
||||
unsigned char *e_rawstrtab; /* file name strings */
|
||||
size_t e_rawstrtabsz;
|
||||
char *e_rawsymtab; /* symbol table */
|
||||
unsigned char *e_rawsymtab; /* symbol table */
|
||||
size_t e_rawsymtabsz;
|
||||
Elf_Arsym *e_symtab;
|
||||
size_t e_symtabsz;
|
||||
@ -162,21 +162,31 @@ enum {
|
||||
ELF_TOMEMORY
|
||||
};
|
||||
|
||||
#define LIBELF_COPY_U32(DST,SRC,NAME) do { \
|
||||
if ((SRC)->NAME > UINT_MAX) { \
|
||||
LIBELF_SET_ERROR(RANGE, 0); \
|
||||
return (0); \
|
||||
} \
|
||||
(DST)->NAME = (SRC)->NAME; \
|
||||
|
||||
/*
|
||||
* The LIBELF_COPY macros are used to copy fields from a GElf_*
|
||||
* structure to their 32-bit counterparts, while checking for out of
|
||||
* range values.
|
||||
*
|
||||
* - LIBELF_COPY_U32 :: copy an unsigned 32 bit field.
|
||||
* - LIBELF_COPY_S32 :: copy a signed 32 bit field.
|
||||
*/
|
||||
|
||||
#define LIBELF_COPY_U32(DST, SRC, NAME) do { \
|
||||
if ((SRC)->NAME > UINT32_MAX) { \
|
||||
LIBELF_SET_ERROR(RANGE, 0); \
|
||||
return (0); \
|
||||
} \
|
||||
(DST)->NAME = (SRC)->NAME & 0xFFFFFFFFU; \
|
||||
} while (0)
|
||||
|
||||
#define LIBELF_COPY_S32(DST,SRC,NAME) do { \
|
||||
if ((SRC)->NAME > INT_MAX || \
|
||||
(SRC)->NAME < INT_MIN) { \
|
||||
LIBELF_SET_ERROR(RANGE, 0); \
|
||||
return (0); \
|
||||
} \
|
||||
(DST)->NAME = (SRC)->NAME; \
|
||||
#define LIBELF_COPY_S32(DST, SRC, NAME) do { \
|
||||
if ((SRC)->NAME > INT32_MAX || \
|
||||
(SRC)->NAME < INT32_MIN) { \
|
||||
LIBELF_SET_ERROR(RANGE, 0); \
|
||||
return (0); \
|
||||
} \
|
||||
(DST)->NAME = (int32_t) (SRC)->NAME; \
|
||||
} while (0)
|
||||
|
||||
|
||||
@ -191,22 +201,22 @@ Elf_Scn *_libelf_allocate_scn(Elf *_e, size_t _ndx);
|
||||
Elf_Arhdr *_libelf_ar_gethdr(Elf *_e);
|
||||
Elf *_libelf_ar_open(Elf *_e, int _reporterror);
|
||||
Elf *_libelf_ar_open_member(int _fd, Elf_Cmd _c, Elf *_ar);
|
||||
int _libelf_ar_get_member(char *_s, size_t _sz, int _base, size_t *_ret);
|
||||
Elf_Arsym *_libelf_ar_process_bsd_symtab(Elf *_ar, size_t *_dst);
|
||||
Elf_Arsym *_libelf_ar_process_svr4_symtab(Elf *_ar, size_t *_dst);
|
||||
unsigned long _libelf_checksum(Elf *_e, int _elfclass);
|
||||
long _libelf_checksum(Elf *_e, int _elfclass);
|
||||
void *_libelf_ehdr(Elf *_e, int _elfclass, int _allocate);
|
||||
int _libelf_falign(Elf_Type _t, int _elfclass);
|
||||
unsigned int _libelf_falign(Elf_Type _t, int _elfclass);
|
||||
size_t _libelf_fsize(Elf_Type _t, int _elfclass, unsigned int _version,
|
||||
size_t count);
|
||||
int (*_libelf_get_translator(Elf_Type _t, int _direction, int _elfclass))
|
||||
(char *_dst, size_t dsz, char *_src, size_t _cnt, int _byteswap);
|
||||
(unsigned char *_dst, size_t dsz, unsigned char *_src,
|
||||
size_t _cnt, int _byteswap);
|
||||
void *_libelf_getphdr(Elf *_e, int _elfclass);
|
||||
void *_libelf_getshdr(Elf_Scn *_scn, int _elfclass);
|
||||
void _libelf_init_elf(Elf *_e, Elf_Kind _kind);
|
||||
int _libelf_load_section_headers(Elf *e, void *ehdr);
|
||||
int _libelf_malign(Elf_Type _t, int _elfclass);
|
||||
Elf *_libelf_memory(char *_image, size_t _sz, int _reporterror);
|
||||
unsigned int _libelf_malign(Elf_Type _t, int _elfclass);
|
||||
Elf *_libelf_memory(unsigned char *_image, size_t _sz, int _reporterror);
|
||||
size_t _libelf_msize(Elf_Type _t, int _elfclass, unsigned int _version);
|
||||
void *_libelf_newphdr(Elf *_e, int _elfclass, size_t _count);
|
||||
Elf *_libelf_open_object(int _fd, Elf_Cmd _c, int _reporterror);
|
||||
|
@ -23,7 +23,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: _libelf_ar.h 2032 2011-10-23 09:07:00Z jkoshy $
|
||||
* $Id: _libelf_ar.h 3013 2014-03-23 06:16:59Z jkoshy $
|
||||
*/
|
||||
|
||||
#ifndef __LIBELF_AR_H_
|
||||
@ -42,15 +42,16 @@
|
||||
(sizeof(LIBELF_AR_BSD_EXTENDED_NAME_PREFIX) - 1)
|
||||
|
||||
#define IS_EXTENDED_BSD_NAME(NAME) \
|
||||
(strncmp((NAME), LIBELF_AR_BSD_EXTENDED_NAME_PREFIX, \
|
||||
(strncmp((const char *) (NAME), \
|
||||
LIBELF_AR_BSD_EXTENDED_NAME_PREFIX, \
|
||||
LIBELF_AR_BSD_EXTENDED_NAME_PREFIX_SIZE) == 0)
|
||||
|
||||
|
||||
char *_libelf_ar_get_string(const char *_buf, size_t _sz, int _rawname,
|
||||
int _svr4names);
|
||||
unsigned char *_libelf_ar_get_string(const char *_buf, size_t _sz,
|
||||
unsigned int _rawname, int _svr4names);
|
||||
char *_libelf_ar_get_raw_name(const struct ar_hdr *_arh);
|
||||
char *_libelf_ar_get_translated_name(const struct ar_hdr *_arh, Elf *_ar);
|
||||
int _libelf_ar_get_number(const char *_buf, size_t _sz, int _base,
|
||||
size_t *_ret);
|
||||
int _libelf_ar_get_number(const char *_buf, size_t _sz,
|
||||
unsigned int _base, size_t *_ret);
|
||||
|
||||
#endif /* __LIBELF_AR_H_ */
|
||||
|
@ -21,9 +21,9 @@
|
||||
.\" out of the use of this software, even if advised of the possibility of
|
||||
.\" such damage.
|
||||
.\"
|
||||
.\" $Id: elf.3 2885 2013-01-11 02:11:28Z jkoshy $
|
||||
.\" $Id: elf.3 3082 2014-07-28 09:13:33Z jkoshy $
|
||||
.\"
|
||||
.Dd August 14, 2011
|
||||
.Dd July 28, 2014
|
||||
.Os
|
||||
.Dt ELF 3
|
||||
.Sh NAME
|
||||
@ -367,6 +367,11 @@ section entries.
|
||||
.Xc
|
||||
.It Dv SHT_DYNSYM Ta Dv ELF_T_SYM Ta Symbols for dynamic linking.
|
||||
.It Dv SHT_FINI_ARRAY Ta Dv ELF_T_ADDR Ta Termination function pointers.
|
||||
.It Dv SHT_GNU_HASH Ta Dv ELF_T_GNUHASH Ta GNU hash sections.
|
||||
.It Dv SHT_GNU_LIBLIST Ta Dv ELF_T_WORD Ta List of libraries to be pre-linked.
|
||||
.It Dv SHT_GNU_verdef Ta Dv ELF_T_VDEF Ta Symbol version definitions.
|
||||
.It Dv SHT_GNU_verneed Ta Dv ELF_T_VNEED Ta Symbol versioning requirements.
|
||||
.It Dv SHT_GNU_versym Ta Dv ELF_T_HALF Ta Version symbols.
|
||||
.It Dv SHT_GROUP Ta Dv ELF_T_WORD Ta Section group marker.
|
||||
.It Dv SHT_HASH Ta Dv ELF_T_HASH Ta Symbol hashes.
|
||||
.It Dv SHT_INIT_ARRAY Ta Dv ELF_T_ADDR Ta Initialization function pointers.
|
||||
@ -383,12 +388,32 @@ See
|
||||
.It Dv SHT_STRTAB Ta Dv ELF_T_BYTE Ta String tables.
|
||||
.It Dv SHT_SYMTAB Ta Dv ELF_T_SYM Ta Symbol tables.
|
||||
.It Dv SHT_SYMTAB_SHNDX Ta Dv ELF_T_WORD Ta Used with extended section numbering.
|
||||
.It Dv SHT_GNU_verdef Ta Dv ELF_T_VDEF Ta Symbol version definitions.
|
||||
.It Dv SHT_GNU_verneed Ta Dv ELF_T_VNEED Ta Symbol versioning requirements.
|
||||
.It Dv SHT_GNU_versym Ta Dv ELF_T_HALF Ta Version symbols.
|
||||
.It Dv SHT_SUNW_dof Ta Dv ELF_T_BYTE Ta Xo
|
||||
Used by
|
||||
.Xr dtrace 1 .
|
||||
.Xc
|
||||
.It Dv SHT_SUNW_move Ta Dv ELF_T_MOVE Ta ELF move records.
|
||||
.It Dv SHT_SUNW_syminfo Ta Dv ELF_T_SYMINFO Ta Additional symbol flags.
|
||||
.It Dv SHT_SUNW_verdef Ta Dv ELF_T_VDEF Ta Xo
|
||||
Same as
|
||||
.Dv SHT_GNU_verdef .
|
||||
.Xc
|
||||
.It Dv SHT_SUNW_verneed Ta Dv ELF_T_VNEED Ta Xo
|
||||
Same as
|
||||
.Dv SHT_GNU_verneed .
|
||||
.Xc
|
||||
.It Dv SHT_SUNW_versym Ta Dv ELF_T_HALF Ta Xo
|
||||
Same as
|
||||
.Dv SHT_GNU_versym .
|
||||
.Xc
|
||||
.El
|
||||
.Pp
|
||||
Section types in the range
|
||||
.Ns [ Dv SHT_LOOS ,
|
||||
.Dv SHT_HIUSER ]
|
||||
are otherwise considered to be of type
|
||||
.Dv ELF_T_BYTE .
|
||||
.TE
|
||||
.Ss Functional Grouping
|
||||
This section contains a brief overview of the available functionality
|
||||
in the ELF library.
|
||||
|
@ -27,11 +27,12 @@
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
#include <libelf.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_data.c 2921 2013-03-04 16:19:22Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_data.c 3009 2014-03-23 01:49:59Z jkoshy $");
|
||||
|
||||
Elf_Data *
|
||||
elf_getdata(Elf_Scn *s, Elf_Data *ed)
|
||||
@ -39,10 +40,11 @@ elf_getdata(Elf_Scn *s, Elf_Data *ed)
|
||||
Elf *e;
|
||||
unsigned int sh_type;
|
||||
int elfclass, elftype;
|
||||
size_t fsz, msz, count;
|
||||
size_t count, fsz, msz;
|
||||
struct _Libelf_Data *d;
|
||||
uint64_t sh_align, sh_offset, sh_size;
|
||||
int (*xlate)(char *_d, size_t _dsz, char *_s, size_t _c, int _swap);
|
||||
int (*xlate)(unsigned char *_d, size_t _dsz, unsigned char *_s,
|
||||
size_t _c, int _swap);
|
||||
|
||||
d = (struct _Libelf_Data *) ed;
|
||||
|
||||
@ -108,11 +110,23 @@ elf_getdata(Elf_Scn *s, Elf_Data *ed)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
count = sh_size / fsz;
|
||||
if (sh_size / fsz > SIZE_MAX) {
|
||||
LIBELF_SET_ERROR(RANGE, 0);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
count = (size_t) (sh_size / fsz);
|
||||
|
||||
msz = _libelf_msize(elftype, elfclass, e->e_version);
|
||||
|
||||
if (count > 0 && msz > SIZE_MAX / count) {
|
||||
LIBELF_SET_ERROR(RANGE, 0);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
assert(msz > 0);
|
||||
assert(count <= SIZE_MAX);
|
||||
assert(msz * count <= SIZE_MAX);
|
||||
|
||||
if ((d = _libelf_allocate_data(s)) == NULL)
|
||||
return (NULL);
|
||||
@ -129,7 +143,7 @@ elf_getdata(Elf_Scn *s, Elf_Data *ed)
|
||||
return (&d->d_data);
|
||||
}
|
||||
|
||||
if ((d->d_data.d_buf = malloc(msz*count)) == NULL) {
|
||||
if ((d->d_data.d_buf = malloc(msz * count)) == NULL) {
|
||||
(void) _libelf_release_data(d);
|
||||
LIBELF_SET_ERROR(RESOURCE, 0);
|
||||
return (NULL);
|
||||
@ -138,7 +152,7 @@ elf_getdata(Elf_Scn *s, Elf_Data *ed)
|
||||
d->d_flags |= LIBELF_F_DATA_MALLOCED;
|
||||
|
||||
xlate = _libelf_get_translator(elftype, ELF_TOMEMORY, elfclass);
|
||||
if (!(*xlate)(d->d_data.d_buf, d->d_data.d_size,
|
||||
if (!(*xlate)(d->d_data.d_buf, (size_t) d->d_data.d_size,
|
||||
e->e_rawfile + sh_offset, count,
|
||||
e->e_byteorder != LIBELF_PRIVATE(byteorder))) {
|
||||
_libelf_release_data(d);
|
||||
|
@ -32,7 +32,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_errmsg.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_errmsg.c 3012 2014-03-23 03:41:38Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Retrieve a human readable translation for an error message.
|
||||
@ -76,7 +76,7 @@ elf_errmsg(int error)
|
||||
if (error < ELF_E_NONE || error >= ELF_E_NUM)
|
||||
return _libelf_errors[ELF_E_NUM];
|
||||
if (oserr) {
|
||||
(void) snprintf(LIBELF_PRIVATE(msg),
|
||||
(void) snprintf((char *) LIBELF_PRIVATE(msg),
|
||||
sizeof(LIBELF_PRIVATE(msg)), "%s: %s",
|
||||
_libelf_errors[error], strerror(oserr));
|
||||
return (const char *)&LIBELF_PRIVATE(msg);
|
||||
|
@ -30,7 +30,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_flag.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_flag.c 2988 2014-03-17 08:51:49Z jkoshy $");
|
||||
|
||||
unsigned int
|
||||
elf_flagarhdr(Elf_Arhdr *a, Elf_Cmd c, unsigned int flags)
|
||||
@ -111,7 +111,7 @@ elf_flagehdr(Elf *e, Elf_Cmd c, unsigned int flags)
|
||||
unsigned int
|
||||
elf_flagelf(Elf *e, Elf_Cmd c, unsigned int flags)
|
||||
{
|
||||
int r;
|
||||
unsigned int r;
|
||||
|
||||
if (e == NULL)
|
||||
return (0);
|
||||
@ -173,7 +173,7 @@ elf_flagphdr(Elf *e, Elf_Cmd c, unsigned int flags)
|
||||
unsigned int
|
||||
elf_flagscn(Elf_Scn *s, Elf_Cmd c, unsigned int flags)
|
||||
{
|
||||
int r;
|
||||
unsigned int r;
|
||||
|
||||
if (s == NULL)
|
||||
return (0);
|
||||
|
@ -28,7 +28,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_memory.c 2368 2011-12-29 06:34:28Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_memory.c 3013 2014-03-23 06:16:59Z jkoshy $");
|
||||
|
||||
Elf *
|
||||
elf_memory(char *image, size_t sz)
|
||||
@ -43,5 +43,5 @@ elf_memory(char *image, size_t sz)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
return (_libelf_memory(image, sz, 1));
|
||||
return (_libelf_memory((unsigned char *) image, sz, 1));
|
||||
}
|
||||
|
@ -32,7 +32,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_next.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_next.c 2989 2014-03-17 09:56:46Z jkoshy $");
|
||||
|
||||
Elf_Cmd
|
||||
elf_next(Elf *e)
|
||||
@ -48,13 +48,17 @@ elf_next(Elf *e)
|
||||
return (ELF_C_NULL);
|
||||
}
|
||||
|
||||
assert (parent->e_kind == ELF_K_AR);
|
||||
assert (parent->e_cmd == ELF_C_READ);
|
||||
assert(parent->e_kind == ELF_K_AR);
|
||||
assert(parent->e_cmd == ELF_C_READ);
|
||||
assert(e->e_rawfile > parent->e_rawfile);
|
||||
|
||||
next = e->e_rawfile - parent->e_rawfile + e->e_rawsize;
|
||||
next = e->e_rawfile - parent->e_rawfile + (off_t) e->e_rawsize;
|
||||
next = (next + 1) & ~1; /* round up to an even boundary */
|
||||
|
||||
/*
|
||||
* Setup the 'e_next' field of the archive descriptor for the
|
||||
* next call to 'elf_begin()'.
|
||||
*/
|
||||
parent->e_u.e_ar.e_next = (next >= (off_t) parent->e_rawsize) ?
|
||||
(off_t) 0 : next;
|
||||
|
||||
|
@ -63,5 +63,5 @@ elf_openmemory(char *image, size_t sz)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
return (_libelf_memory(image, sz, 0));
|
||||
return (_libelf_memory((unsigned char *) image, sz, 0));
|
||||
}
|
||||
|
@ -31,7 +31,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_rand.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_rand.c 2991 2014-03-17 09:57:04Z jkoshy $");
|
||||
|
||||
off_t
|
||||
elf_rand(Elf *ar, off_t offset)
|
||||
@ -40,7 +40,7 @@ elf_rand(Elf *ar, off_t offset)
|
||||
|
||||
if (ar == NULL || ar->e_kind != ELF_K_AR ||
|
||||
(offset & 1) || offset < SARMAG ||
|
||||
offset + sizeof(struct ar_hdr) >= ar->e_rawsize) {
|
||||
(size_t) offset + sizeof(struct ar_hdr) >= ar->e_rawsize) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return 0;
|
||||
}
|
||||
|
@ -30,13 +30,13 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_rawfile.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_rawfile.c 3013 2014-03-23 06:16:59Z jkoshy $");
|
||||
|
||||
char *
|
||||
elf_rawfile(Elf *e, size_t *sz)
|
||||
{
|
||||
char *ptr;
|
||||
size_t size;
|
||||
unsigned char *ptr;
|
||||
|
||||
size = e ? e->e_rawsize : 0;
|
||||
ptr = NULL;
|
||||
@ -49,5 +49,5 @@ elf_rawfile(Elf *e, size_t *sz)
|
||||
if (sz)
|
||||
*sz = size;
|
||||
|
||||
return (ptr);
|
||||
return ((char *) ptr);
|
||||
}
|
||||
|
@ -36,7 +36,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_scn.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_scn.c 3013 2014-03-23 06:16:59Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Load an ELF section table and create a list of Elf_Scn structures.
|
||||
@ -44,14 +44,15 @@ ELFTC_VCSID("$Id: elf_scn.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
int
|
||||
_libelf_load_section_headers(Elf *e, void *ehdr)
|
||||
{
|
||||
int ec, swapbytes;
|
||||
size_t fsz, i, shnum;
|
||||
Elf_Scn *scn;
|
||||
uint64_t shoff;
|
||||
char *src;
|
||||
Elf32_Ehdr *eh32;
|
||||
Elf64_Ehdr *eh64;
|
||||
Elf_Scn *scn;
|
||||
int (*xlator)(char *_d, size_t _dsz, char *_s, size_t _c, int _swap);
|
||||
int ec, swapbytes;
|
||||
unsigned char *src;
|
||||
size_t fsz, i, shnum;
|
||||
int (*xlator)(unsigned char *_d, size_t _dsz, unsigned char *_s,
|
||||
size_t _c, int _swap);
|
||||
|
||||
assert(e != NULL);
|
||||
assert(ehdr != NULL);
|
||||
@ -104,8 +105,8 @@ _libelf_load_section_headers(Elf *e, void *ehdr)
|
||||
if ((scn = _libelf_allocate_scn(e, i)) == NULL)
|
||||
return (0);
|
||||
|
||||
(*xlator)((char *) &scn->s_shdr, sizeof(scn->s_shdr), src,
|
||||
(size_t) 1, swapbytes);
|
||||
(*xlator)((unsigned char *) &scn->s_shdr, sizeof(scn->s_shdr),
|
||||
src, (size_t) 1, swapbytes);
|
||||
|
||||
if (ec == ELFCLASS32) {
|
||||
scn->s_offset = scn->s_rawoff =
|
||||
|
@ -31,7 +31,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elf_strptr.c 2271 2011-12-03 17:06:35Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_strptr.c 2990 2014-03-17 09:56:58Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Convert an ELF section#,offset pair to a string pointer.
|
||||
@ -42,8 +42,8 @@ elf_strptr(Elf *e, size_t scndx, size_t offset)
|
||||
{
|
||||
Elf_Scn *s;
|
||||
Elf_Data *d;
|
||||
size_t alignment, count;
|
||||
GElf_Shdr shdr;
|
||||
uint64_t alignment, count;
|
||||
|
||||
if (e == NULL || e->e_kind != ELF_K_ELF) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
@ -90,7 +90,7 @@ elf_strptr(Elf *e, size_t scndx, size_t offset)
|
||||
* account 'holes' in coverage of the section introduced
|
||||
* by alignment requirements.
|
||||
*/
|
||||
count = (size_t) 0; /* cumulative count of bytes seen */
|
||||
count = (uint64_t) 0; /* cumulative count of bytes seen */
|
||||
while ((d = elf_getdata(s, d)) != NULL && count <= offset) {
|
||||
|
||||
if (d->d_buf == NULL || d->d_size == 0)
|
||||
|
@ -41,7 +41,7 @@
|
||||
#include <sys/mman.h>
|
||||
#endif
|
||||
|
||||
ELFTC_VCSID("$Id: elf_update.c 2931 2013-03-23 11:41:07Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elf_update.c 3013 2014-03-23 06:16:59Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Layout strategy:
|
||||
@ -110,14 +110,13 @@ SLIST_HEAD(_Elf_Extent_List, _Elf_Extent);
|
||||
static int
|
||||
_libelf_compute_section_extents(Elf *e, Elf_Scn *s, off_t rc)
|
||||
{
|
||||
int ec;
|
||||
Elf_Data *d;
|
||||
size_t fsz, msz;
|
||||
int ec, elftype;
|
||||
uint32_t sh_type;
|
||||
uint64_t d_align;
|
||||
Elf32_Shdr *shdr32;
|
||||
Elf64_Shdr *shdr64;
|
||||
unsigned int elftype;
|
||||
struct _Libelf_Data *ld;
|
||||
uint64_t scn_size, scn_alignment;
|
||||
uint64_t sh_align, sh_entsize, sh_offset, sh_size;
|
||||
@ -253,7 +252,7 @@ _libelf_compute_section_extents(Elf *e, Elf_Scn *s, off_t rc)
|
||||
scn_size = roundup2(scn_size, d->d_align);
|
||||
d->d_off = scn_size;
|
||||
fsz = _libelf_fsize(d->d_type, ec, d->d_version,
|
||||
d->d_size / msz);
|
||||
(size_t) d->d_size / msz);
|
||||
scn_size += fsz;
|
||||
}
|
||||
|
||||
@ -307,7 +306,7 @@ computeoffset:
|
||||
* Compute the new offset for the section based on
|
||||
* the section's alignment needs.
|
||||
*/
|
||||
sh_offset = roundup(rc, sh_align);
|
||||
sh_offset = roundup((uint64_t) rc, sh_align);
|
||||
|
||||
/*
|
||||
* Update the section header.
|
||||
@ -471,7 +470,7 @@ _libelf_resync_sections(Elf *e, off_t rc, struct _Elf_Extent_List *extents)
|
||||
return ((off_t) -1);
|
||||
|
||||
if ((size_t) rc < s->s_offset + s->s_size)
|
||||
rc = s->s_offset + s->s_size;
|
||||
rc = (off_t) (s->s_offset + s->s_size);
|
||||
}
|
||||
|
||||
return (rc);
|
||||
@ -529,17 +528,22 @@ _libelf_resync_elf(Elf *e, struct _Elf_Extent_List *extents)
|
||||
if (ec == ELFCLASS32) {
|
||||
eh_byteorder = eh32->e_ident[EI_DATA];
|
||||
eh_class = eh32->e_ident[EI_CLASS];
|
||||
phoff = (uint64_t) eh32->e_phoff;
|
||||
shoff = (uint64_t) eh32->e_shoff;
|
||||
phoff = (off_t) eh32->e_phoff;
|
||||
shoff = (off_t) eh32->e_shoff;
|
||||
eh_version = eh32->e_version;
|
||||
} else {
|
||||
eh_byteorder = eh64->e_ident[EI_DATA];
|
||||
eh_class = eh64->e_ident[EI_CLASS];
|
||||
phoff = eh64->e_phoff;
|
||||
shoff = eh64->e_shoff;
|
||||
phoff = (off_t) eh64->e_phoff;
|
||||
shoff = (off_t) eh64->e_shoff;
|
||||
eh_version = eh64->e_version;
|
||||
}
|
||||
|
||||
if (phoff < 0 || shoff < 0) {
|
||||
LIBELF_SET_ERROR(HEADER, 0);
|
||||
return ((off_t) -1);
|
||||
}
|
||||
|
||||
if (eh_version == EV_NONE)
|
||||
eh_version = EV_CURRENT;
|
||||
|
||||
@ -564,18 +568,20 @@ _libelf_resync_elf(Elf *e, struct _Elf_Extent_List *extents)
|
||||
e->e_byteorder = eh_byteorder;
|
||||
|
||||
#define INITIALIZE_EHDR(E,EC,V) do { \
|
||||
unsigned int _version = (unsigned int) (V); \
|
||||
(E)->e_ident[EI_MAG0] = ELFMAG0; \
|
||||
(E)->e_ident[EI_MAG1] = ELFMAG1; \
|
||||
(E)->e_ident[EI_MAG2] = ELFMAG2; \
|
||||
(E)->e_ident[EI_MAG3] = ELFMAG3; \
|
||||
(E)->e_ident[EI_CLASS] = (EC); \
|
||||
(E)->e_ident[EI_VERSION] = (V); \
|
||||
(E)->e_ehsize = _libelf_fsize(ELF_T_EHDR, (EC), (V), \
|
||||
(size_t) 1); \
|
||||
(E)->e_phentsize = (phnum == 0) ? 0 : _libelf_fsize( \
|
||||
ELF_T_PHDR, (EC), (V), (size_t) 1); \
|
||||
(E)->e_shentsize = _libelf_fsize(ELF_T_SHDR, (EC), (V), \
|
||||
(size_t) 1); \
|
||||
(E)->e_ident[EI_CLASS] = (unsigned char) (EC); \
|
||||
(E)->e_ident[EI_VERSION] = (_version & 0xFFU); \
|
||||
(E)->e_ehsize = (uint16_t) _libelf_fsize(ELF_T_EHDR, \
|
||||
(EC), _version, (size_t) 1); \
|
||||
(E)->e_phentsize = (uint16_t) ((phnum == 0) ? 0 : \
|
||||
_libelf_fsize(ELF_T_PHDR, (EC), _version, \
|
||||
(size_t) 1)); \
|
||||
(E)->e_shentsize = (uint16_t) _libelf_fsize(ELF_T_SHDR, \
|
||||
(EC), _version, (size_t) 1); \
|
||||
} while (0)
|
||||
|
||||
if (ec == ELFCLASS32)
|
||||
@ -585,9 +591,10 @@ _libelf_resync_elf(Elf *e, struct _Elf_Extent_List *extents)
|
||||
|
||||
(void) elf_flagehdr(e, ELF_C_SET, ELF_F_DIRTY);
|
||||
|
||||
rc += _libelf_fsize(ELF_T_EHDR, ec, eh_version, (size_t) 1);
|
||||
rc += (off_t) _libelf_fsize(ELF_T_EHDR, ec, eh_version, (size_t) 1);
|
||||
|
||||
if (!_libelf_insert_extent(extents, ELF_EXTENT_EHDR, 0, rc, ehdr))
|
||||
if (!_libelf_insert_extent(extents, ELF_EXTENT_EHDR, 0, (uint64_t) rc,
|
||||
ehdr))
|
||||
return ((off_t) -1);
|
||||
|
||||
/*
|
||||
@ -608,20 +615,20 @@ _libelf_resync_elf(Elf *e, struct _Elf_Extent_List *extents)
|
||||
return ((off_t) -1);
|
||||
}
|
||||
|
||||
if (phoff % align) {
|
||||
if (phoff % (off_t) align) {
|
||||
LIBELF_SET_ERROR(LAYOUT, 0);
|
||||
return ((off_t) -1);
|
||||
}
|
||||
|
||||
} else
|
||||
phoff = roundup(rc, align);
|
||||
phoff = roundup(rc, (off_t) align);
|
||||
|
||||
rc = phoff + fsz;
|
||||
rc = phoff + (off_t) fsz;
|
||||
|
||||
phdr = _libelf_getphdr(e, ec);
|
||||
|
||||
if (!_libelf_insert_extent(extents, ELF_EXTENT_PHDR, phoff,
|
||||
fsz, phdr))
|
||||
if (!_libelf_insert_extent(extents, ELF_EXTENT_PHDR,
|
||||
(uint64_t) phoff, fsz, phdr))
|
||||
return ((off_t) -1);
|
||||
} else
|
||||
phoff = 0;
|
||||
@ -656,18 +663,18 @@ _libelf_resync_elf(Elf *e, struct _Elf_Extent_List *extents)
|
||||
align = _libelf_falign(ELF_T_SHDR, ec);
|
||||
|
||||
if (e->e_flags & ELF_F_LAYOUT) {
|
||||
if (shoff % align) {
|
||||
if (shoff % (off_t) align) {
|
||||
LIBELF_SET_ERROR(LAYOUT, 0);
|
||||
return ((off_t) -1);
|
||||
}
|
||||
} else
|
||||
shoff = roundup(rc, align);
|
||||
shoff = roundup(rc, (off_t) align);
|
||||
|
||||
if (shoff + fsz > (size_t) rc)
|
||||
rc = shoff + fsz;
|
||||
if (shoff + (off_t) fsz > rc)
|
||||
rc = shoff + (off_t) fsz;
|
||||
|
||||
if (!_libelf_insert_extent(extents, ELF_EXTENT_SHDR, shoff,
|
||||
fsz, NULL))
|
||||
if (!_libelf_insert_extent(extents, ELF_EXTENT_SHDR,
|
||||
(uint64_t) shoff, fsz, NULL))
|
||||
return ((off_t) -1);
|
||||
} else
|
||||
shoff = 0;
|
||||
@ -700,22 +707,23 @@ _libelf_resync_elf(Elf *e, struct _Elf_Extent_List *extents)
|
||||
* Write out the contents of an ELF section.
|
||||
*/
|
||||
|
||||
static size_t
|
||||
_libelf_write_scn(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
static off_t
|
||||
_libelf_write_scn(Elf *e, unsigned char *nf, struct _Elf_Extent *ex)
|
||||
{
|
||||
int ec;
|
||||
off_t rc;
|
||||
Elf_Scn *s;
|
||||
int elftype;
|
||||
Elf_Data *d, dst;
|
||||
uint32_t sh_type;
|
||||
struct _Libelf_Data *ld;
|
||||
uint64_t sh_off, sh_size;
|
||||
size_t fsz, msz, nobjects, rc;
|
||||
size_t fsz, msz, nobjects;
|
||||
|
||||
assert(ex->ex_type == ELF_EXTENT_SECTION);
|
||||
|
||||
s = ex->ex_desc;
|
||||
rc = ex->ex_start;
|
||||
rc = (off_t) ex->ex_start;
|
||||
|
||||
if ((ec = e->e_class) == ELFCLASS32) {
|
||||
sh_type = s->s_shdr.s_shdr32.sh_type;
|
||||
@ -756,18 +764,20 @@ _libelf_write_scn(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
|
||||
if ((uint64_t) rc < sh_off + d->d_off)
|
||||
(void) memset(nf + rc,
|
||||
LIBELF_PRIVATE(fillchar), sh_off +
|
||||
d->d_off - rc);
|
||||
rc = sh_off + d->d_off;
|
||||
LIBELF_PRIVATE(fillchar),
|
||||
(size_t) (sh_off + d->d_off -
|
||||
(uint64_t) rc));
|
||||
rc = (off_t) (sh_off + d->d_off);
|
||||
|
||||
assert(d->d_buf != NULL);
|
||||
assert(d->d_type == ELF_T_BYTE);
|
||||
assert(d->d_version == e->e_version);
|
||||
|
||||
(void) memcpy(nf + rc,
|
||||
e->e_rawfile + s->s_rawoff + d->d_off, d->d_size);
|
||||
e->e_rawfile + s->s_rawoff + d->d_off,
|
||||
(size_t) d->d_size);
|
||||
|
||||
rc += d->d_size;
|
||||
rc += (off_t) d->d_size;
|
||||
}
|
||||
|
||||
return (rc);
|
||||
@ -789,15 +799,16 @@ _libelf_write_scn(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
|
||||
if ((uint64_t) rc < sh_off + d->d_off)
|
||||
(void) memset(nf + rc,
|
||||
LIBELF_PRIVATE(fillchar), sh_off + d->d_off - rc);
|
||||
LIBELF_PRIVATE(fillchar),
|
||||
(size_t) (sh_off + d->d_off - (uint64_t) rc));
|
||||
|
||||
rc = sh_off + d->d_off;
|
||||
rc = (off_t) (sh_off + d->d_off);
|
||||
|
||||
assert(d->d_buf != NULL);
|
||||
assert(d->d_version == e->e_version);
|
||||
assert(d->d_size % msz == 0);
|
||||
|
||||
nobjects = d->d_size / msz;
|
||||
nobjects = (size_t) (d->d_size / msz);
|
||||
|
||||
fsz = _libelf_fsize(d->d_type, ec, e->e_version, nobjects);
|
||||
|
||||
@ -808,10 +819,10 @@ _libelf_write_scn(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
NULL)
|
||||
return ((off_t) -1);
|
||||
|
||||
rc += fsz;
|
||||
rc += (off_t) fsz;
|
||||
}
|
||||
|
||||
return ((off_t) rc);
|
||||
return (rc);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -819,7 +830,7 @@ _libelf_write_scn(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
*/
|
||||
|
||||
static off_t
|
||||
_libelf_write_ehdr(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
_libelf_write_ehdr(Elf *e, unsigned char *nf, struct _Elf_Extent *ex)
|
||||
{
|
||||
int ec;
|
||||
void *ehdr;
|
||||
@ -860,7 +871,7 @@ _libelf_write_ehdr(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
*/
|
||||
|
||||
static off_t
|
||||
_libelf_write_phdr(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
_libelf_write_phdr(Elf *e, unsigned char *nf, struct _Elf_Extent *ex)
|
||||
{
|
||||
int ec;
|
||||
void *ehdr;
|
||||
@ -909,7 +920,7 @@ _libelf_write_phdr(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
NULL)
|
||||
return ((off_t) -1);
|
||||
|
||||
return (phoff + fsz);
|
||||
return ((off_t) (phoff + fsz));
|
||||
}
|
||||
|
||||
/*
|
||||
@ -917,7 +928,7 @@ _libelf_write_phdr(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
*/
|
||||
|
||||
static off_t
|
||||
_libelf_write_shdr(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
_libelf_write_shdr(Elf *e, unsigned char *nf, struct _Elf_Extent *ex)
|
||||
{
|
||||
int ec;
|
||||
void *ehdr;
|
||||
@ -969,7 +980,7 @@ _libelf_write_shdr(Elf *e, char *nf, struct _Elf_Extent *ex)
|
||||
return ((off_t) -1);
|
||||
}
|
||||
|
||||
return (ex->ex_start + nscn * fsz);
|
||||
return ((off_t) (ex->ex_start + nscn * fsz));
|
||||
}
|
||||
|
||||
/*
|
||||
@ -993,9 +1004,9 @@ static off_t
|
||||
_libelf_write_elf(Elf *e, off_t newsize, struct _Elf_Extent_List *extents)
|
||||
{
|
||||
off_t nrc, rc;
|
||||
char *newfile;
|
||||
Elf_Scn *scn, *tscn;
|
||||
struct _Elf_Extent *ex;
|
||||
unsigned char *newfile;
|
||||
|
||||
assert(e->e_kind == ELF_K_ELF);
|
||||
assert(e->e_cmd == ELF_C_RDWR || e->e_cmd == ELF_C_WRITE);
|
||||
@ -1012,7 +1023,7 @@ _libelf_write_elf(Elf *e, off_t newsize, struct _Elf_Extent_List *extents)
|
||||
/* Fill inter-extent gaps. */
|
||||
if (ex->ex_start > (size_t) rc)
|
||||
(void) memset(newfile + rc, LIBELF_PRIVATE(fillchar),
|
||||
ex->ex_start - rc);
|
||||
(size_t) (ex->ex_start - (uint64_t) rc));
|
||||
|
||||
switch (ex->ex_type) {
|
||||
case ELF_EXTENT_EHDR:
|
||||
@ -1103,7 +1114,7 @@ _libelf_write_elf(Elf *e, off_t newsize, struct _Elf_Extent_List *extents)
|
||||
#endif /* ELFTC_HAVE_MMAP */
|
||||
|
||||
/* Record the new size of the file. */
|
||||
e->e_rawsize = newsize;
|
||||
e->e_rawsize = (size_t) newsize;
|
||||
} else {
|
||||
/* File opened in ELF_C_WRITE mode. */
|
||||
assert(e->e_rawfile == NULL);
|
||||
|
@ -29,10 +29,11 @@
|
||||
#include <assert.h>
|
||||
#include <gelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_cap.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_cap.c 2995 2014-03-18 02:16:31Z jkoshy $");
|
||||
|
||||
GElf_Cap *
|
||||
gelf_getcap(Elf_Data *ed, int ndx, GElf_Cap *dst)
|
||||
@ -72,7 +73,7 @@ gelf_getcap(Elf_Data *ed, int ndx, GElf_Cap *dst)
|
||||
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -131,7 +132,7 @@ gelf_update_cap(Elf_Data *ed, int ndx, GElf_Cap *gc)
|
||||
msz = _libelf_msize(ELF_T_CAP, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
|
@ -29,10 +29,11 @@
|
||||
#include <assert.h>
|
||||
#include <gelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_dyn.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_dyn.c 2998 2014-03-18 17:19:00Z jkoshy $");
|
||||
|
||||
GElf_Dyn *
|
||||
gelf_getdyn(Elf_Data *ed, int ndx, GElf_Dyn *dst)
|
||||
@ -71,8 +72,9 @@ gelf_getdyn(Elf_Data *ed, int ndx, GElf_Dyn *dst)
|
||||
msz = _libelf_msize(ELF_T_DYN, ec, e->e_version);
|
||||
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -128,9 +130,11 @@ gelf_update_dyn(Elf_Data *ed, int ndx, GElf_Dyn *ds)
|
||||
}
|
||||
|
||||
msz = _libelf_msize(ELF_T_DYN, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
|
@ -30,6 +30,7 @@
|
||||
#include <gelf.h>
|
||||
#include <libelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
@ -29,10 +29,11 @@
|
||||
#include <assert.h>
|
||||
#include <gelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_move.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_move.c 2998 2014-03-18 17:19:00Z jkoshy $");
|
||||
|
||||
GElf_Move *
|
||||
gelf_getmove(Elf_Data *ed, int ndx, GElf_Move *dst)
|
||||
@ -71,8 +72,9 @@ gelf_getmove(Elf_Data *ed, int ndx, GElf_Move *dst)
|
||||
msz = _libelf_msize(ELF_T_MOVE, ec, e->e_version);
|
||||
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -131,9 +133,11 @@ gelf_update_move(Elf_Data *ed, int ndx, GElf_Move *gm)
|
||||
}
|
||||
|
||||
msz = _libelf_msize(ELF_T_MOVE, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
|
@ -29,6 +29,7 @@
|
||||
#include <gelf.h>
|
||||
#include <libelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
|
@ -29,10 +29,11 @@
|
||||
#include <assert.h>
|
||||
#include <gelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_rel.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_rel.c 2998 2014-03-18 17:19:00Z jkoshy $");
|
||||
|
||||
GElf_Rel *
|
||||
gelf_getrel(Elf_Data *ed, int ndx, GElf_Rel *dst)
|
||||
@ -71,8 +72,9 @@ gelf_getrel(Elf_Data *ed, int ndx, GElf_Rel *dst)
|
||||
msz = _libelf_msize(ELF_T_REL, ec, e->e_version);
|
||||
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -130,9 +132,11 @@ gelf_update_rel(Elf_Data *ed, int ndx, GElf_Rel *dr)
|
||||
}
|
||||
|
||||
msz = _libelf_msize(ELF_T_REL, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
@ -147,8 +151,9 @@ gelf_update_rel(Elf_Data *ed, int ndx, GElf_Rel *dr)
|
||||
LIBELF_SET_ERROR(RANGE, 0);
|
||||
return (0);
|
||||
}
|
||||
rel32->r_info = ELF32_R_INFO(ELF64_R_SYM(dr->r_info),
|
||||
ELF64_R_TYPE(dr->r_info));
|
||||
rel32->r_info = ELF32_R_INFO(
|
||||
(Elf32_Word) ELF64_R_SYM(dr->r_info),
|
||||
(Elf32_Word) ELF64_R_TYPE(dr->r_info));
|
||||
} else {
|
||||
rel64 = (Elf64_Rel *) d->d_data.d_buf + ndx;
|
||||
|
||||
|
@ -29,10 +29,11 @@
|
||||
#include <assert.h>
|
||||
#include <gelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_rela.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_rela.c 2998 2014-03-18 17:19:00Z jkoshy $");
|
||||
|
||||
GElf_Rela *
|
||||
gelf_getrela(Elf_Data *ed, int ndx, GElf_Rela *dst)
|
||||
@ -71,8 +72,9 @@ gelf_getrela(Elf_Data *ed, int ndx, GElf_Rela *dst)
|
||||
msz = _libelf_msize(ELF_T_RELA, ec, e->e_version);
|
||||
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -131,9 +133,11 @@ gelf_update_rela(Elf_Data *ed, int ndx, GElf_Rela *dr)
|
||||
}
|
||||
|
||||
msz = _libelf_msize(ELF_T_RELA, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
@ -148,8 +152,9 @@ gelf_update_rela(Elf_Data *ed, int ndx, GElf_Rela *dr)
|
||||
LIBELF_SET_ERROR(RANGE, 0);
|
||||
return (0);
|
||||
}
|
||||
rela32->r_info = ELF32_R_INFO(ELF64_R_SYM(dr->r_info),
|
||||
ELF64_R_TYPE(dr->r_info));
|
||||
rela32->r_info = ELF32_R_INFO(
|
||||
(Elf32_Word) ELF64_R_SYM(dr->r_info),
|
||||
(Elf32_Word) ELF64_R_TYPE(dr->r_info));
|
||||
|
||||
LIBELF_COPY_S32(rela32, dr, r_addend);
|
||||
} else {
|
||||
|
@ -30,6 +30,7 @@
|
||||
#include <gelf.h>
|
||||
#include <libelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
|
@ -29,10 +29,11 @@
|
||||
#include <assert.h>
|
||||
#include <gelf.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_sym.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_sym.c 2999 2014-03-18 17:19:06Z jkoshy $");
|
||||
|
||||
GElf_Sym *
|
||||
gelf_getsym(Elf_Data *ed, int ndx, GElf_Sym *dst)
|
||||
@ -71,25 +72,23 @@ gelf_getsym(Elf_Data *ed, int ndx, GElf_Sym *dst)
|
||||
msz = _libelf_msize(ELF_T_SYM, ec, e->e_version);
|
||||
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
if (ec == ELFCLASS32) {
|
||||
|
||||
sym32 = (Elf32_Sym *) d->d_data.d_buf + ndx;
|
||||
|
||||
dst->st_name = sym32->st_name;
|
||||
dst->st_value = (Elf64_Addr) sym32->st_value;
|
||||
dst->st_size = (Elf64_Xword) sym32->st_size;
|
||||
dst->st_info = ELF64_ST_INFO(ELF32_ST_BIND(sym32->st_info),
|
||||
ELF32_ST_TYPE(sym32->st_info));
|
||||
dst->st_info = sym32->st_info;
|
||||
dst->st_other = sym32->st_other;
|
||||
dst->st_shndx = sym32->st_shndx;
|
||||
} else {
|
||||
|
||||
sym64 = (Elf64_Sym *) d->d_data.d_buf + ndx;
|
||||
|
||||
*dst = *sym64;
|
||||
@ -133,9 +132,11 @@ gelf_update_sym(Elf_Data *ed, int ndx, GElf_Sym *gs)
|
||||
}
|
||||
|
||||
msz = _libelf_msize(ELF_T_SYM, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
|
@ -31,7 +31,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_syminfo.c 2272 2011-12-03 17:07:31Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_syminfo.c 2998 2014-03-18 17:19:00Z jkoshy $");
|
||||
|
||||
GElf_Syminfo *
|
||||
gelf_getsyminfo(Elf_Data *ed, int ndx, GElf_Syminfo *dst)
|
||||
@ -70,8 +70,9 @@ gelf_getsyminfo(Elf_Data *ed, int ndx, GElf_Syminfo *dst)
|
||||
msz = _libelf_msize(ELF_T_SYMINFO, ec, e->e_version);
|
||||
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -128,9 +129,11 @@ gelf_update_syminfo(Elf_Data *ed, int ndx, GElf_Syminfo *gs)
|
||||
}
|
||||
|
||||
msz = _libelf_msize(ELF_T_SYMINFO, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= d->d_data.d_size) {
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * (size_t) ndx >= d->d_data.d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
|
@ -31,7 +31,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: gelf_symshndx.c 2283 2011-12-04 04:07:24Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: gelf_symshndx.c 2998 2014-03-18 17:19:00Z jkoshy $");
|
||||
|
||||
GElf_Sym *
|
||||
gelf_getsymshndx(Elf_Data *d, Elf_Data *id, int ndx, GElf_Sym *dst,
|
||||
@ -74,8 +74,9 @@ gelf_getsymshndx(Elf_Data *d, Elf_Data *id, int ndx, GElf_Sym *dst,
|
||||
msz = _libelf_msize(ELF_T_WORD, ec, e->e_version);
|
||||
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * ndx >= id->d_size) {
|
||||
if (msz * (size_t) ndx >= id->d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -123,9 +124,11 @@ gelf_update_symshndx(Elf_Data *d, Elf_Data *id, int ndx, GElf_Sym *gs,
|
||||
}
|
||||
|
||||
msz = _libelf_msize(ELF_T_WORD, ec, e->e_version);
|
||||
assert(msz > 0);
|
||||
|
||||
if (msz * ndx >= id->d_size) {
|
||||
assert(msz > 0);
|
||||
assert(ndx >= 0);
|
||||
|
||||
if (msz * (size_t) ndx >= id->d_size) {
|
||||
LIBELF_SET_ERROR(ARGUMENT, 0);
|
||||
return (0);
|
||||
}
|
||||
|
@ -23,7 +23,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: libelf.h 2366 2011-12-29 06:12:14Z jkoshy $
|
||||
* $Id: libelf.h 2988 2014-03-17 08:51:49Z jkoshy $
|
||||
*/
|
||||
|
||||
#ifndef _LIBELF_H_
|
||||
@ -129,7 +129,7 @@ typedef struct {
|
||||
/*
|
||||
* Members that are not part of the public API.
|
||||
*/
|
||||
int ar_flags;
|
||||
unsigned int ar_flags;
|
||||
} Elf_Arhdr;
|
||||
|
||||
/*
|
||||
|
@ -32,11 +32,11 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_align.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_align.c 3006 2014-03-22 08:10:07Z jkoshy $");
|
||||
|
||||
struct align {
|
||||
int a32;
|
||||
int a64;
|
||||
unsigned int a32;
|
||||
unsigned int a64;
|
||||
};
|
||||
|
||||
#ifdef __GNUC__
|
||||
@ -87,7 +87,7 @@ static struct align malign[ELF_T_NUM] = {
|
||||
[ELF_T_GNUHASH] = MALIGN_WORD()
|
||||
};
|
||||
|
||||
int
|
||||
unsigned int
|
||||
_libelf_malign(Elf_Type t, int elfclass)
|
||||
{
|
||||
if (t >= ELF_T_NUM || (int) t < 0)
|
||||
@ -126,7 +126,7 @@ static struct align falign[ELF_T_NUM] = {
|
||||
[ELF_T_GNUHASH] = FALIGN(4,8)
|
||||
};
|
||||
|
||||
int
|
||||
unsigned int
|
||||
_libelf_falign(Elf_Type t, int elfclass)
|
||||
{
|
||||
if (t >= ELF_T_NUM || (int) t < 0)
|
||||
|
@ -35,7 +35,7 @@
|
||||
#include "_libelf.h"
|
||||
#include "_libelf_ar.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_ar.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_ar.c 3013 2014-03-23 06:16:59Z jkoshy $");
|
||||
|
||||
#define LIBELF_NALLOC_SIZE 16
|
||||
|
||||
@ -110,8 +110,8 @@ Elf_Arhdr *
|
||||
_libelf_ar_gethdr(Elf *e)
|
||||
{
|
||||
Elf *parent;
|
||||
char *namelen;
|
||||
Elf_Arhdr *eh;
|
||||
char *namelen;
|
||||
size_t n, nlen;
|
||||
struct ar_hdr *arh;
|
||||
|
||||
@ -192,7 +192,7 @@ _libelf_ar_gethdr(Elf *e)
|
||||
}
|
||||
|
||||
e->e_flags &= ~LIBELF_F_AR_HEADER;
|
||||
e->e_hdr.e_rawhdr = (char *) arh;
|
||||
e->e_hdr.e_rawhdr = (unsigned char *) arh;
|
||||
|
||||
return (NULL);
|
||||
}
|
||||
@ -201,10 +201,10 @@ Elf *
|
||||
_libelf_ar_open_member(int fd, Elf_Cmd c, Elf *elf)
|
||||
{
|
||||
Elf *e;
|
||||
char *member, *namelen;
|
||||
size_t nsz, sz;
|
||||
off_t next;
|
||||
size_t nsz, sz;
|
||||
struct ar_hdr *arh;
|
||||
char *member, *namelen;
|
||||
|
||||
assert(elf->e_kind == ELF_K_AR);
|
||||
|
||||
@ -249,12 +249,12 @@ _libelf_ar_open_member(int fd, Elf_Cmd c, Elf *elf)
|
||||
member = (char *) (arh + 1);
|
||||
|
||||
|
||||
if ((e = elf_memory((char *) member, sz)) == NULL)
|
||||
if ((e = elf_memory(member, sz)) == NULL)
|
||||
return (NULL);
|
||||
|
||||
e->e_fd = fd;
|
||||
e->e_cmd = c;
|
||||
e->e_hdr.e_rawhdr = (char *) arh;
|
||||
e->e_hdr.e_rawhdr = (unsigned char *) arh;
|
||||
|
||||
elf->e_u.e_ar.e_nchildren++;
|
||||
e->e_parent = elf;
|
||||
@ -274,9 +274,10 @@ _libelf_ar_open_member(int fd, Elf_Cmd c, Elf *elf)
|
||||
*/
|
||||
|
||||
/*
|
||||
* A helper macro to read in a 'long' value from the archive. We use
|
||||
* memcpy() since the source pointer may be misaligned with respect to
|
||||
* the natural alignment for a C 'long'.
|
||||
* A helper macro to read in a 'long' value from the archive.
|
||||
*
|
||||
* We use memcpy() since the source pointer may be misaligned with
|
||||
* respect to the natural alignment for a C 'long'.
|
||||
*/
|
||||
#define GET_LONG(P, V)do { \
|
||||
memcpy(&(V), (P), sizeof(long)); \
|
||||
@ -287,9 +288,10 @@ Elf_Arsym *
|
||||
_libelf_ar_process_bsd_symtab(Elf *e, size_t *count)
|
||||
{
|
||||
Elf_Arsym *symtab, *sym;
|
||||
unsigned int n, nentries;
|
||||
unsigned char *end, *p, *p0, *s, *s0;
|
||||
const unsigned int entrysize = 2 * sizeof(long);
|
||||
long arraysize, fileoffset, n, nentries, stroffset, strtabsize;
|
||||
const size_t entrysize = 2 * sizeof(long);
|
||||
long arraysize, fileoffset, stroffset, strtabsize;
|
||||
|
||||
assert(e != NULL);
|
||||
assert(count != NULL);
|
||||
@ -313,7 +315,8 @@ _libelf_ar_process_bsd_symtab(Elf *e, size_t *count)
|
||||
*/
|
||||
GET_LONG(p, arraysize);
|
||||
|
||||
if (p0 + arraysize >= end || (arraysize % entrysize != 0))
|
||||
if (arraysize < 0 || p0 + arraysize >= end ||
|
||||
((size_t) arraysize % entrysize != 0))
|
||||
goto symtaberror;
|
||||
|
||||
/*
|
||||
@ -323,10 +326,10 @@ _libelf_ar_process_bsd_symtab(Elf *e, size_t *count)
|
||||
GET_LONG(s, strtabsize);
|
||||
|
||||
s0 = s; /* Start of string table. */
|
||||
if (s0 + strtabsize > end)
|
||||
if (strtabsize < 0 || s0 + strtabsize > end)
|
||||
goto symtaberror;
|
||||
|
||||
nentries = arraysize / entrysize;
|
||||
nentries = (size_t) arraysize / entrysize;
|
||||
|
||||
/*
|
||||
* Allocate space for the returned Elf_Arsym array.
|
||||
@ -341,12 +344,16 @@ _libelf_ar_process_bsd_symtab(Elf *e, size_t *count)
|
||||
GET_LONG(p, stroffset);
|
||||
GET_LONG(p, fileoffset);
|
||||
|
||||
if (stroffset < 0 || fileoffset < 0 ||
|
||||
(size_t) fileoffset >= e->e_rawsize)
|
||||
goto symtaberror;
|
||||
|
||||
s = s0 + stroffset;
|
||||
|
||||
if (s >= end)
|
||||
goto symtaberror;
|
||||
|
||||
sym->as_off = fileoffset;
|
||||
sym->as_off = (off_t) fileoffset;
|
||||
sym->as_hash = elf_hash((char *) s);
|
||||
sym->as_name = (char *) s;
|
||||
}
|
||||
@ -393,7 +400,8 @@ symtaberror:
|
||||
Elf_Arsym *
|
||||
_libelf_ar_process_svr4_symtab(Elf *e, size_t *count)
|
||||
{
|
||||
size_t n, nentries, off;
|
||||
uint32_t off;
|
||||
size_t n, nentries;
|
||||
Elf_Arsym *symtab, *sym;
|
||||
unsigned char *p, *s, *end;
|
||||
|
||||
@ -424,15 +432,14 @@ _libelf_ar_process_svr4_symtab(Elf *e, size_t *count)
|
||||
s = p + (nentries * INTSZ); /* start of the string table. */
|
||||
|
||||
for (n = nentries, sym = symtab; n > 0; n--) {
|
||||
|
||||
if (s >= end)
|
||||
goto symtaberror;
|
||||
|
||||
off = 0;
|
||||
|
||||
GET_WORD(p, off);
|
||||
if (off >= e->e_rawsize)
|
||||
goto symtaberror;
|
||||
|
||||
sym->as_off = off;
|
||||
sym->as_off = (off_t) off;
|
||||
sym->as_hash = elf_hash((char *) s);
|
||||
sym->as_name = (char *) s;
|
||||
|
||||
|
@ -34,21 +34,23 @@
|
||||
#include "_libelf.h"
|
||||
#include "_libelf_ar.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_ar_util.c 2365 2011-12-29 04:36:44Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_ar_util.c 3013 2014-03-23 06:16:59Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Convert a string bounded by `start' and `start+sz' (exclusive) to a
|
||||
* number in the specified base.
|
||||
*/
|
||||
int
|
||||
_libelf_ar_get_number(const char *s, size_t sz, int base, size_t *ret)
|
||||
_libelf_ar_get_number(const char *src, size_t sz, unsigned int base,
|
||||
size_t *ret)
|
||||
{
|
||||
int c, v;
|
||||
size_t r;
|
||||
const char *e;
|
||||
unsigned int c, v;
|
||||
const unsigned char *e, *s;
|
||||
|
||||
assert(base <= 10);
|
||||
|
||||
s = (const unsigned char *) src;
|
||||
e = s + sz;
|
||||
|
||||
/* skip leading blanks */
|
||||
@ -79,17 +81,18 @@ _libelf_ar_get_number(const char *s, size_t sz, int base, size_t *ret)
|
||||
char *
|
||||
_libelf_ar_get_translated_name(const struct ar_hdr *arh, Elf *ar)
|
||||
{
|
||||
char c, *s;
|
||||
char *s;
|
||||
unsigned char c;
|
||||
size_t len, offset;
|
||||
const char *buf, *p, *q, *r;
|
||||
const unsigned char *buf, *p, *q, *r;
|
||||
const size_t bufsize = sizeof(arh->ar_name);
|
||||
|
||||
assert(arh != NULL);
|
||||
assert(ar->e_kind == ELF_K_AR);
|
||||
assert((const char *) arh >= ar->e_rawfile &&
|
||||
(const char *) arh < ar->e_rawfile + ar->e_rawsize);
|
||||
assert((const unsigned char *) arh >= ar->e_rawfile &&
|
||||
(const unsigned char *) arh < ar->e_rawfile + ar->e_rawsize);
|
||||
|
||||
buf = arh->ar_name;
|
||||
buf = (const unsigned char *) arh->ar_name;
|
||||
|
||||
/*
|
||||
* Check for extended naming.
|
||||
@ -104,8 +107,8 @@ _libelf_ar_get_translated_name(const struct ar_hdr *arh, Elf *ar)
|
||||
* the archive string table where the actual name
|
||||
* resides.
|
||||
*/
|
||||
if (_libelf_ar_get_number(buf + 1, bufsize - 1, 10,
|
||||
&offset) == 0) {
|
||||
if (_libelf_ar_get_number((const char *) (buf + 1),
|
||||
bufsize - 1, 10, &offset) == 0) {
|
||||
LIBELF_SET_ERROR(ARCHIVE, 0);
|
||||
return (NULL);
|
||||
}
|
||||
@ -120,21 +123,21 @@ _libelf_ar_get_translated_name(const struct ar_hdr *arh, Elf *ar)
|
||||
|
||||
for (; p < r && *p != '/'; p++)
|
||||
;
|
||||
len = p - q + 1; /* space for the trailing NUL */
|
||||
len = (size_t) (p - q + 1); /* space for the trailing NUL */
|
||||
|
||||
if ((s = malloc(len)) == NULL) {
|
||||
LIBELF_SET_ERROR(RESOURCE, 0);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
(void) strncpy(s, q, len - 1);
|
||||
(void) strncpy(s, (const char *) q, len - 1);
|
||||
s[len - 1] = '\0';
|
||||
|
||||
return (s);
|
||||
} else if (IS_EXTENDED_BSD_NAME(buf)) {
|
||||
r = buf + LIBELF_AR_BSD_EXTENDED_NAME_PREFIX_SIZE;
|
||||
|
||||
if (_libelf_ar_get_number(r, bufsize -
|
||||
if (_libelf_ar_get_number((const char *) r, bufsize -
|
||||
LIBELF_AR_BSD_EXTENDED_NAME_PREFIX_SIZE, 10,
|
||||
&len) == 0) {
|
||||
LIBELF_SET_ERROR(ARCHIVE, 0);
|
||||
@ -153,9 +156,9 @@ _libelf_ar_get_translated_name(const struct ar_hdr *arh, Elf *ar)
|
||||
/*
|
||||
* The file name follows the archive header.
|
||||
*/
|
||||
q = (const char *) (arh + 1);
|
||||
q = (const unsigned char *) (arh + 1);
|
||||
|
||||
(void) strncpy(s, q, len);
|
||||
(void) strncpy(s, (const char *) q, len);
|
||||
s[len] = '\0';
|
||||
|
||||
return (s);
|
||||
@ -183,10 +186,10 @@ _libelf_ar_get_translated_name(const struct ar_hdr *arh, Elf *ar)
|
||||
q--;
|
||||
}
|
||||
|
||||
len = q - buf + 2; /* Add space for a trailing NUL. */
|
||||
len = (size_t) (q - buf + 2); /* Space for a trailing NUL. */
|
||||
} else {
|
||||
/* The buffer only had blanks. */
|
||||
buf = "";
|
||||
buf = (const unsigned char *) "";
|
||||
len = 1;
|
||||
}
|
||||
|
||||
@ -195,7 +198,7 @@ _libelf_ar_get_translated_name(const struct ar_hdr *arh, Elf *ar)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
(void) strncpy(s, buf, len - 1);
|
||||
(void) strncpy(s, (const char *) buf, len - 1);
|
||||
s[len - 1] = '\0';
|
||||
|
||||
return (s);
|
||||
@ -229,8 +232,8 @@ _libelf_ar_open(Elf *e, int reporterror)
|
||||
{
|
||||
size_t sz;
|
||||
int scanahead;
|
||||
char *s, *end;
|
||||
struct ar_hdr arh;
|
||||
unsigned char *s, *end;
|
||||
|
||||
_libelf_init_elf(e, ELF_K_AR);
|
||||
|
||||
@ -264,7 +267,7 @@ _libelf_ar_open(Elf *e, int reporterror)
|
||||
(void) memcpy(&(ARH), (S), sizeof((ARH))); \
|
||||
if ((ARH).ar_fmag[0] != '`' || (ARH).ar_fmag[1] != '\n') \
|
||||
goto error; \
|
||||
if (_libelf_ar_get_number((ARH).ar_size, \
|
||||
if (_libelf_ar_get_number((char *) (ARH).ar_size, \
|
||||
sizeof((ARH).ar_size), 10, &(SZ)) == 0) \
|
||||
goto error; \
|
||||
} while (0)
|
||||
|
@ -30,7 +30,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_checksum.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_checksum.c 3003 2014-03-22 07:43:10Z jkoshy $");
|
||||
|
||||
static unsigned long
|
||||
_libelf_sum(unsigned long c, const unsigned char *s, size_t size)
|
||||
@ -44,7 +44,7 @@ _libelf_sum(unsigned long c, const unsigned char *s, size_t size)
|
||||
return (c);
|
||||
}
|
||||
|
||||
unsigned long
|
||||
long
|
||||
_libelf_checksum(Elf *e, int elfclass)
|
||||
{
|
||||
size_t shn;
|
||||
@ -90,11 +90,11 @@ _libelf_checksum(Elf *e, int elfclass)
|
||||
d = NULL;
|
||||
while ((d = elf_rawdata(scn, d)) != NULL)
|
||||
checksum = _libelf_sum(checksum,
|
||||
(unsigned char *) d->d_buf, d->d_size);
|
||||
(unsigned char *) d->d_buf, (size_t) d->d_size);
|
||||
}
|
||||
|
||||
/*
|
||||
* Return a 16-bit checksum compatible with Solaris.
|
||||
*/
|
||||
return (((checksum >> 16) & 0xFFFFUL) + (checksum & 0xFFFFUL));
|
||||
return (long) (((checksum >> 16) & 0xFFFFUL) + (checksum & 0xFFFFUL));
|
||||
}
|
||||
|
@ -32,7 +32,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_convert.m4 2361 2011-12-28 12:03:05Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_convert.m4 3009 2014-03-23 01:49:59Z jkoshy $");
|
||||
|
||||
/* WARNING: GENERATED FROM __file__. */
|
||||
|
||||
@ -143,8 +143,8 @@ define(`SIZEDEP_OFF', 1)
|
||||
# Generates a pair of conversion functions.
|
||||
define(`MAKEPRIMFUNCS',`
|
||||
static int
|
||||
_libelf_cvt_$1$4_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_$1$4_tof(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
Elf$3_$2 t, *s = (Elf$3_$2 *) (uintptr_t) src;
|
||||
size_t c;
|
||||
@ -166,8 +166,8 @@ _libelf_cvt_$1$4_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
}
|
||||
|
||||
static int
|
||||
_libelf_cvt_$1$4_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_$1$4_tom(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
Elf$3_$2 t, *d = (Elf$3_$2 *) (uintptr_t) dst;
|
||||
size_t c;
|
||||
@ -267,8 +267,8 @@ define(`READ_STRUCT',
|
||||
# `$3': ELF class specifier, one of [`', `32', `64']
|
||||
define(`MAKECOMPFUNCS', `ifdef(`NOFUNC_'$1$3,`',`
|
||||
static int
|
||||
_libelf_cvt_$1$3_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_$1$3_tof(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
Elf$3_$2 t, *s;
|
||||
size_t c;
|
||||
@ -288,16 +288,16 @@ _libelf_cvt_$1$3_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
}
|
||||
|
||||
static int
|
||||
_libelf_cvt_$1$3_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_$1$3_tom(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
Elf$3_$2 t, *d;
|
||||
char *s,*s0;
|
||||
Elf$3_$2 t, *d;
|
||||
unsigned char *s,*s0;
|
||||
size_t fsz;
|
||||
|
||||
fsz = elf$3_fsize(ELF_T_$1, (size_t) 1, EV_CURRENT);
|
||||
d = ((Elf$3_$2 *) (uintptr_t) dst) + (count - 1);
|
||||
s0 = (char *) src + (count - 1) * fsz;
|
||||
s0 = src + (count - 1) * fsz;
|
||||
|
||||
if (dsz < count * sizeof(Elf$3_$2))
|
||||
return (0);
|
||||
@ -398,8 +398,8 @@ define(`MAKE_VERSION_CONVERTERS',
|
||||
# conversion function.
|
||||
define(`MAKE_VERSION_CONVERTER',`
|
||||
static int
|
||||
_libelf_cvt_$1$5_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_$1$5_tof(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
Elf$5_$2 t;
|
||||
Elf$5_$3 a;
|
||||
@ -407,12 +407,12 @@ _libelf_cvt_$1$5_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
const size_t auxfsz = FSZ(Elf$5_$3_DEF);
|
||||
const size_t vermsz = sizeof(Elf$5_$2);
|
||||
const size_t auxmsz = sizeof(Elf$5_$3);
|
||||
char * const dstend = dst + dsz;
|
||||
char * const srcend = src + count;
|
||||
char *dtmp, *dstaux, *srcaux;
|
||||
unsigned char * const dstend = dst + dsz;
|
||||
unsigned char * const srcend = src + count;
|
||||
unsigned char *dtmp, *dstaux, *srcaux;
|
||||
Elf$5_Word aux, anext, cnt, vnext;
|
||||
|
||||
for (dtmp = dst, vnext = ~0;
|
||||
for (dtmp = dst, vnext = ~0U;
|
||||
vnext != 0 && dtmp + verfsz <= dstend && src + vermsz <= srcend;
|
||||
dtmp += vnext, src += vnext) {
|
||||
|
||||
@ -434,7 +434,7 @@ _libelf_cvt_$1$5_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
return (0);
|
||||
|
||||
/* Process AUX entries. */
|
||||
for (anext = ~0, dstaux = dtmp + aux, srcaux = src + aux;
|
||||
for (anext = ~0U, dstaux = dtmp + aux, srcaux = src + aux;
|
||||
cnt != 0 && anext != 0 && dstaux + auxfsz <= dstend &&
|
||||
srcaux + auxmsz <= srcend;
|
||||
dstaux += anext, srcaux += anext, cnt--) {
|
||||
@ -462,8 +462,8 @@ _libelf_cvt_$1$5_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
}
|
||||
|
||||
static int
|
||||
_libelf_cvt_$1$5_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_$1$5_tom(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
Elf$5_$2 t, *dp;
|
||||
Elf$5_$3 a, *ap;
|
||||
@ -471,12 +471,12 @@ _libelf_cvt_$1$5_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
const size_t auxfsz = FSZ(Elf$5_$3_DEF);
|
||||
const size_t vermsz = sizeof(Elf$5_$2);
|
||||
const size_t auxmsz = sizeof(Elf$5_$3);
|
||||
char * const dstend = dst + dsz;
|
||||
char * const srcend = src + count;
|
||||
char *dstaux, *s, *srcaux, *stmp;
|
||||
unsigned char * const dstend = dst + dsz;
|
||||
unsigned char * const srcend = src + count;
|
||||
unsigned char *dstaux, *s, *srcaux, *stmp;
|
||||
Elf$5_Word aux, anext, cnt, vnext;
|
||||
|
||||
for (stmp = src, vnext = ~0;
|
||||
for (stmp = src, vnext = ~0U;
|
||||
vnext != 0 && stmp + verfsz <= srcend && dst + vermsz <= dstend;
|
||||
stmp += vnext, dst += vnext) {
|
||||
|
||||
@ -498,7 +498,7 @@ _libelf_cvt_$1$5_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
return (0);
|
||||
|
||||
/* Process AUX entries. */
|
||||
for (anext = ~0, dstaux = dst + aux, srcaux = stmp + aux;
|
||||
for (anext = ~0U, dstaux = dst + aux, srcaux = stmp + aux;
|
||||
cnt != 0 && anext != 0 && dstaux + auxmsz <= dstend &&
|
||||
srcaux + auxfsz <= srcend;
|
||||
dstaux += anext, srcaux += anext, cnt--) {
|
||||
@ -536,22 +536,23 @@ divert(0)
|
||||
#define SWAP_IDENT(X) do { (void) (X); } while (0)
|
||||
#define SWAP_HALF(X) do { \
|
||||
uint16_t _x = (uint16_t) (X); \
|
||||
uint16_t _t = _x & 0xFF; \
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
(X) = _t; \
|
||||
uint32_t _t = _x & 0xFFU; \
|
||||
_t <<= 8U; _x >>= 8U; _t |= _x & 0xFFU; \
|
||||
(X) = (uint16_t) _t; \
|
||||
} while (0)
|
||||
#define SWAP_WORD(X) do { \
|
||||
#define _SWAP_WORD(X, T) do { \
|
||||
uint32_t _x = (uint32_t) (X); \
|
||||
uint32_t _t = _x & 0xFF; \
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
(X) = _t; \
|
||||
(X) = (T) _t; \
|
||||
} while (0)
|
||||
#define SWAP_ADDR32(X) SWAP_WORD(X)
|
||||
#define SWAP_OFF32(X) SWAP_WORD(X)
|
||||
#define SWAP_SWORD(X) SWAP_WORD(X)
|
||||
#define SWAP_WORD64(X) do { \
|
||||
#define SWAP_ADDR32(X) _SWAP_WORD(X, Elf32_Addr)
|
||||
#define SWAP_OFF32(X) _SWAP_WORD(X, Elf32_Off)
|
||||
#define SWAP_SWORD(X) _SWAP_WORD(X, Elf32_Sword)
|
||||
#define SWAP_WORD(X) _SWAP_WORD(X, Elf32_Word)
|
||||
#define _SWAP_WORD64(X, T) do { \
|
||||
uint64_t _x = (uint64_t) (X); \
|
||||
uint64_t _t = _x & 0xFF; \
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
@ -561,13 +562,13 @@ divert(0)
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
_t <<= 8; _x >>= 8; _t |= _x & 0xFF; \
|
||||
(X) = _t; \
|
||||
(X) = (T) _t; \
|
||||
} while (0)
|
||||
#define SWAP_ADDR64(X) SWAP_WORD64(X)
|
||||
#define SWAP_LWORD(X) SWAP_WORD64(X)
|
||||
#define SWAP_OFF64(X) SWAP_WORD64(X)
|
||||
#define SWAP_SXWORD(X) SWAP_WORD64(X)
|
||||
#define SWAP_XWORD(X) SWAP_WORD64(X)
|
||||
#define SWAP_ADDR64(X) _SWAP_WORD64(X, Elf64_Addr)
|
||||
#define SWAP_LWORD(X) _SWAP_WORD64(X, Elf64_Lword)
|
||||
#define SWAP_OFF64(X) _SWAP_WORD64(X, Elf64_Off)
|
||||
#define SWAP_SXWORD(X) _SWAP_WORD64(X, Elf64_Sxword)
|
||||
#define SWAP_XWORD(X) _SWAP_WORD64(X, Elf64_Xword)
|
||||
|
||||
/*
|
||||
* C macros to write out various integral values.
|
||||
@ -578,22 +579,22 @@ divert(0)
|
||||
* - The destination pointer is incremented after the write.
|
||||
*/
|
||||
#define WRITE_BYTE(P,X) do { \
|
||||
char *const _p = (char *) (P); \
|
||||
_p[0] = (char) (X); \
|
||||
unsigned char *const _p = (unsigned char *) (P); \
|
||||
_p[0] = (unsigned char) (X); \
|
||||
(P) = _p + 1; \
|
||||
} while (0)
|
||||
#define WRITE_HALF(P,X) do { \
|
||||
uint16_t _t = (X); \
|
||||
char *const _p = (char *) (P); \
|
||||
const char *const _q = (char *) &_t; \
|
||||
unsigned char *const _p = (unsigned char *) (P); \
|
||||
const unsigned char *const _q = (unsigned char *) &_t; \
|
||||
_p[0] = _q[0]; \
|
||||
_p[1] = _q[1]; \
|
||||
(P) = _p + 2; \
|
||||
} while (0)
|
||||
#define WRITE_WORD(P,X) do { \
|
||||
uint32_t _t = (X); \
|
||||
char *const _p = (char *) (P); \
|
||||
const char *const _q = (char *) &_t; \
|
||||
#define WRITE_WORD(P,X) do { \
|
||||
uint32_t _t = (uint32_t) (X); \
|
||||
unsigned char *const _p = (unsigned char *) (P); \
|
||||
const unsigned char *const _q = (unsigned char *) &_t; \
|
||||
_p[0] = _q[0]; \
|
||||
_p[1] = _q[1]; \
|
||||
_p[2] = _q[2]; \
|
||||
@ -604,9 +605,9 @@ divert(0)
|
||||
#define WRITE_OFF32(P,X) WRITE_WORD(P,X)
|
||||
#define WRITE_SWORD(P,X) WRITE_WORD(P,X)
|
||||
#define WRITE_WORD64(P,X) do { \
|
||||
uint64_t _t = (X); \
|
||||
char *const _p = (char *) (P); \
|
||||
const char *const _q = (char *) &_t; \
|
||||
uint64_t _t = (uint64_t) (X); \
|
||||
unsigned char *const _p = (unsigned char *) (P); \
|
||||
const unsigned char *const _q = (unsigned char *) &_t; \
|
||||
_p[0] = _q[0]; \
|
||||
_p[1] = _q[1]; \
|
||||
_p[2] = _q[2]; \
|
||||
@ -637,41 +638,42 @@ divert(0)
|
||||
*/
|
||||
|
||||
#define READ_BYTE(P,X) do { \
|
||||
const char *const _p = \
|
||||
(const char *) (P); \
|
||||
const unsigned char *const _p = \
|
||||
(const unsigned char *) (P); \
|
||||
(X) = _p[0]; \
|
||||
(P) = (P) + 1; \
|
||||
} while (0)
|
||||
#define READ_HALF(P,X) do { \
|
||||
uint16_t _t; \
|
||||
char *const _q = (char *) &_t; \
|
||||
const char *const _p = \
|
||||
(const char *) (P); \
|
||||
unsigned char *const _q = (unsigned char *) &_t; \
|
||||
const unsigned char *const _p = \
|
||||
(const unsigned char *) (P); \
|
||||
_q[0] = _p[0]; \
|
||||
_q[1] = _p[1]; \
|
||||
(P) = (P) + 2; \
|
||||
(X) = _t; \
|
||||
} while (0)
|
||||
#define READ_WORD(P,X) do { \
|
||||
#define _READ_WORD(P,X,T) do { \
|
||||
uint32_t _t; \
|
||||
char *const _q = (char *) &_t; \
|
||||
const char *const _p = \
|
||||
(const char *) (P); \
|
||||
unsigned char *const _q = (unsigned char *) &_t; \
|
||||
const unsigned char *const _p = \
|
||||
(const unsigned char *) (P); \
|
||||
_q[0] = _p[0]; \
|
||||
_q[1] = _p[1]; \
|
||||
_q[2] = _p[2]; \
|
||||
_q[3] = _p[3]; \
|
||||
(P) = (P) + 4; \
|
||||
(X) = _t; \
|
||||
(X) = (T) _t; \
|
||||
} while (0)
|
||||
#define READ_ADDR32(P,X) READ_WORD(P,X)
|
||||
#define READ_OFF32(P,X) READ_WORD(P,X)
|
||||
#define READ_SWORD(P,X) READ_WORD(P,X)
|
||||
#define READ_WORD64(P,X) do { \
|
||||
#define READ_ADDR32(P,X) _READ_WORD(P, X, Elf32_Addr)
|
||||
#define READ_OFF32(P,X) _READ_WORD(P, X, Elf32_Off)
|
||||
#define READ_SWORD(P,X) _READ_WORD(P, X, Elf32_Sword)
|
||||
#define READ_WORD(P,X) _READ_WORD(P, X, Elf32_Word)
|
||||
#define _READ_WORD64(P,X,T) do { \
|
||||
uint64_t _t; \
|
||||
char *const _q = (char *) &_t; \
|
||||
const char *const _p = \
|
||||
(const char *) (P); \
|
||||
unsigned char *const _q = (unsigned char *) &_t; \
|
||||
const unsigned char *const _p = \
|
||||
(const unsigned char *) (P); \
|
||||
_q[0] = _p[0]; \
|
||||
_q[1] = _p[1]; \
|
||||
_q[2] = _p[2]; \
|
||||
@ -681,13 +683,13 @@ divert(0)
|
||||
_q[6] = _p[6]; \
|
||||
_q[7] = _p[7]; \
|
||||
(P) = (P) + 8; \
|
||||
(X) = _t; \
|
||||
(X) = (T) _t; \
|
||||
} while (0)
|
||||
#define READ_ADDR64(P,X) READ_WORD64(P,X)
|
||||
#define READ_LWORD(P,X) READ_WORD64(P,X)
|
||||
#define READ_OFF64(P,X) READ_WORD64(P,X)
|
||||
#define READ_SXWORD(P,X) READ_WORD64(P,X)
|
||||
#define READ_XWORD(P,X) READ_WORD64(P,X)
|
||||
#define READ_ADDR64(P,X) _READ_WORD64(P, X, Elf64_Addr)
|
||||
#define READ_LWORD(P,X) _READ_WORD64(P, X, Elf64_Lword)
|
||||
#define READ_OFF64(P,X) _READ_WORD64(P, X, Elf64_Off)
|
||||
#define READ_SXWORD(P,X) _READ_WORD64(P, X, Elf64_Sxword)
|
||||
#define READ_XWORD(P,X) _READ_WORD64(P, X, Elf64_Xword)
|
||||
#define READ_IDENT(P,X) do { \
|
||||
(void) memcpy((X), (P), sizeof((X))); \
|
||||
(P) = (P) + EI_NIDENT; \
|
||||
@ -707,8 +709,8 @@ MAKE_VERSION_CONVERTERS(VNEED,Verneed,Vernaux,vn)
|
||||
*/
|
||||
|
||||
static int
|
||||
_libelf_cvt_BYTE_tox(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_BYTE_tox(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
(void) byteswap;
|
||||
if (dsz < count)
|
||||
@ -732,24 +734,24 @@ _libelf_cvt_BYTE_tox(char *dst, size_t dsz, char *src, size_t count,
|
||||
*/
|
||||
|
||||
static int
|
||||
_libelf_cvt_GNUHASH32_tom(char *dst, size_t dsz, char *src, size_t srcsz,
|
||||
int byteswap)
|
||||
_libelf_cvt_GNUHASH32_tom(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t srcsz, int byteswap)
|
||||
{
|
||||
return (_libelf_cvt_WORD_tom(dst, dsz, src, srcsz / sizeof(uint32_t),
|
||||
byteswap));
|
||||
}
|
||||
|
||||
static int
|
||||
_libelf_cvt_GNUHASH32_tof(char *dst, size_t dsz, char *src, size_t srcsz,
|
||||
int byteswap)
|
||||
_libelf_cvt_GNUHASH32_tof(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t srcsz, int byteswap)
|
||||
{
|
||||
return (_libelf_cvt_WORD_tof(dst, dsz, src, srcsz / sizeof(uint32_t),
|
||||
byteswap));
|
||||
}
|
||||
|
||||
static int
|
||||
_libelf_cvt_GNUHASH64_tom(char *dst, size_t dsz, char *src, size_t srcsz,
|
||||
int byteswap)
|
||||
_libelf_cvt_GNUHASH64_tom(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t srcsz, int byteswap)
|
||||
{
|
||||
size_t sz;
|
||||
uint64_t t64, *bloom64;
|
||||
@ -834,8 +836,8 @@ _libelf_cvt_GNUHASH64_tom(char *dst, size_t dsz, char *src, size_t srcsz,
|
||||
}
|
||||
|
||||
static int
|
||||
_libelf_cvt_GNUHASH64_tof(char *dst, size_t dsz, char *src, size_t srcsz,
|
||||
int byteswap)
|
||||
_libelf_cvt_GNUHASH64_tof(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t srcsz, int byteswap)
|
||||
{
|
||||
uint32_t *s32;
|
||||
size_t sz, hdrsz;
|
||||
@ -921,8 +923,8 @@ _libelf_cvt_GNUHASH64_tof(char *dst, size_t dsz, char *src, size_t srcsz,
|
||||
* The destination buffer needs to be at least `count' bytes in size.
|
||||
*/
|
||||
static int
|
||||
_libelf_cvt_NOTE_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_NOTE_tom(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
uint32_t namesz, descsz, type;
|
||||
Elf_Note *en;
|
||||
@ -962,8 +964,8 @@ _libelf_cvt_NOTE_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
dst += sizeof(Elf_Note);
|
||||
count -= hdrsz;
|
||||
|
||||
ROUNDUP2(namesz, 4);
|
||||
ROUNDUP2(descsz, 4);
|
||||
ROUNDUP2(namesz, 4U);
|
||||
ROUNDUP2(descsz, 4U);
|
||||
|
||||
sz = namesz + descsz;
|
||||
|
||||
@ -983,8 +985,8 @@ _libelf_cvt_NOTE_tom(char *dst, size_t dsz, char *src, size_t count,
|
||||
}
|
||||
|
||||
static int
|
||||
_libelf_cvt_NOTE_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
int byteswap)
|
||||
_libelf_cvt_NOTE_tof(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t count, int byteswap)
|
||||
{
|
||||
uint32_t namesz, descsz, type;
|
||||
Elf_Note *en;
|
||||
@ -1006,9 +1008,9 @@ _libelf_cvt_NOTE_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
type = en->n_type;
|
||||
|
||||
sz = namesz;
|
||||
ROUNDUP2(sz, 4);
|
||||
ROUNDUP2(sz, 4U);
|
||||
sz += descsz;
|
||||
ROUNDUP2(sz, 4);
|
||||
ROUNDUP2(sz, 4U);
|
||||
|
||||
SWAP_WORD(namesz);
|
||||
SWAP_WORD(descsz);
|
||||
@ -1034,14 +1036,14 @@ _libelf_cvt_NOTE_tof(char *dst, size_t dsz, char *src, size_t count,
|
||||
}
|
||||
|
||||
struct converters {
|
||||
int (*tof32)(char *dst, size_t dsz, char *src, size_t cnt,
|
||||
int byteswap);
|
||||
int (*tom32)(char *dst, size_t dsz, char *src, size_t cnt,
|
||||
int byteswap);
|
||||
int (*tof64)(char *dst, size_t dsz, char *src, size_t cnt,
|
||||
int byteswap);
|
||||
int (*tom64)(char *dst, size_t dsz, char *src, size_t cnt,
|
||||
int byteswap);
|
||||
int (*tof32)(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t cnt, int byteswap);
|
||||
int (*tom32)(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t cnt, int byteswap);
|
||||
int (*tof64)(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t cnt, int byteswap);
|
||||
int (*tom64)(unsigned char *dst, size_t dsz, unsigned char *src,
|
||||
size_t cnt, int byteswap);
|
||||
};
|
||||
|
||||
|
||||
@ -1070,7 +1072,8 @@ CONVERTER_NAMES(ELF_TYPE_LIST)
|
||||
};
|
||||
|
||||
int (*_libelf_get_translator(Elf_Type t, int direction, int elfclass))
|
||||
(char *_dst, size_t dsz, char *_src, size_t _cnt, int _byteswap)
|
||||
(unsigned char *_dst, size_t dsz, unsigned char *_src, size_t _cnt,
|
||||
int _byteswap)
|
||||
{
|
||||
assert(elfclass == ELFCLASS32 || elfclass == ELFCLASS64);
|
||||
assert(direction == ELF_TOFILE || direction == ELF_TOMEMORY);
|
||||
|
@ -30,11 +30,14 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_data.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_data.c 3080 2014-07-28 08:46:17Z jkoshy $");
|
||||
|
||||
int
|
||||
_libelf_xlate_shtype(uint32_t sht)
|
||||
{
|
||||
/*
|
||||
* Look for known section types.
|
||||
*/
|
||||
switch (sht) {
|
||||
case SHT_DYNAMIC:
|
||||
return (ELF_T_DYN);
|
||||
@ -82,18 +85,19 @@ _libelf_xlate_shtype(uint32_t sht)
|
||||
return (ELF_T_VNEED);
|
||||
case SHT_SUNW_versym: /* == SHT_GNU_versym */
|
||||
return (ELF_T_HALF);
|
||||
|
||||
case SHT_ARM_PREEMPTMAP:
|
||||
case SHT_ARM_ATTRIBUTES:
|
||||
case SHT_ARM_DEBUGOVERLAY:
|
||||
case SHT_ARM_OVERLAYSECTION:
|
||||
case SHT_MIPS_DWARF:
|
||||
case SHT_MIPS_REGINFO:
|
||||
case SHT_MIPS_OPTIONS:
|
||||
case SHT_AMD64_UNWIND: /* == SHT_IA_64_UNWIND == SHT_ARM_EXIDX */
|
||||
return (ELF_T_BYTE);
|
||||
|
||||
default:
|
||||
/*
|
||||
* Values in the range [SHT_LOOS..SHT_HIUSER] (i.e.,
|
||||
* OS, processor and user-defined section types) are
|
||||
* legal, but since we do not know anything more about
|
||||
* their semantics, we return a type of ELF_T_BYTE.
|
||||
*/
|
||||
if (sht >= SHT_LOOS && sht <= SHT_HIUSER)
|
||||
return (ELF_T_BYTE);
|
||||
|
||||
/*
|
||||
* Other values are unsupported.
|
||||
*/
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
|
@ -33,7 +33,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_ehdr.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_ehdr.c 3009 2014-03-23 01:49:59Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Retrieve counts for sections, phdrs and the section string table index
|
||||
@ -45,7 +45,8 @@ _libelf_load_extended(Elf *e, int ec, uint64_t shoff, uint16_t phnum,
|
||||
{
|
||||
Elf_Scn *scn;
|
||||
size_t fsz;
|
||||
int (*xlator)(char *_d, size_t _dsz, char *_s, size_t _c, int _swap);
|
||||
int (*xlator)(unsigned char *_d, size_t _dsz, unsigned char *_s,
|
||||
size_t _c, int _swap);
|
||||
uint32_t shtype;
|
||||
|
||||
assert(STAILQ_EMPTY(&e->e_u.e_elf.e_scn));
|
||||
@ -62,8 +63,8 @@ _libelf_load_extended(Elf *e, int ec, uint64_t shoff, uint16_t phnum,
|
||||
return (0);
|
||||
|
||||
xlator = _libelf_get_translator(ELF_T_SHDR, ELF_TOMEMORY, ec);
|
||||
(*xlator)((char *) &scn->s_shdr, sizeof(scn->s_shdr),
|
||||
e->e_rawfile + shoff, (size_t) 1,
|
||||
(*xlator)((unsigned char *) &scn->s_shdr, sizeof(scn->s_shdr),
|
||||
(unsigned char *) e->e_rawfile + shoff, (size_t) 1,
|
||||
e->e_byteorder != LIBELF_PRIVATE(byteorder));
|
||||
|
||||
#define GET_SHDR_MEMBER(M) ((ec == ELFCLASS32) ? scn->s_shdr.s_shdr32.M : \
|
||||
@ -74,7 +75,7 @@ _libelf_load_extended(Elf *e, int ec, uint64_t shoff, uint16_t phnum,
|
||||
return (0);
|
||||
}
|
||||
|
||||
e->e_u.e_elf.e_nscn = GET_SHDR_MEMBER(sh_size);
|
||||
e->e_u.e_elf.e_nscn = (size_t) GET_SHDR_MEMBER(sh_size);
|
||||
e->e_u.e_elf.e_nphdr = (phnum != PN_XNUM) ? phnum :
|
||||
GET_SHDR_MEMBER(sh_info);
|
||||
e->e_u.e_elf.e_strndx = (strndx != SHN_XINDEX) ? strndx :
|
||||
@ -92,7 +93,7 @@ _libelf_load_extended(Elf *e, int ec, uint64_t shoff, uint16_t phnum,
|
||||
eh->e_ident[EI_MAG3] = ELFMAG3; \
|
||||
eh->e_ident[EI_CLASS] = ELFCLASS##SZ; \
|
||||
eh->e_ident[EI_DATA] = ELFDATANONE; \
|
||||
eh->e_ident[EI_VERSION] = LIBELF_PRIVATE(version); \
|
||||
eh->e_ident[EI_VERSION] = LIBELF_PRIVATE(version) & 0xFFU; \
|
||||
eh->e_machine = EM_NONE; \
|
||||
eh->e_type = ELF_K_NONE; \
|
||||
eh->e_version = LIBELF_PRIVATE(version); \
|
||||
@ -105,7 +106,8 @@ _libelf_ehdr(Elf *e, int ec, int allocate)
|
||||
size_t fsz, msz;
|
||||
uint16_t phnum, shnum, strndx;
|
||||
uint64_t shoff;
|
||||
int (*xlator)(char *_d, size_t _dsz, char *_s, size_t _c, int _swap);
|
||||
int (*xlator)(unsigned char *_d, size_t _dsz, unsigned char *_s,
|
||||
size_t _c, int _swap);
|
||||
|
||||
assert(ec == ELFCLASS32 || ec == ELFCLASS64);
|
||||
|
||||
@ -167,7 +169,7 @@ _libelf_ehdr(Elf *e, int ec, int allocate)
|
||||
return (ehdr);
|
||||
|
||||
xlator = _libelf_get_translator(ELF_T_EHDR, ELF_TOMEMORY, ec);
|
||||
(*xlator)(ehdr, msz, e->e_rawfile, (size_t) 1,
|
||||
(*xlator)((unsigned char*) ehdr, msz, e->e_rawfile, (size_t) 1,
|
||||
e->e_byteorder != LIBELF_PRIVATE(byteorder));
|
||||
|
||||
/*
|
||||
|
@ -31,7 +31,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_extended.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_extended.c 3005 2014-03-22 07:43:25Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Retrieve section #0, allocating a new section if needed.
|
||||
@ -69,9 +69,9 @@ _libelf_setshnum(Elf *e, void *eh, int ec, size_t shnum)
|
||||
}
|
||||
|
||||
if (ec == ELFCLASS32)
|
||||
((Elf32_Ehdr *) eh)->e_shnum = shnum;
|
||||
((Elf32_Ehdr *) eh)->e_shnum = shnum & 0xFFFFU;
|
||||
else
|
||||
((Elf64_Ehdr *) eh)->e_shnum = shnum;
|
||||
((Elf64_Ehdr *) eh)->e_shnum = shnum & 0xFFFFU;
|
||||
|
||||
|
||||
return (1);
|
||||
@ -99,9 +99,9 @@ _libelf_setshstrndx(Elf *e, void *eh, int ec, size_t shstrndx)
|
||||
}
|
||||
|
||||
if (ec == ELFCLASS32)
|
||||
((Elf32_Ehdr *) eh)->e_shstrndx = shstrndx;
|
||||
((Elf32_Ehdr *) eh)->e_shstrndx = shstrndx & 0xFFFFU;
|
||||
else
|
||||
((Elf64_Ehdr *) eh)->e_shstrndx = shstrndx;
|
||||
((Elf64_Ehdr *) eh)->e_shstrndx = shstrndx & 0xFFFFU;
|
||||
|
||||
return (1);
|
||||
}
|
||||
@ -128,9 +128,9 @@ _libelf_setphnum(Elf *e, void *eh, int ec, size_t phnum)
|
||||
}
|
||||
|
||||
if (ec == ELFCLASS32)
|
||||
((Elf32_Ehdr *) eh)->e_phnum = phnum;
|
||||
((Elf32_Ehdr *) eh)->e_phnum = phnum & 0xFFFFU;
|
||||
else
|
||||
((Elf64_Ehdr *) eh)->e_phnum = phnum;
|
||||
((Elf64_Ehdr *) eh)->e_phnum = phnum & 0xFFFFU;
|
||||
|
||||
return (1);
|
||||
}
|
||||
|
@ -31,7 +31,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_memory.c 2368 2011-12-29 06:34:28Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_memory.c 3013 2014-03-23 06:16:59Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Create an ELF descriptor for a memory image, optionally reporting
|
||||
@ -39,7 +39,7 @@ ELFTC_VCSID("$Id: libelf_memory.c 2368 2011-12-29 06:34:28Z jkoshy $");
|
||||
*/
|
||||
|
||||
Elf *
|
||||
_libelf_memory(char *image, size_t sz, int reporterror)
|
||||
_libelf_memory(unsigned char *image, size_t sz, int reporterror)
|
||||
{
|
||||
Elf *e;
|
||||
int e_class;
|
||||
@ -89,7 +89,7 @@ _libelf_memory(char *image, size_t sz, int reporterror)
|
||||
e->e_version = e_version;
|
||||
}
|
||||
} else if (sz >= SARMAG &&
|
||||
strncmp(image, ARMAG, (size_t) SARMAG) == 0)
|
||||
strncmp((const char *) image, ARMAG, (size_t) SARMAG) == 0)
|
||||
return (_libelf_ar_open(e, reporterror));
|
||||
|
||||
return (e);
|
||||
|
@ -39,7 +39,7 @@
|
||||
#include <sys/mman.h>
|
||||
#endif
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_open.c 2932 2013-03-30 01:26:04Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_open.c 3007 2014-03-22 08:10:14Z jkoshy $");
|
||||
|
||||
#define _LIBELF_INITSIZE (64*1024)
|
||||
|
||||
@ -73,11 +73,11 @@ _libelf_read_special_file(int fd, size_t *fsz)
|
||||
}
|
||||
|
||||
do {
|
||||
readsz = bufsz - datasz;
|
||||
assert(bufsz - datasz > 0);
|
||||
t = buf + datasz;
|
||||
if ((readsz = read(fd, t, readsz)) <= 0)
|
||||
if ((readsz = read(fd, t, bufsz - datasz)) <= 0)
|
||||
break;
|
||||
datasz += readsz;
|
||||
datasz += (size_t) readsz;
|
||||
} while (datasz < bufsz);
|
||||
|
||||
} while (readsz > 0);
|
||||
|
@ -33,7 +33,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_phdr.c 2931 2013-03-23 11:41:07Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_phdr.c 3009 2014-03-23 01:49:59Z jkoshy $");
|
||||
|
||||
void *
|
||||
_libelf_getphdr(Elf *e, int ec)
|
||||
@ -44,7 +44,8 @@ _libelf_getphdr(Elf *e, int ec)
|
||||
Elf32_Ehdr *eh32;
|
||||
Elf64_Ehdr *eh64;
|
||||
void *ehdr, *phdr;
|
||||
int (*xlator)(char *_d, size_t _dsz, char *_s, size_t _c, int _swap);
|
||||
int (*xlator)(unsigned char *_d, size_t _dsz, unsigned char *_s,
|
||||
size_t _c, int _swap);
|
||||
|
||||
assert(ec == ELFCLASS32 || ec == ELFCLASS64);
|
||||
|
||||
|
@ -31,7 +31,7 @@
|
||||
|
||||
#include "_libelf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelf_xlate.c 2225 2011-11-26 18:55:54Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelf_xlate.c 3007 2014-03-22 08:10:14Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Translate to/from the file representation of ELF objects.
|
||||
@ -99,10 +99,10 @@ _libelf_xlate(Elf_Data *dst, const Elf_Data *src, unsigned int encoding,
|
||||
* buffer.
|
||||
*/
|
||||
if (direction == ELF_TOMEMORY) {
|
||||
cnt = src->d_size / fsz;
|
||||
cnt = (size_t) src->d_size / fsz;
|
||||
dsz = cnt * msz;
|
||||
} else {
|
||||
cnt = src->d_size / msz;
|
||||
cnt = (size_t) src->d_size / msz;
|
||||
dsz = cnt * fsz;
|
||||
}
|
||||
|
||||
@ -112,9 +112,9 @@ _libelf_xlate(Elf_Data *dst, const Elf_Data *src, unsigned int encoding,
|
||||
}
|
||||
|
||||
sb = (uintptr_t) src->d_buf;
|
||||
se = sb + src->d_size;
|
||||
se = sb + (size_t) src->d_size;
|
||||
db = (uintptr_t) dst->d_buf;
|
||||
de = db + dst->d_size;
|
||||
de = db + (size_t) dst->d_size;
|
||||
|
||||
/*
|
||||
* Check for overlapping buffers. Note that db == sb is
|
||||
|
@ -37,7 +37,7 @@
|
||||
#include <sys/mman.h>
|
||||
#endif
|
||||
|
||||
ELFTC_VCSID("$Id: elftc_copyfile.c 2318 2011-12-11 10:54:27Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elftc_copyfile.c 2981 2014-02-01 02:41:13Z jkoshy $");
|
||||
|
||||
/*
|
||||
* Copy the contents referenced by 'ifd' to 'ofd'. Returns 0 on
|
||||
@ -79,11 +79,13 @@ elftc_copyfile(int ifd, int ofd)
|
||||
* If mmap() is not available, or if the mmap() operation
|
||||
* failed, allocate a buffer, and read in input data.
|
||||
*/
|
||||
if (buf == NULL) {
|
||||
if (buf_mmapped == false) {
|
||||
if ((buf = malloc(sb.st_size)) == NULL)
|
||||
return (-1);
|
||||
if (read(ifd, buf, sb.st_size) != sb.st_size)
|
||||
if (read(ifd, buf, sb.st_size) != sb.st_size) {
|
||||
free(buf);
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -29,14 +29,13 @@
|
||||
#include <sys/param.h>
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
#include <libelf.h>
|
||||
#include <libelftc.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "_libelftc.h"
|
||||
|
||||
ELFTC_VCSID("$Id: elftc_demangle.c 2065 2011-10-26 15:24:47Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: elftc_demangle.c 3030 2014-05-01 06:30:48Z kaiwang27 $");
|
||||
|
||||
static int
|
||||
is_mangled(const char *s, int style)
|
||||
|
@ -24,7 +24,7 @@
|
||||
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* $FreeBSD: users/kaiwang27/elftc/libelftc.h 392 2009-05-31 19:17:46Z kaiwang27 $
|
||||
* $Id: libelftc.h 2863 2013-01-06 03:18:32Z jkoshy $
|
||||
* $Id: libelftc.h 3031 2014-05-01 17:45:41Z jkoshy $
|
||||
*/
|
||||
|
||||
#ifndef _LIBELFTC_H_
|
||||
@ -34,6 +34,9 @@
|
||||
|
||||
#include <libelf.h>
|
||||
|
||||
/*
|
||||
* Types meant to be opaque to the consumers of these APIs.
|
||||
*/
|
||||
typedef struct _Elftc_Bfd_Target Elftc_Bfd_Target;
|
||||
typedef struct _Elftc_String_Table Elftc_String_Table;
|
||||
|
||||
|
@ -36,7 +36,7 @@
|
||||
|
||||
#include "_libelftc.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libelftc_dem_gnu3.c 2179 2011-11-18 03:05:47Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libelftc_dem_gnu3.c 3123 2014-12-21 05:46:19Z kaiwang27 $");
|
||||
|
||||
/**
|
||||
* @file cpp_demangle.c
|
||||
|
@ -48,7 +48,7 @@
|
||||
|
||||
#include "_elftc.h"
|
||||
|
||||
ELFTC_VCSID("$Id: nm.c 2484 2012-04-07 15:52:05Z kaiwang27 $");
|
||||
ELFTC_VCSID("$Id: nm.c 3124 2014-12-21 05:46:28Z kaiwang27 $");
|
||||
|
||||
/* symbol information list */
|
||||
STAILQ_HEAD(sym_head, sym_entry);
|
||||
|
@ -22,7 +22,7 @@
|
||||
.\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
.\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $Id: readelf.1 2577 2012-09-13 16:07:04Z jkoshy $
|
||||
.\" $Id: readelf.1 3059 2014-06-02 00:42:32Z kaiwang27 $
|
||||
.\"
|
||||
.Dd September 13, 2012
|
||||
.Os
|
||||
@ -139,7 +139,7 @@ option names:
|
||||
.It p Ta pubnames Ta Show global names.
|
||||
.It r Ta aranges|ranges Ta Show address range information.
|
||||
.It s Ta str Ta Show the debug string table.
|
||||
.It F Ta Ta Show frame information, displaying register rules.
|
||||
.It F Ta frames-interp Ta Show frame information, displaying register rules.
|
||||
.It L Ta decodedline Ta Show line information in decoded form.
|
||||
.It R Ta Ranges Ta Show range lists.
|
||||
.El
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -46,7 +46,7 @@
|
||||
|
||||
#include "_elftc.h"
|
||||
|
||||
ELFTC_VCSID("$Id: strings.c 2351 2011-12-19 11:20:37Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: strings.c 3124 2014-12-21 05:46:28Z kaiwang27 $");
|
||||
|
||||
enum return_code {
|
||||
RETURN_OK,
|
||||
|
@ -46,6 +46,7 @@ SRCS= \
|
||||
dwarf_pubtypes.c \
|
||||
dwarf_ranges.c \
|
||||
dwarf_reloc.c \
|
||||
dwarf_sections.c \
|
||||
dwarf_seterror.c \
|
||||
dwarf_str.c \
|
||||
dwarf_types.c \
|
||||
@ -130,6 +131,7 @@ MAN= dwarf.3 \
|
||||
dwarf_add_weakname.3 \
|
||||
dwarf_attr.3 \
|
||||
dwarf_attrlist.3 \
|
||||
dwarf_attroffset.3 \
|
||||
dwarf_attrval_signed.3 \
|
||||
dwarf_child.3 \
|
||||
dwarf_dealloc.3 \
|
||||
@ -169,6 +171,7 @@ MAN= dwarf.3 \
|
||||
dwarf_get_cie_info.3 \
|
||||
dwarf_get_cie_of_fde.3 \
|
||||
dwarf_get_cu_die_offset.3 \
|
||||
dwarf_get_die_infotypes_flag.3 \
|
||||
dwarf_get_elf.3 \
|
||||
dwarf_get_fde_at_pc.3 \
|
||||
dwarf_get_fde_info_for_all_regs.3 \
|
||||
@ -190,6 +193,7 @@ MAN= dwarf.3 \
|
||||
dwarf_get_relocation_info.3 \
|
||||
dwarf_get_relocation_info_count.3 \
|
||||
dwarf_get_section_bytes.3 \
|
||||
dwarf_get_section_max_offsets.3 \
|
||||
dwarf_get_str.3 \
|
||||
dwarf_get_types.3 \
|
||||
dwarf_get_vars.3 \
|
||||
@ -207,6 +211,7 @@ MAN= dwarf.3 \
|
||||
dwarf_new_expr.3 \
|
||||
dwarf_new_fde.3 \
|
||||
dwarf_next_cu_header.3 \
|
||||
dwarf_next_types_section.3 \
|
||||
dwarf_object_init.3 \
|
||||
dwarf_producer_init.3 \
|
||||
dwarf_producer_set_isa.3 \
|
||||
@ -235,7 +240,9 @@ MLINKS+= \
|
||||
dwarf_attrval_signed.3 dwarf_attrval_string.3 \
|
||||
dwarf_attrval_signed.3 dwarf_attrval_unsigned.3 \
|
||||
dwarf_child.3 dwarf_offdie.3 \
|
||||
dwarf_child.3 dwarf_offdie_b.3 \
|
||||
dwarf_child.3 dwarf_siblingof.3 \
|
||||
dwarf_child.3 dwarf_siblingof_b.3 \
|
||||
dwarf_dealloc.3 dwarf_fde_cie_list_dealloc.3 \
|
||||
dwarf_dealloc.3 dwarf_funcs_dealloc.3 \
|
||||
dwarf_dealloc.3 dwarf_globals_dealloc.3 \
|
||||
@ -249,6 +256,7 @@ MLINKS+= \
|
||||
dwarf_dieoffset.3 dwarf_die_CU_offset.3 \
|
||||
dwarf_dieoffset.3 dwarf_die_CU_offset_range.3 \
|
||||
dwarf_dieoffset.3 dwarf_get_cu_die_offset_given_cu_header_offset.3 \
|
||||
dwarf_dieoffset.3 dwarf_get_cu_die_offset_given_cu_header_offset_b.3 \
|
||||
dwarf_finish.3 dwarf_object_finish.3 \
|
||||
dwarf_formref.3 dwarf_global_formref.3 \
|
||||
dwarf_formudata.3 dwarf_formsdata.3 \
|
||||
@ -288,6 +296,7 @@ MLINKS+= \
|
||||
dwarf_get_pubtypes.3 dwarf_pubtype_name_offsets.3 \
|
||||
dwarf_get_pubtypes.3 dwarf_pubtypename.3 \
|
||||
dwarf_get_ranges.3 dwarf_get_ranges_a.3 \
|
||||
dwarf_get_section_max_offsets.3 dwarf_get_section_max_offsets_b.3 \
|
||||
dwarf_get_types.3 dwarf_type_die_offset.3 \
|
||||
dwarf_get_types.3 dwarf_type_cu_offset.3 \
|
||||
dwarf_get_types.3 dwarf_type_name_offsets.3 \
|
||||
@ -306,6 +315,7 @@ MLINKS+= \
|
||||
dwarf_highpc.3 dwarf_bitoffset.3 \
|
||||
dwarf_highpc.3 dwarf_bitsize.3 \
|
||||
dwarf_highpc.3 dwarf_bytesize.3 \
|
||||
dwarf_highpc.3 dwarf_highpc_b.3 \
|
||||
dwarf_highpc.3 dwarf_lowpc.3 \
|
||||
dwarf_highpc.3 dwarf_srclang.3 \
|
||||
dwarf_lineno.3 dwarf_lineaddr.3 \
|
||||
@ -317,6 +327,9 @@ MLINKS+= \
|
||||
dwarf_lineno.3 dwarf_line_srcfileno.3 \
|
||||
dwarf_loclist.3 dwarf_loclist_n.3 \
|
||||
dwarf_loclist_from_expr.3 dwarf_loclist_from_expr_a.3 \
|
||||
dwarf_loclist_from_expr.3 dwarf_loclist_from_expr_b.3 \
|
||||
dwarf_next_cu_header.3 dwarf_next_cu_header_b.3 \
|
||||
dwarf_next_cu_header.3 dwarf_next_cu_header_c.3 \
|
||||
dwarf_producer_init.3 dwarf_producer_init_b.3 \
|
||||
dwarf_seterrarg.3 dwarf_seterrhand.3 \
|
||||
dwarf_set_frame_cfa_value.3 dwarf_set_frame_rule_initial_value.3 \
|
||||
|
@ -6,5 +6,5 @@
|
||||
const char *
|
||||
elftc_version(void)
|
||||
{
|
||||
return "libelftc r2974";
|
||||
return "libelftc r3130";
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user