MFhead @ r276594
This commit is contained in:
commit
a4ed727666
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/projects/building-blocks/; revision=276595
@ -4,7 +4,7 @@
|
||||
The compilation of software known as FreeBSD is distributed under the
|
||||
following terms:
|
||||
|
||||
Copyright (c) 1992-2014 The FreeBSD Project. All rights reserved.
|
||||
Copyright (c) 1992-2015 The FreeBSD Project. All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions
|
||||
|
@ -260,7 +260,7 @@ BMAKE= MAKEOBJDIRPREFIX=${WORLDTMP} \
|
||||
DESTDIR= \
|
||||
BOOTSTRAPPING=${OSRELDATE} \
|
||||
SSP_CFLAGS= \
|
||||
MK_HTML=no MK_INFO=no NO_LINT=yes MK_MAN=no \
|
||||
MK_HTML=no NO_LINT=yes MK_MAN=no \
|
||||
-DNO_PIC MK_PROFILE=no -DNO_SHARED \
|
||||
-DNO_CPU_CFLAGS MK_WARNS=no MK_CTF=no \
|
||||
MK_CLANG_EXTRAS=no MK_CLANG_FULL=no \
|
||||
@ -298,7 +298,7 @@ KTMAKE= TOOLS_PREFIX=${WORLDTMP} MAKEOBJDIRPREFIX=${WORLDTMP} \
|
||||
DESTDIR= \
|
||||
BOOTSTRAPPING=${OSRELDATE} \
|
||||
SSP_CFLAGS= \
|
||||
MK_HTML=no MK_INFO=no -DNO_LINT MK_MAN=no \
|
||||
MK_HTML=no -DNO_LINT MK_MAN=no \
|
||||
-DNO_PIC MK_PROFILE=no -DNO_SHARED \
|
||||
-DNO_CPU_CFLAGS MK_WARNS=no MK_CTF=no
|
||||
|
||||
@ -443,7 +443,7 @@ LIB32WMAKEFLAGS+= CC="${XCC} ${LIB32FLAGS}" \
|
||||
MK_TESTS=no
|
||||
|
||||
LIB32WMAKE= ${LIB32WMAKEENV} ${MAKE} ${LIB32WMAKEFLAGS} \
|
||||
MK_MAN=no MK_INFO=no MK_HTML=no MK_HYPERV=no MK_BHYVE=no
|
||||
MK_MAN=no MK_HTML=no MK_HYPERV=no MK_BHYVE=no
|
||||
LIB32IMAKE= ${LIB32WMAKE:NINSTALL=*:NDESTDIR=*:N_LDSCRIPTROOT=*} \
|
||||
MK_TOOLCHAIN=no ${IMAKE_INSTALL}
|
||||
.endif
|
||||
@ -595,7 +595,7 @@ _libraries:
|
||||
@echo ">>> stage 4.2: building libraries"
|
||||
@echo "--------------------------------------------------------------"
|
||||
${_+_}cd ${.CURDIR}; \
|
||||
${WMAKE} -DNO_FSCHG MK_HTML=no MK_INFO=no -DNO_LINT MK_MAN=no \
|
||||
${WMAKE} -DNO_FSCHG MK_HTML=no -DNO_LINT MK_MAN=no \
|
||||
MK_PROFILE=no MK_TESTS=no MK_TESTS_SUPPORT=${MK_TESTS} libraries
|
||||
_depend:
|
||||
@echo
|
||||
@ -789,9 +789,6 @@ __installcheck_UGID:
|
||||
#
|
||||
# Required install tools to be saved in a scratch dir for safety.
|
||||
#
|
||||
.if ${MK_INFO} != "no"
|
||||
_install-info= install-info
|
||||
.endif
|
||||
.if ${MK_ZONEINFO} != "no"
|
||||
_zoneinfo= zic tzsetup
|
||||
.endif
|
||||
@ -1448,8 +1445,10 @@ _kgzip= usr.sbin/kgzip
|
||||
.endif
|
||||
|
||||
# If we're given an XAS, don't build binutils.
|
||||
.if ${XAS:M/*} == "" && ${MK_BINUTILS_BOOTSTRAP} != "no"
|
||||
.if ${XAS:M/*} == ""
|
||||
.if ${MK_BINUTILS_BOOTSTRAP} != "no"
|
||||
_binutils= gnu/usr.bin/binutils
|
||||
.endif
|
||||
.if ${MK_ELFTOOLCHAIN_TOOLS} != "no"
|
||||
_elftctools= lib/libelftc \
|
||||
usr.bin/addr2line \
|
||||
@ -1501,7 +1500,7 @@ NXBMAKE= ${NXBENV} ${MAKE} \
|
||||
MACHINE=${TARGET} MACHINE_ARCH=${TARGET_ARCH} \
|
||||
MK_DEBUG_FILES=no MK_GDB=no MK_TESTS=no \
|
||||
SSP_CFLAGS= \
|
||||
MK_HTML=no MK_INFO=no NO_LINT=yes MK_MAN=no \
|
||||
MK_HTML=no NO_LINT=yes MK_MAN=no \
|
||||
-DNO_PIC MK_PROFILE=no -DNO_SHARED \
|
||||
-DNO_CPU_CFLAGS MK_WARNS=no MK_CTF=no \
|
||||
MK_CLANG_EXTRAS=no MK_CLANG_FULL=no \
|
||||
@ -2034,7 +2033,7 @@ XDEV_CPUTYPE?=${CPUTYPE}
|
||||
XDEV_CPUTYPE?=${TARGET_CPUTYPE}
|
||||
.endif
|
||||
|
||||
NOFUN=-DNO_FSCHG MK_HTML=no MK_INFO=no -DNO_LINT \
|
||||
NOFUN=-DNO_FSCHG MK_HTML=no -DNO_LINT \
|
||||
MK_MAN=no MK_NLS=no MK_PROFILE=no \
|
||||
MK_KERBEROS=no MK_RESCUE=no MK_TESTS=no MK_WARNS=no \
|
||||
MK_DEBUG_FILES=no \
|
||||
|
@ -38,6 +38,103 @@
|
||||
# xargs -n1 | sort | uniq -d;
|
||||
# done
|
||||
|
||||
# 20150102: removal of texinfo
|
||||
OLD_FILES+=usr/bin/info
|
||||
OLD_FILES+=usr/bin/infokey
|
||||
OLD_FILES+=usr/bin/install-info
|
||||
OLD_FILES+=usr/bin/makeinfo
|
||||
OLD_FILES+=usr/bin/texindex
|
||||
OLD_FILES+=usr/share/info/am-utils.info.gz
|
||||
OLD_FILES+=usr/share/info/as-utils.info.gz
|
||||
OLD_FILES+=usr/share/info/binutils.info.gz
|
||||
OLD_FILES+=usr/share/info/com_err.info.gz
|
||||
OLD_FILES+=usr/share/info/diff.info.gz
|
||||
OLD_FILES+=usr/share/info/gdb.info.gz
|
||||
OLD_FILES+=usr/share/info/gdbint.info.gz
|
||||
OLD_FILES+=usr/share/info/gperf.info.gz
|
||||
OLD_FILES+=usr/share/info/grep.info.gz
|
||||
OLD_FILES+=usr/share/info/groff.info.gz
|
||||
OLD_FILES+=usr/share/info/heimdal.info.gz
|
||||
OLD_FILES+=usr/share/info/history.info.gz
|
||||
OLD_FILES+=usr/share/info/info-stnd.info.gz
|
||||
OLD_FILES+=usr/share/info/info.info.gz
|
||||
OLD_FILES+=usr/share/info/ld.info.gz
|
||||
OLD_FILES+=usr/share/info/regex.info.gz
|
||||
OLD_FILES+=usr/share/info/rluserman.info.gz
|
||||
OLD_FILES+=usr/share/info/stabs.info.gz
|
||||
OLD_FILES+=usr/share/info/texinfo.info.gz
|
||||
OLD_FILES+=usr/share/man/man1/info.1.gz
|
||||
OLD_FILES+=usr/share/man/man1/infokey.1.gz
|
||||
OLD_FILES+=usr/share/man/man1/install-info.1.gz
|
||||
OLD_FILES+=usr/share/man/man1/makeinfo.1.gz
|
||||
OLD_FILES+=usr/share/man/man1/texindex.1.gz
|
||||
OLD_FILES+=usr/share/man/man5/info.5.gz
|
||||
OLD_FILES+=usr/share/man/man5/texinfo.5.gz
|
||||
# 20141231: new clang import which bumps version from 3.4.1 to 3.5.0.
|
||||
OLD_FILES+=usr/include/clang/3.4.1/__wmmintrin_aes.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/__wmmintrin_pclmul.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/altivec.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/ammintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/arm_neon.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/avx2intrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/avxintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/bmi2intrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/bmiintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/cpuid.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/emmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/f16cintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/fma4intrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/fmaintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/immintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/lzcntintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/mm3dnow.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/mm_malloc.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/mmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/module.map
|
||||
OLD_FILES+=usr/include/clang/3.4.1/nmmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/pmmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/popcntintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/prfchwintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/rdseedintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/rtmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/shaintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/smmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/tbmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/tmmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/wmmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/x86intrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/xmmintrin.h
|
||||
OLD_FILES+=usr/include/clang/3.4.1/xopintrin.h
|
||||
OLD_DIRS+=usr/include/clang/3.4.1
|
||||
# 20141226: Remove gpib/ieee488
|
||||
OLD_FILES+=usr/include/dev/ieee488/ibfoo_int.h
|
||||
OLD_FILES+=usr/include/dev/ieee488/tnt4882.h
|
||||
OLD_FILES+=usr/include/dev/ieee488/ugpib.h
|
||||
OLD_FILES+=usr/include/dev/ieee488/upd7210.h
|
||||
OLD_DIRS+=usr/include/dev/ieee488
|
||||
OLD_FILES+=usr/include/gpib/gpib.h
|
||||
OLD_DIRS+=usr/include/gpib
|
||||
OLD_FILES+=usr/lib/libgpib.a
|
||||
OLD_FILES+=usr/lib/libgpib_p.a
|
||||
OLD_FILES+=usr/lib/libgpib.so
|
||||
OLD_LIBS+=usr/lib/libgpib.so.3
|
||||
OLD_FILES+=usr/lib/libgpib_p.a
|
||||
OLD_FILES+=share/man/man4/pcii.4.gz
|
||||
OLD_FILES+=share/man/man4/gpib.4.gz
|
||||
OLD_FILES+=share/man/man4/tnt4882.4.gz
|
||||
.if ${TARGET_ARCH} == "amd64" || ${TARGET_ARCH} == "powerpc64"
|
||||
OLD_FILES+=usr/lib32/libgpib.a
|
||||
OLD_FILES+=usr/lib32/libgpib_p.a
|
||||
OLD_FILES+=usr/lib32/libgpib.so
|
||||
OLD_LIBS+=usr/lib32/libgpib.so.3
|
||||
.endif
|
||||
|
||||
# 20141224: libxo moved to /lib
|
||||
OLD_LIBS+=usr/lib/libxo.so.0
|
||||
# 20141223: remove in6_gif.h, in_gif.h and if_stf.h
|
||||
OLD_FILES+=usr/include/net/if_stf.h
|
||||
OLD_FILES+=usr/include/netinet/in_gif.h
|
||||
OLD_FILES+=usr/include/netinet6/in6_gif.h
|
||||
# 20141202: update to mandoc CVS 20141201
|
||||
OLD_FILES+=usr.bin/preconv
|
||||
OLD_FILES+=share/man/man1/preconv.1.gz
|
||||
|
75
UPDATING
75
UPDATING
@ -31,6 +31,80 @@ NOTE TO PEOPLE WHO THINK THAT FreeBSD 11.x IS SLOW:
|
||||
disable the most expensive debugging functionality run
|
||||
"ln -s 'abort:false,junk:false' /etc/malloc.conf".)
|
||||
|
||||
20150102:
|
||||
The GNU texinfo and GNU info pages have been removed.
|
||||
To be able to view GNU info pages please install texinfo from ports.
|
||||
|
||||
20141231:
|
||||
Clang, llvm and lldb have been upgraded to 3.5.0 release.
|
||||
|
||||
As of this release, a prerequisite for building clang, llvm and lldb is
|
||||
a C++11 capable compiler and C++11 standard library. This means that to
|
||||
be able to successfully build the cross-tools stage of buildworld, with
|
||||
clang as the bootstrap compiler, your system compiler or cross compiler
|
||||
should either be clang 3.3 or later, or gcc 4.8 or later, and your
|
||||
system C++ library should be libc++, or libdstdc++ from gcc 4.8 or
|
||||
later.
|
||||
|
||||
On any standard FreeBSD 10.x or 11.x installation, where clang and
|
||||
libc++ are on by default (that is, on x86 or arm), this should work out
|
||||
of the box.
|
||||
|
||||
On 9.x installations where clang is enabled by default, e.g. on x86 and
|
||||
powerpc, libc++ will not be enabled by default, so libc++ should be
|
||||
built (with clang) and installed first. If both clang and libc++ are
|
||||
missing, build clang first, then use it to build libc++.
|
||||
|
||||
On 8.x and earlier installations, upgrade to 9.x first, and then follow
|
||||
the instructions for 9.x above.
|
||||
|
||||
Sparc64 and mips users are unaffected, as they still use gcc 4.2.1 by
|
||||
default, and do not build clang.
|
||||
|
||||
Many embedded systems are resource constrained, and will not be able to
|
||||
build clang in a reasonable time, or in some cases at all. In those
|
||||
cases, cross building bootable systems on amd64 is a workaround.
|
||||
|
||||
This new version of clang introduces a number of new warnings, of which
|
||||
the following are most likely to appear:
|
||||
|
||||
-Wabsolute-value
|
||||
|
||||
This warns in two cases, for both C and C++:
|
||||
* When the code is trying to take the absolute value of an unsigned
|
||||
quantity, which is effectively a no-op, and almost never what was
|
||||
intended. The code should be fixed, if at all possible. If you are
|
||||
sure that the unsigned quantity can be safely cast to signed, without
|
||||
loss of information or undefined behavior, you can add an explicit
|
||||
cast, or disable the warning.
|
||||
|
||||
* When the code is trying to take an absolute value, but the called
|
||||
abs() variant is for the wrong type, which can lead to truncation.
|
||||
If you want to disable the warning instead of fixing the code, please
|
||||
make sure that truncation will not occur, or it might lead to unwanted
|
||||
side-effects.
|
||||
|
||||
-Wtautological-undefined-compare and
|
||||
-Wundefined-bool-conversion
|
||||
|
||||
These warn when C++ code is trying to compare 'this' against NULL, while
|
||||
'this' should never be NULL in well-defined C++ code. However, there is
|
||||
some legacy (pre C++11) code out there, which actively abuses this
|
||||
feature, which was less strictly defined in previous C++ versions.
|
||||
|
||||
Squid and openjdk do this, for example. The warning can be turned off
|
||||
for C++98 and earlier, but compiling the code in C++11 mode might result
|
||||
in unexpected behavior; for example, the parts of the program that are
|
||||
unreachable could be optimized away.
|
||||
|
||||
20141222:
|
||||
The old NFS client and server (kernel options NFSCLIENT, NFSSERVER)
|
||||
kernel sources have been removed. The .h files remain, since some
|
||||
utilities include them. This will need to be fixed later.
|
||||
If "mount -t oldnfs ..." is attempted, it will fail.
|
||||
If the "-o" option on mountd(8), nfsd(8) or nfsstat(1) is used,
|
||||
the utilities will report errors.
|
||||
|
||||
20141121:
|
||||
The handling of LOCAL_LIB_DIRS has been altered to skip addition of
|
||||
directories to top level SUBDIR variable when their parent
|
||||
@ -106,6 +180,7 @@ NOTE TO PEOPLE WHO THINK THAT FreeBSD 11.x IS SLOW:
|
||||
The GNU texinfo and GNU info pages are not built and installed
|
||||
anymore, WITH_INFO knob has been added to allow to built and install
|
||||
them again.
|
||||
UPDATE: see 20150102 entry on texinfo's removal
|
||||
|
||||
20140708:
|
||||
The GNU readline library is now an INTERNALLIB - that is, it is
|
||||
|
@ -29,7 +29,7 @@
|
||||
.\" @(#)symlink.7 8.3 (Berkeley) 3/31/94
|
||||
.\" $FreeBSD$
|
||||
.\"
|
||||
.Dd April 25, 2010
|
||||
.Dd December 29, 2014
|
||||
.Dt SYMLINK 7
|
||||
.Os
|
||||
.Sh NAME
|
||||
@ -219,7 +219,7 @@ would change the ownership of
|
||||
.Dq Li slink
|
||||
itself.
|
||||
.Pp
|
||||
There are four exceptions to this rule.
|
||||
There are five exceptions to this rule.
|
||||
The
|
||||
.Xr mv 1
|
||||
and
|
||||
@ -262,13 +262,12 @@ a file tree.)
|
||||
.Pp
|
||||
The
|
||||
.Xr file 1
|
||||
command is also an exception to this rule.
|
||||
The
|
||||
.Xr file 1
|
||||
command does not follow symbolic links named as argument by default.
|
||||
The
|
||||
.Xr file 1
|
||||
command does follow symbolic links named as argument if
|
||||
and
|
||||
.Xr stat 1
|
||||
commands are also exceptions to this rule.
|
||||
These
|
||||
commands do not follow symbolic links named as argument by default,
|
||||
but do follow symbolic links named as argument if the
|
||||
.Fl L
|
||||
option is specified.
|
||||
.Pp
|
||||
|
@ -90,13 +90,14 @@ exraise(int e)
|
||||
|
||||
|
||||
/*
|
||||
* Called from trap.c when a SIGINT is received. (If the user specifies
|
||||
* that SIGINT is to be trapped or ignored using the trap builtin, then
|
||||
* this routine is not called.) Suppressint is nonzero when interrupts
|
||||
* are held using the INTOFF macro. If SIGINTs are not suppressed and
|
||||
* the shell is not a root shell, then we want to be terminated if we
|
||||
* get here, as if we were terminated directly by a SIGINT. Arrange for
|
||||
* this here.
|
||||
* Called from trap.c when a SIGINT is received and not suppressed, or when
|
||||
* an interrupt is pending and interrupts are re-enabled using INTON.
|
||||
* (If the user specifies that SIGINT is to be trapped or ignored using the
|
||||
* trap builtin, then this routine is not called.) Suppressint is nonzero
|
||||
* when interrupts are held using the INTOFF macro. If SIGINTs are not
|
||||
* suppressed and the shell is not a root shell, then we want to be
|
||||
* terminated if we get here, as if we were terminated directly by a SIGINT.
|
||||
* Arrange for this here.
|
||||
*/
|
||||
|
||||
void
|
||||
@ -104,16 +105,6 @@ onint(void)
|
||||
{
|
||||
sigset_t sigs;
|
||||
|
||||
/*
|
||||
* The !in_dotrap here is safe. The only way we can arrive here
|
||||
* with in_dotrap set is that a trap handler set SIGINT to SIG_DFL
|
||||
* and killed itself.
|
||||
*/
|
||||
|
||||
if (suppressint && !in_dotrap) {
|
||||
intpending++;
|
||||
return;
|
||||
}
|
||||
intpending = 0;
|
||||
sigemptyset(&sigs);
|
||||
sigprocmask(SIG_SETMASK, &sigs, NULL);
|
||||
@ -130,6 +121,7 @@ onint(void)
|
||||
else {
|
||||
signal(SIGINT, SIG_DFL);
|
||||
kill(getpid(), SIGINT);
|
||||
_exit(128 + SIGINT);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -75,11 +75,12 @@ extern volatile sig_atomic_t intpending;
|
||||
#define is_int_on() suppressint
|
||||
#define SETINTON(s) suppressint = (s)
|
||||
#define FORCEINTON {suppressint = 0; if (intpending) onint();}
|
||||
#define SET_PENDING_INT intpending = 1
|
||||
#define CLEAR_PENDING_INT intpending = 0
|
||||
#define int_pending() intpending
|
||||
|
||||
void exraise(int) __dead2;
|
||||
void onint(void);
|
||||
void onint(void) __dead2;
|
||||
void warning(const char *, ...) __printflike(1, 2);
|
||||
void error(const char *, ...) __printf0like(1, 2) __dead2;
|
||||
void exerror(int, const char *, ...) __printf0like(2, 3) __dead2;
|
||||
|
@ -539,13 +539,13 @@ expredir(union node *n)
|
||||
case NFROMTO:
|
||||
case NAPPEND:
|
||||
case NCLOBBER:
|
||||
expandarg(redir->nfile.fname, &fn, EXP_TILDE | EXP_REDIR);
|
||||
expandarg(redir->nfile.fname, &fn, EXP_TILDE);
|
||||
redir->nfile.expfname = fn.list->text;
|
||||
break;
|
||||
case NFROMFD:
|
||||
case NTOFD:
|
||||
if (redir->ndup.vname) {
|
||||
expandarg(redir->ndup.vname, &fn, EXP_TILDE | EXP_REDIR);
|
||||
expandarg(redir->ndup.vname, &fn, EXP_TILDE);
|
||||
fixredir(redir, fn.list->text, 1);
|
||||
}
|
||||
break;
|
||||
|
@ -171,17 +171,12 @@ expandarg(union node *arg, struct arglist *arglist, int flag)
|
||||
STPUTC('\0', expdest);
|
||||
p = grabstackstr(expdest);
|
||||
exparg.lastp = &exparg.list;
|
||||
/*
|
||||
* TODO - EXP_REDIR
|
||||
*/
|
||||
if (flag & EXP_FULL) {
|
||||
ifsbreakup(p, &exparg);
|
||||
*exparg.lastp = NULL;
|
||||
exparg.lastp = &exparg.list;
|
||||
expandmeta(exparg.list, flag);
|
||||
} else {
|
||||
if (flag & EXP_REDIR) /*XXX - for now, just remove escapes */
|
||||
rmescapes(p);
|
||||
sp = (struct strlist *)stalloc(sizeof (struct strlist));
|
||||
sp->text = p;
|
||||
*exparg.lastp = sp;
|
||||
@ -209,7 +204,7 @@ expandarg(union node *arg, struct arglist *arglist, int flag)
|
||||
* expansion, and tilde expansion if requested via EXP_TILDE/EXP_VARTILDE.
|
||||
* Processing ends at a CTLENDVAR or CTLENDARI character as well as '\0'.
|
||||
* This is used to expand word in ${var+word} etc.
|
||||
* If EXP_FULL, EXP_CASE or EXP_REDIR are set, keep and/or generate CTLESC
|
||||
* If EXP_FULL or EXP_CASE are set, keep and/or generate CTLESC
|
||||
* characters to allow for further processing.
|
||||
* If EXP_FULL is set, also preserve CTLQUOTEMARK characters.
|
||||
*/
|
||||
@ -217,7 +212,7 @@ static char *
|
||||
argstr(char *p, int flag)
|
||||
{
|
||||
char c;
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE | EXP_REDIR); /* do CTLESC */
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE); /* do CTLESC */
|
||||
int firsteq = 1;
|
||||
int split_lit;
|
||||
int lit_quoted;
|
||||
@ -303,7 +298,7 @@ exptilde(char *p, int flag)
|
||||
char c, *startp = p;
|
||||
struct passwd *pw;
|
||||
char *home;
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE | EXP_REDIR);
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE);
|
||||
|
||||
while ((c = *p) != '\0') {
|
||||
switch(c) {
|
||||
@ -437,7 +432,7 @@ expbackq(union node *cmd, int quoted, int flag)
|
||||
char lastc;
|
||||
int startloc = dest - stackblock();
|
||||
char const *syntax = quoted? DQSYNTAX : BASESYNTAX;
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE | EXP_REDIR);
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE);
|
||||
size_t nnl;
|
||||
|
||||
INTOFF;
|
||||
@ -637,7 +632,7 @@ evalvar(char *p, int flag)
|
||||
int varlen;
|
||||
int varlenb;
|
||||
int easy;
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE | EXP_REDIR);
|
||||
int quotes = flag & (EXP_FULL | EXP_CASE);
|
||||
|
||||
varflags = (unsigned char)*p++;
|
||||
subtype = varflags & VSTYPE;
|
||||
@ -862,7 +857,7 @@ varisset(const char *name, int nulok)
|
||||
static void
|
||||
strtodest(const char *p, int flag, int subtype, int quoted)
|
||||
{
|
||||
if (flag & (EXP_FULL | EXP_CASE | EXP_REDIR) && subtype != VSLENGTH)
|
||||
if (flag & (EXP_FULL | EXP_CASE) && subtype != VSLENGTH)
|
||||
STPUTS_QUOTES(p, quoted ? DQSYNTAX : BASESYNTAX, expdest);
|
||||
else
|
||||
STPUTS(p, expdest);
|
||||
@ -1104,7 +1099,6 @@ expandmeta(struct strlist *str, int flag __unused)
|
||||
struct strlist **savelastp;
|
||||
struct strlist *sp;
|
||||
char c;
|
||||
/* TODO - EXP_REDIR */
|
||||
|
||||
while (str) {
|
||||
savelastp = exparg.lastp;
|
||||
|
@ -50,7 +50,6 @@ struct arglist {
|
||||
#define EXP_FULL 0x1 /* perform word splitting & file globbing */
|
||||
#define EXP_TILDE 0x2 /* do normal tilde expansion */
|
||||
#define EXP_VARTILDE 0x4 /* expand tildes in an assignment */
|
||||
#define EXP_REDIR 0x8 /* file glob for a redirection (1 match only) */
|
||||
#define EXP_CASE 0x10 /* keeps quotes around for CASE pattern */
|
||||
#define EXP_SPLIT_LIT 0x20 /* IFS split literal text ${v+-a b c} */
|
||||
#define EXP_LIT_QUOTED 0x40 /* for EXP_SPLIT_LIT, start off quoted */
|
||||
|
@ -75,7 +75,7 @@ __FBSDID("$FreeBSD$");
|
||||
static char sigmode[NSIG]; /* current value of signal */
|
||||
volatile sig_atomic_t pendingsig; /* indicates some signal received */
|
||||
volatile sig_atomic_t pendingsig_waitcmd; /* indicates SIGINT/SIGQUIT received */
|
||||
int in_dotrap; /* do we execute in a trap handler? */
|
||||
static int in_dotrap; /* do we execute in a trap handler? */
|
||||
static char *volatile trap[NSIG]; /* trap handler commands */
|
||||
static volatile sig_atomic_t gotsig[NSIG];
|
||||
/* indicates specified signal received */
|
||||
@ -380,7 +380,15 @@ onsig(int signo)
|
||||
{
|
||||
|
||||
if (signo == SIGINT && trap[SIGINT] == NULL) {
|
||||
onint();
|
||||
/*
|
||||
* The !in_dotrap here is safe. The only way we can arrive
|
||||
* here with in_dotrap set is that a trap handler set SIGINT to
|
||||
* SIG_DFL and killed itself.
|
||||
*/
|
||||
if (suppressint && !in_dotrap)
|
||||
SET_PENDING_INT;
|
||||
else
|
||||
onint();
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -35,7 +35,6 @@
|
||||
|
||||
extern volatile sig_atomic_t pendingsig;
|
||||
extern volatile sig_atomic_t pendingsig_waitcmd;
|
||||
extern int in_dotrap;
|
||||
|
||||
void clear_traps(void);
|
||||
int have_traps(void);
|
||||
|
@ -443,7 +443,7 @@ This feature becomes
|
||||
.Sy active
|
||||
once a
|
||||
.Sy recordsize
|
||||
property has been set larger than 128KB, and will return to being
|
||||
property has been set larger than 128KB, and will return to being
|
||||
.Sy enabled
|
||||
once all filesystems that have ever had their recordsize larger than 128KB
|
||||
are destroyed.
|
||||
|
@ -4509,11 +4509,12 @@ zpool_do_status(int argc, char **argv)
|
||||
}
|
||||
|
||||
typedef struct upgrade_cbdata {
|
||||
int cb_first;
|
||||
char cb_poolname[ZPOOL_MAXNAMELEN];
|
||||
int cb_argc;
|
||||
uint64_t cb_version;
|
||||
char **cb_argv;
|
||||
boolean_t cb_first;
|
||||
boolean_t cb_unavail;
|
||||
char cb_poolname[ZPOOL_MAXNAMELEN];
|
||||
int cb_argc;
|
||||
uint64_t cb_version;
|
||||
char **cb_argv;
|
||||
} upgrade_cbdata_t;
|
||||
|
||||
#ifdef __FreeBSD__
|
||||
@ -4629,6 +4630,14 @@ upgrade_cb(zpool_handle_t *zhp, void *arg)
|
||||
boolean_t printnl = B_FALSE;
|
||||
int ret;
|
||||
|
||||
if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) {
|
||||
(void) fprintf(stderr, gettext("cannot upgrade '%s': pool is "
|
||||
"currently unavailable.\n\n"), zpool_get_name(zhp));
|
||||
cbp->cb_unavail = B_TRUE;
|
||||
/* Allow iteration to continue. */
|
||||
return (0);
|
||||
}
|
||||
|
||||
config = zpool_get_config(zhp, NULL);
|
||||
verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
|
||||
&version) == 0);
|
||||
@ -4689,6 +4698,26 @@ upgrade_cb(zpool_handle_t *zhp, void *arg)
|
||||
return (0);
|
||||
}
|
||||
|
||||
static int
|
||||
upgrade_list_unavail(zpool_handle_t *zhp, void *arg)
|
||||
{
|
||||
upgrade_cbdata_t *cbp = arg;
|
||||
|
||||
if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) {
|
||||
if (cbp->cb_first) {
|
||||
(void) fprintf(stderr, gettext("The following pools "
|
||||
"are unavailable and cannot be upgraded as this "
|
||||
"time.\n\n"));
|
||||
(void) fprintf(stderr, gettext("POOL\n"));
|
||||
(void) fprintf(stderr, gettext("------------\n"));
|
||||
cbp->cb_first = B_FALSE;
|
||||
}
|
||||
(void) printf(gettext("%s\n"), zpool_get_name(zhp));
|
||||
cbp->cb_unavail = B_TRUE;
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
|
||||
static int
|
||||
upgrade_list_older_cb(zpool_handle_t *zhp, void *arg)
|
||||
{
|
||||
@ -4696,6 +4725,15 @@ upgrade_list_older_cb(zpool_handle_t *zhp, void *arg)
|
||||
nvlist_t *config;
|
||||
uint64_t version;
|
||||
|
||||
if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) {
|
||||
/*
|
||||
* This will have been reported by upgrade_list_unavail so
|
||||
* just allow iteration to continue.
|
||||
*/
|
||||
cbp->cb_unavail = B_TRUE;
|
||||
return (0);
|
||||
}
|
||||
|
||||
config = zpool_get_config(zhp, NULL);
|
||||
verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
|
||||
&version) == 0);
|
||||
@ -4729,6 +4767,15 @@ upgrade_list_disabled_cb(zpool_handle_t *zhp, void *arg)
|
||||
nvlist_t *config;
|
||||
uint64_t version;
|
||||
|
||||
if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) {
|
||||
/*
|
||||
* This will have been reported by upgrade_list_unavail so
|
||||
* just allow iteration to continue.
|
||||
*/
|
||||
cbp->cb_unavail = B_TRUE;
|
||||
return (0);
|
||||
}
|
||||
|
||||
config = zpool_get_config(zhp, NULL);
|
||||
verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
|
||||
&version) == 0);
|
||||
@ -4782,10 +4829,17 @@ upgrade_one(zpool_handle_t *zhp, void *data)
|
||||
uint64_t cur_version;
|
||||
int ret;
|
||||
|
||||
if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) {
|
||||
(void) fprintf(stderr, gettext("cannot upgrade '%s': pool is "
|
||||
"is currently unavailable.\n\n"), zpool_get_name(zhp));
|
||||
cbp->cb_unavail = B_TRUE;
|
||||
return (1);
|
||||
}
|
||||
|
||||
if (strcmp("log", zpool_get_name(zhp)) == 0) {
|
||||
(void) printf(gettext("'log' is now a reserved word\n"
|
||||
"Pool 'log' must be renamed using export and import"
|
||||
" to upgrade.\n"));
|
||||
" to upgrade.\n\n"));
|
||||
return (1);
|
||||
}
|
||||
|
||||
@ -4829,7 +4883,7 @@ upgrade_one(zpool_handle_t *zhp, void *data)
|
||||
#endif /* __FreeBSD __*/
|
||||
} else if (cur_version == SPA_VERSION) {
|
||||
(void) printf(gettext("Pool '%s' already has all "
|
||||
"supported features enabled.\n"),
|
||||
"supported features enabled.\n\n"),
|
||||
zpool_get_name(zhp));
|
||||
}
|
||||
}
|
||||
@ -4986,11 +5040,13 @@ zpool_do_upgrade(int argc, char **argv)
|
||||
ret = zpool_iter(g_zfs, upgrade_cb, &cb);
|
||||
if (ret == 0 && cb.cb_first) {
|
||||
if (cb.cb_version == SPA_VERSION) {
|
||||
(void) printf(gettext("All pools are already "
|
||||
"formatted using feature flags.\n\n"));
|
||||
(void) printf(gettext("Every feature flags "
|
||||
(void) printf(gettext("All %spools are already "
|
||||
"formatted using feature flags.\n\n"),
|
||||
cb.cb_unavail ? gettext("available ") : "");
|
||||
(void) printf(gettext("Every %sfeature flags "
|
||||
"pool already has all supported features "
|
||||
"enabled.\n"));
|
||||
"enabled.\n"),
|
||||
cb.cb_unavail ? gettext("available ") : "");
|
||||
} else {
|
||||
(void) printf(gettext("All pools are already "
|
||||
"formatted with version %llu or higher.\n"),
|
||||
@ -4998,13 +5054,22 @@ zpool_do_upgrade(int argc, char **argv)
|
||||
}
|
||||
}
|
||||
} else if (argc == 0) {
|
||||
cb.cb_first = B_TRUE;
|
||||
ret = zpool_iter(g_zfs, upgrade_list_unavail, &cb);
|
||||
assert(ret == 0);
|
||||
|
||||
if (!cb.cb_first) {
|
||||
(void) fprintf(stderr, "\n");
|
||||
}
|
||||
|
||||
cb.cb_first = B_TRUE;
|
||||
ret = zpool_iter(g_zfs, upgrade_list_older_cb, &cb);
|
||||
assert(ret == 0);
|
||||
|
||||
if (cb.cb_first) {
|
||||
(void) printf(gettext("All pools are formatted "
|
||||
"using feature flags.\n\n"));
|
||||
(void) printf(gettext("All %spools are formatted using "
|
||||
"feature flags.\n\n"), cb.cb_unavail ?
|
||||
gettext("available ") : "");
|
||||
} else {
|
||||
(void) printf(gettext("\nUse 'zpool upgrade -v' "
|
||||
"for a list of available legacy versions.\n"));
|
||||
@ -5015,13 +5080,14 @@ zpool_do_upgrade(int argc, char **argv)
|
||||
assert(ret == 0);
|
||||
|
||||
if (cb.cb_first) {
|
||||
(void) printf(gettext("Every feature flags pool has "
|
||||
"all supported features enabled.\n"));
|
||||
(void) printf(gettext("Every %sfeature flags pool has "
|
||||
"all supported features enabled.\n"),
|
||||
cb.cb_unavail ? gettext("available ") : "");
|
||||
} else {
|
||||
(void) printf(gettext("\n"));
|
||||
}
|
||||
} else {
|
||||
ret = for_each_pool(argc, argv, B_FALSE, NULL,
|
||||
ret = for_each_pool(argc, argv, B_TRUE, NULL,
|
||||
upgrade_one, &cb);
|
||||
}
|
||||
|
||||
|
@ -127,6 +127,7 @@ dtrace_dof_init(void)
|
||||
int efd;
|
||||
char *s;
|
||||
size_t shstridx;
|
||||
uint64_t aligned_filesz;
|
||||
#endif
|
||||
|
||||
if (getenv("DTRACE_DOF_INIT_DISABLE") != NULL)
|
||||
@ -171,6 +172,7 @@ dtrace_dof_init(void)
|
||||
if (s != NULL && strcmp(s, ".SUNW_dof") == 0) {
|
||||
dofdata = elf_getdata(scn, NULL);
|
||||
dof = dofdata->d_buf;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -182,7 +184,9 @@ dtrace_dof_init(void)
|
||||
}
|
||||
|
||||
while ((char *) dof < (char *) dofdata->d_buf + dofdata->d_size) {
|
||||
dof_next = (void *) ((char *) dof + dof->dofh_filesz);
|
||||
aligned_filesz = (shdr.sh_addralign == 0 ? dof->dofh_filesz :
|
||||
roundup2(dof->dofh_filesz, shdr.sh_addralign));
|
||||
dof_next = (void *) ((char *) dof + aligned_filesz);
|
||||
#endif
|
||||
|
||||
if (dof->dofh_ident[DOF_ID_MAG0] != DOF_MAG_MAG0 ||
|
||||
|
@ -685,8 +685,8 @@ dump_elf64(dtrace_hdl_t *dtp, const dof_hdr_t *dof, int fd)
|
||||
elf_file.ehdr.e_machine = EM_ARM;
|
||||
#elif defined(__mips__)
|
||||
elf_file.ehdr.e_machine = EM_MIPS;
|
||||
#elif defined(__powerpc__)
|
||||
elf_file.ehdr.e_machine = EM_PPC;
|
||||
#elif defined(__powerpc64__)
|
||||
elf_file.ehdr.e_machine = EM_PPC64;
|
||||
#elif defined(__sparc)
|
||||
elf_file.ehdr.e_machine = EM_SPARCV9;
|
||||
#elif defined(__i386) || defined(__amd64)
|
||||
@ -784,21 +784,32 @@ dump_elf64(dtrace_hdl_t *dtp, const dof_hdr_t *dof, int fd)
|
||||
|
||||
static int
|
||||
dt_symtab_lookup(Elf_Data *data_sym, int nsym, uintptr_t addr, uint_t shn,
|
||||
GElf_Sym *sym)
|
||||
GElf_Sym *sym, int uses_funcdesc, Elf *elf)
|
||||
{
|
||||
int i, ret = -1;
|
||||
Elf64_Addr symval;
|
||||
Elf_Scn *opd_scn;
|
||||
Elf_Data *opd_desc;
|
||||
GElf_Sym s;
|
||||
|
||||
for (i = 0; i < nsym && gelf_getsym(data_sym, i, sym) != NULL; i++) {
|
||||
if (GELF_ST_TYPE(sym->st_info) == STT_FUNC &&
|
||||
shn == sym->st_shndx &&
|
||||
sym->st_value <= addr &&
|
||||
addr < sym->st_value + sym->st_size) {
|
||||
if (GELF_ST_BIND(sym->st_info) == STB_GLOBAL)
|
||||
return (0);
|
||||
if (GELF_ST_TYPE(sym->st_info) == STT_FUNC) {
|
||||
symval = sym->st_value;
|
||||
if (uses_funcdesc) {
|
||||
opd_scn = elf_getscn(elf, sym->st_shndx);
|
||||
opd_desc = elf_rawdata(opd_scn, NULL);
|
||||
symval =
|
||||
*(uint64_t*)((char *)opd_desc->d_buf + symval);
|
||||
}
|
||||
if ((uses_funcdesc || shn == sym->st_shndx) &&
|
||||
symval <= addr &&
|
||||
addr < symval + sym->st_size) {
|
||||
if (GELF_ST_BIND(sym->st_info) == STB_GLOBAL)
|
||||
return (0);
|
||||
|
||||
ret = 0;
|
||||
s = *sym;
|
||||
ret = 0;
|
||||
s = *sym;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1375,7 +1386,8 @@ process_obj(dtrace_hdl_t *dtp, const char *obj, int *eprobesp)
|
||||
continue;
|
||||
|
||||
if (dt_symtab_lookup(data_sym, isym, rela.r_offset,
|
||||
shdr_rel.sh_info, &fsym) != 0) {
|
||||
shdr_rel.sh_info, &fsym,
|
||||
(emachine1 == EM_PPC64), elf) != 0) {
|
||||
dt_strtab_destroy(strtab);
|
||||
goto err;
|
||||
}
|
||||
@ -1536,7 +1548,8 @@ process_obj(dtrace_hdl_t *dtp, const char *obj, int *eprobesp)
|
||||
p = strhyphenate(p + 3); /* strlen("___") */
|
||||
|
||||
if (dt_symtab_lookup(data_sym, isym, rela.r_offset,
|
||||
shdr_rel.sh_info, &fsym) != 0)
|
||||
shdr_rel.sh_info, &fsym,
|
||||
(emachine1 == EM_PPC64), elf) != 0)
|
||||
goto err;
|
||||
|
||||
if (fsym.st_name > data_str->d_size)
|
||||
|
@ -256,7 +256,8 @@ zpool_get_prop(zpool_handle_t *zhp, zpool_prop_t prop, char *buf, size_t len,
|
||||
break;
|
||||
|
||||
case ZPOOL_PROP_HEALTH:
|
||||
(void) strlcpy(buf, "FAULTED", len);
|
||||
(void) strlcpy(buf,
|
||||
zpool_pool_state_to_name(POOL_STATE_UNAVAIL), len);
|
||||
break;
|
||||
|
||||
case ZPOOL_PROP_GUID:
|
||||
|
@ -74,8 +74,8 @@ Write the output to file in
|
||||
.Sh EXIT STATUS
|
||||
.Ex -std
|
||||
.Sh SEE ALSO
|
||||
.Xr ctfmerge 1 ,
|
||||
.Xr ctfdump 1
|
||||
.Xr ctfdump 1 ,
|
||||
.Xr ctfmerge 1
|
||||
.Sh HISTORY
|
||||
The
|
||||
.Nm
|
||||
|
@ -6185,7 +6185,7 @@ ppc_elf_relocate_section (bfd *output_bfd,
|
||||
howto = NULL;
|
||||
if (r_type < R_PPC_max)
|
||||
howto = ppc_elf_howto_table[r_type];
|
||||
switch (r_type)
|
||||
switch ((int) r_type)
|
||||
{
|
||||
default:
|
||||
(*_bfd_error_handler)
|
||||
|
@ -1548,7 +1548,7 @@ ppc_insert_operand (unsigned long insn,
|
||||
errmsg = NULL;
|
||||
insn = (*operand->insert) (insn, (long) val, ppc_cpu, &errmsg);
|
||||
if (errmsg != (const char *) NULL)
|
||||
as_bad_where (file, line, errmsg);
|
||||
as_bad_where (file, line, "%s", errmsg);
|
||||
}
|
||||
else
|
||||
insn |= ((long) val & operand->bitm) << operand->shift;
|
||||
@ -2279,7 +2279,7 @@ md_assemble (char *str)
|
||||
{
|
||||
insn = (*operand->insert) (insn, 0L, ppc_cpu, &errmsg);
|
||||
if (errmsg != (const char *) NULL)
|
||||
as_bad (errmsg);
|
||||
as_bad ("%s", errmsg);
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -2292,7 +2292,7 @@ md_assemble (char *str)
|
||||
{
|
||||
insn = (*operand->insert) (insn, 0L, ppc_cpu, &errmsg);
|
||||
if (errmsg != (const char *) NULL)
|
||||
as_bad (errmsg);
|
||||
as_bad ("%s", errmsg);
|
||||
}
|
||||
if ((operand->flags & PPC_OPERAND_NEXT) != 0)
|
||||
next_opindex = *opindex_ptr + 1;
|
||||
|
@ -1040,6 +1040,15 @@ operand (expressionS *expressionP, enum expr_mode mode)
|
||||
{
|
||||
for (i = 0; i < expressionP->X_add_number; ++i)
|
||||
generic_bignum[i] = ~generic_bignum[i];
|
||||
|
||||
/* Extend the bignum to at least the size of .octa. */
|
||||
if (expressionP->X_add_number < SIZE_OF_LARGE_NUMBER)
|
||||
{
|
||||
expressionP->X_add_number = SIZE_OF_LARGE_NUMBER;
|
||||
for (; i < expressionP->X_add_number; ++i)
|
||||
generic_bignum[i] = ~(LITTLENUM_TYPE) 0;
|
||||
}
|
||||
|
||||
if (c == '-')
|
||||
for (i = 0; i < expressionP->X_add_number; ++i)
|
||||
{
|
||||
@ -1050,14 +1059,12 @@ operand (expressionS *expressionP, enum expr_mode mode)
|
||||
}
|
||||
else if (c == '!')
|
||||
{
|
||||
int nonzero = 0;
|
||||
for (i = 0; i < expressionP->X_add_number; ++i)
|
||||
{
|
||||
if (generic_bignum[i])
|
||||
nonzero = 1;
|
||||
generic_bignum[i] = 0;
|
||||
}
|
||||
generic_bignum[0] = nonzero;
|
||||
if (generic_bignum[i] != 0)
|
||||
break;
|
||||
expressionP->X_add_number = i >= expressionP->X_add_number;
|
||||
expressionP->X_op = O_constant;
|
||||
expressionP->X_unsigned = 1;
|
||||
}
|
||||
}
|
||||
else if (expressionP->X_op != O_illegal
|
||||
|
@ -335,7 +335,7 @@ input_scrub_next_buffer (char **bufp)
|
||||
|
||||
if (partial_size)
|
||||
{
|
||||
memcpy (buffer_start + BEFORE_SIZE, partial_where,
|
||||
memmove (buffer_start + BEFORE_SIZE, partial_where,
|
||||
(unsigned int) partial_size);
|
||||
memcpy (buffer_start + BEFORE_SIZE, save_source, AFTER_SIZE);
|
||||
}
|
||||
|
@ -4117,15 +4117,32 @@ emit_expr (expressionS *exp, unsigned int nbytes)
|
||||
unsigned int size;
|
||||
LITTLENUM_TYPE *nums;
|
||||
|
||||
know (nbytes % CHARS_PER_LITTLENUM == 0);
|
||||
|
||||
size = exp->X_add_number * CHARS_PER_LITTLENUM;
|
||||
if (nbytes < size)
|
||||
{
|
||||
as_warn (_("bignum truncated to %d bytes"), nbytes);
|
||||
int i = nbytes / CHARS_PER_LITTLENUM;
|
||||
if (i != 0)
|
||||
{
|
||||
LITTLENUM_TYPE sign = 0;
|
||||
if ((generic_bignum[--i]
|
||||
& (1 << (LITTLENUM_NUMBER_OF_BITS - 1))) != 0)
|
||||
sign = ~(LITTLENUM_TYPE) 0;
|
||||
while (++i < exp->X_add_number)
|
||||
if (generic_bignum[i] != sign)
|
||||
break;
|
||||
}
|
||||
if (i < exp->X_add_number)
|
||||
as_warn (_("bignum truncated to %d bytes"), nbytes);
|
||||
size = nbytes;
|
||||
}
|
||||
|
||||
if (nbytes == 1)
|
||||
{
|
||||
md_number_to_chars (p, (valueT) generic_bignum[0], 1);
|
||||
return;
|
||||
}
|
||||
know (nbytes % CHARS_PER_LITTLENUM == 0);
|
||||
|
||||
if (target_big_endian)
|
||||
{
|
||||
while (nbytes > size)
|
||||
|
@ -366,7 +366,7 @@ snmp_pdu_decrypt(const struct snmp_pdu *pdu)
|
||||
return (SNMP_CODE_OK);
|
||||
}
|
||||
|
||||
int
|
||||
enum snmp_code
|
||||
snmp_passwd_to_keys(struct snmp_user *user, char *passwd __unused)
|
||||
{
|
||||
if (user->auth_proto == SNMP_AUTH_NOAUTH &&
|
||||
@ -378,7 +378,7 @@ snmp_passwd_to_keys(struct snmp_user *user, char *passwd __unused)
|
||||
return (SNMP_CODE_FAILED);
|
||||
}
|
||||
|
||||
int
|
||||
enum snmp_code
|
||||
snmp_get_local_keys(struct snmp_user *user, uint8_t *eid __unused,
|
||||
uint32_t elen __unused)
|
||||
{
|
||||
|
@ -1,4 +1,3 @@
|
||||
.PU
|
||||
.TH bzip2 1
|
||||
.SH NAME
|
||||
bzip2, bunzip2 \- a block-sorting file compressor, v1.0.6
|
||||
|
@ -7,7 +7,7 @@
|
||||
.\" $Header: /home/hugh/sources/old_ae/RCS/ee.1,v 1.22 2001/12/16 04:49:27 hugh Exp $
|
||||
.\"
|
||||
.\"
|
||||
.TH ee 1 "" "" "" ""
|
||||
.TH ee 1 "" "" ""
|
||||
.SH NAME
|
||||
ee \- easy editor
|
||||
.SH SYNOPSIS
|
||||
|
@ -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 $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -770,6 +770,8 @@ _ELF_DEFINE_EM(EM_ETPU, 178, \
|
||||
"Freescale Extended Time Processing Unit") \
|
||||
_ELF_DEFINE_EM(EM_SLE9X, 179, \
|
||||
"Infineon Technologies SLE9X core") \
|
||||
_ELF_DEFINE_EM(EM_AARCH64, 183, \
|
||||
"AArch64 (64-bit ARM)") \
|
||||
_ELF_DEFINE_EM(EM_AVR32, 185, \
|
||||
"Atmel Corporation 32-bit microprocessor family") \
|
||||
_ELF_DEFINE_EM(EM_STM8, 186, \
|
||||
@ -819,7 +821,8 @@ enum {
|
||||
EM__LAST__
|
||||
};
|
||||
|
||||
/* Older synonyms. */
|
||||
/* Other synonyms. */
|
||||
#define EM_AMD64 EM_X86_64
|
||||
#define EM_ARC_A5 EM_ARC_COMPACT
|
||||
|
||||
/*
|
||||
@ -2112,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() \
|
||||
@ -2364,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;
|
||||
|
||||
@ -2453,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. */
|
||||
|
@ -23,7 +23,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id: elfcopy.h 2970 2013-12-01 15:22:12Z kaiwang27 $
|
||||
* $Id: elfcopy.h 3134 2014-12-23 10:43:59Z kaiwang27 $
|
||||
*/
|
||||
|
||||
#include <sys/queue.h>
|
||||
@ -115,6 +115,7 @@ struct segment;
|
||||
/* Internal data structure for sections. */
|
||||
struct section {
|
||||
struct segment *seg; /* containing segment */
|
||||
struct segment *seg_tls; /* tls segment */
|
||||
const char *name; /* section name */
|
||||
char *newname; /* new section name */
|
||||
Elf_Scn *is; /* input scn */
|
||||
|
@ -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
|
||||
{
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*-
|
||||
* Copyright (c) 2007-2011 Kai Wang
|
||||
* Copyright (c) 2007-2011,2014 Kai Wang
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -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 3134 2014-12-23 10:43:59Z 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);
|
||||
|
||||
@ -477,7 +485,10 @@ insert_shtab(struct elfcopy *ecp, int tail)
|
||||
if ((shtab = calloc(1, sizeof(*shtab))) == NULL)
|
||||
errx(EXIT_FAILURE, "calloc failed");
|
||||
if (!tail) {
|
||||
/* shoff of input object is used as a hint. */
|
||||
/*
|
||||
* "shoff" of input object is used as a hint for section
|
||||
* resync later.
|
||||
*/
|
||||
if (gelf_getehdr(ecp->ein, &ieh) == NULL)
|
||||
errx(EXIT_FAILURE, "gelf_getehdr() failed: %s",
|
||||
elf_errmsg(-1));
|
||||
@ -756,14 +767,23 @@ resync_sections(struct elfcopy *ecp)
|
||||
first = 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Ignore TLS sections with load address 0 and without
|
||||
* content. We don't need to adjust their file offset or
|
||||
* VMA, only the size matters.
|
||||
*/
|
||||
if (s->seg_tls != NULL && s->type == SHT_NOBITS &&
|
||||
s->off == 0)
|
||||
continue;
|
||||
|
||||
/* Align section offset. */
|
||||
if (off <= s->off) {
|
||||
if (!s->loadable)
|
||||
s->off = roundup(off, s->align);
|
||||
} else {
|
||||
if (s->loadable)
|
||||
warnx("moving loadable section,"
|
||||
"is this intentional?");
|
||||
warnx("moving loadable section %s, "
|
||||
"is this intentional?", s->name);
|
||||
s->off = roundup(off, s->align);
|
||||
}
|
||||
|
||||
@ -1042,6 +1062,17 @@ copy_data(struct section *s)
|
||||
od->d_size = id->d_size;
|
||||
od->d_version = id->d_version;
|
||||
}
|
||||
|
||||
/*
|
||||
* Alignment Fixup. libelf does not allow the alignment for
|
||||
* Elf_Data descriptor to be set to 0. In this case we workaround
|
||||
* it by setting the alignment to 1.
|
||||
*
|
||||
* According to the ELF ABI, alignment 0 and 1 has the same
|
||||
* meaning: the section has no alignment constraints.
|
||||
*/
|
||||
if (od->d_align == 0)
|
||||
od->d_align = 1;
|
||||
}
|
||||
|
||||
struct section *
|
||||
@ -1139,12 +1170,6 @@ add_to_shstrtab(struct elfcopy *ecp, const char *name)
|
||||
struct section *s;
|
||||
|
||||
s = ecp->shstrtab;
|
||||
if (s->buf == NULL) {
|
||||
insert_to_strtab(s, "");
|
||||
insert_to_strtab(s, ".symtab");
|
||||
insert_to_strtab(s, ".strtab");
|
||||
insert_to_strtab(s, ".shstrtab");
|
||||
}
|
||||
insert_to_strtab(s, name);
|
||||
}
|
||||
|
||||
@ -1206,6 +1231,11 @@ init_shstrtab(struct elfcopy *ecp)
|
||||
s->loadable = 0;
|
||||
s->type = SHT_STRTAB;
|
||||
s->vma = 0;
|
||||
|
||||
insert_to_strtab(s, "");
|
||||
insert_to_strtab(s, ".symtab");
|
||||
insert_to_strtab(s, ".strtab");
|
||||
insert_to_strtab(s, ".shstrtab");
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -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 3134 2014-12-23 10:43:59Z kaiwang27 $");
|
||||
|
||||
static void insert_to_inseg_list(struct segment *seg, struct section *sec);
|
||||
|
||||
@ -73,17 +73,21 @@ 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)
|
||||
s->seg = seg;
|
||||
else if (seg->type == PT_TLS)
|
||||
s->seg_tls = seg;
|
||||
s->lma = seg->addr + (s->off - seg->off);
|
||||
loadable = 1;
|
||||
}
|
||||
@ -97,7 +101,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 +118,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 3135 2014-12-24 08:22:43Z kaiwang27 $");
|
||||
|
||||
/* Symbol table buffer structure. */
|
||||
struct symbuf {
|
||||
@ -46,12 +46,25 @@ struct symbuf {
|
||||
size_t gcap, lcap; /* buffer capacities. */
|
||||
};
|
||||
|
||||
struct sthash {
|
||||
LIST_ENTRY(sthash) sh_next;
|
||||
size_t sh_off;
|
||||
};
|
||||
typedef LIST_HEAD(,sthash) hash_head;
|
||||
#define STHASHSIZE 65536
|
||||
|
||||
struct strimpl {
|
||||
char *buf; /* string table */
|
||||
size_t sz; /* entries */
|
||||
size_t cap; /* buffer capacity */
|
||||
hash_head hash[STHASHSIZE];
|
||||
};
|
||||
|
||||
|
||||
/* String table buffer structure. */
|
||||
struct strbuf {
|
||||
char *l; /* local symbol string table */
|
||||
char *g; /* global symbol string table */
|
||||
size_t lsz, gsz; /* size of each kind */
|
||||
size_t gcap, lcap; /* buffer capacities. */
|
||||
struct strimpl l; /* local symbols */
|
||||
struct strimpl g; /* global symbols */
|
||||
};
|
||||
|
||||
static int is_debug_symbol(unsigned char st_info);
|
||||
@ -62,10 +75,12 @@ static int is_needed_symbol(struct elfcopy *ecp, int i, GElf_Sym *s);
|
||||
static int is_remove_symbol(struct elfcopy *ecp, size_t sc, int i,
|
||||
GElf_Sym *s, const char *name);
|
||||
static int is_weak_symbol(unsigned char st_info);
|
||||
static int lookup_exact_string(const char *buf, size_t sz, const char *s);
|
||||
static int lookup_exact_string(hash_head *hash, const char *buf,
|
||||
const char *s);
|
||||
static int generate_symbols(struct elfcopy *ecp);
|
||||
static void mark_symbols(struct elfcopy *ecp, size_t sc);
|
||||
static int match_wildcard(const char *name, const char *pattern);
|
||||
uint32_t str_hash(const char *s);
|
||||
|
||||
/* Convenient bit vector operation macros. */
|
||||
#define BIT_SET(v, n) (v[(n)>>3] |= 1U << ((n) & 7))
|
||||
@ -300,7 +315,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)
|
||||
@ -316,11 +331,10 @@ generate_symbols(struct elfcopy *ecp)
|
||||
if ((st_buf = calloc(1, sizeof(*st_buf))) == NULL)
|
||||
err(EXIT_FAILURE, "calloc failed");
|
||||
sy_buf->gcap = sy_buf->lcap = 64;
|
||||
st_buf->gcap = 256;
|
||||
st_buf->lcap = 64;
|
||||
st_buf->lsz = 1; /* '\0' at start. */
|
||||
st_buf->gsz = 0;
|
||||
nsyms = 0;
|
||||
st_buf->g.cap = 256;
|
||||
st_buf->l.cap = 64;
|
||||
st_buf->l.sz = 1; /* '\0' at start. */
|
||||
st_buf->g.sz = 0;
|
||||
|
||||
ecp->symtab->sz = 0;
|
||||
ecp->strtab->sz = 0;
|
||||
@ -542,10 +556,10 @@ generate_symbols(struct elfcopy *ecp)
|
||||
/* Update st_name. */
|
||||
if (ec == ELFCLASS32)
|
||||
sy_buf->g32[ecp->symndx[i]].st_name +=
|
||||
st_buf->lsz;
|
||||
st_buf->l.sz;
|
||||
else
|
||||
sy_buf->g64[ecp->symndx[i]].st_name +=
|
||||
st_buf->lsz;
|
||||
st_buf->l.sz;
|
||||
|
||||
/* Update index map. */
|
||||
ecp->symndx[i] += sy_buf->nls;
|
||||
@ -634,6 +648,8 @@ free_symtab(struct elfcopy *ecp)
|
||||
{
|
||||
struct symbuf *sy_buf;
|
||||
struct strbuf *st_buf;
|
||||
struct sthash *sh, *shtmp;
|
||||
int i;
|
||||
|
||||
if (ecp->symtab != NULL && ecp->symtab->buf != NULL) {
|
||||
sy_buf = ecp->symtab->buf;
|
||||
@ -649,10 +665,22 @@ free_symtab(struct elfcopy *ecp)
|
||||
|
||||
if (ecp->strtab != NULL && ecp->strtab->buf != NULL) {
|
||||
st_buf = ecp->strtab->buf;
|
||||
if (st_buf->l != NULL)
|
||||
free(st_buf->l);
|
||||
if (st_buf->g != NULL)
|
||||
free(st_buf->g);
|
||||
if (st_buf->l.buf != NULL)
|
||||
free(st_buf->l.buf);
|
||||
if (st_buf->g.buf != NULL)
|
||||
free(st_buf->g.buf);
|
||||
for (i = 0; i < STHASHSIZE; i++) {
|
||||
LIST_FOREACH_SAFE(sh, &st_buf->l.hash[i], sh_next,
|
||||
shtmp) {
|
||||
LIST_REMOVE(sh, sh_next);
|
||||
free(sh);
|
||||
}
|
||||
LIST_FOREACH_SAFE(sh, &st_buf->g.hash[i], sh_next,
|
||||
shtmp) {
|
||||
LIST_REMOVE(sh, sh_next);
|
||||
free(sh);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -690,10 +718,10 @@ create_external_symtab(struct elfcopy *ecp)
|
||||
if ((st_buf = calloc(1, sizeof(*st_buf))) == NULL)
|
||||
err(EXIT_FAILURE, "calloc failed");
|
||||
sy_buf->gcap = sy_buf->lcap = 64;
|
||||
st_buf->gcap = 256;
|
||||
st_buf->lcap = 64;
|
||||
st_buf->lsz = 1; /* '\0' at start. */
|
||||
st_buf->gsz = 0;
|
||||
st_buf->g.cap = 256;
|
||||
st_buf->l.cap = 64;
|
||||
st_buf->l.sz = 1; /* '\0' at start. */
|
||||
st_buf->g.sz = 0;
|
||||
|
||||
ecp->symtab->sz = 0;
|
||||
ecp->strtab->sz = 0;
|
||||
@ -730,6 +758,8 @@ add_to_symtab(struct elfcopy *ecp, const char *name, uint64_t st_value,
|
||||
{
|
||||
struct symbuf *sy_buf;
|
||||
struct strbuf *st_buf;
|
||||
struct sthash *sh;
|
||||
uint32_t hash;
|
||||
int pos;
|
||||
|
||||
/*
|
||||
@ -762,32 +792,39 @@ add_to_symtab(struct elfcopy *ecp, const char *name, uint64_t st_value,
|
||||
else \
|
||||
sy_buf->B##SZ[sy_buf->n##B##s].st_shndx = \
|
||||
ecp->secndx[st_shndx]; \
|
||||
if (st_buf->B == NULL) { \
|
||||
st_buf->B = calloc(st_buf->B##cap, sizeof(*st_buf->B)); \
|
||||
if (st_buf->B == NULL) \
|
||||
if (st_buf->B.buf == NULL) { \
|
||||
st_buf->B.buf = calloc(st_buf->B.cap, \
|
||||
sizeof(*st_buf->B.buf)); \
|
||||
if (st_buf->B.buf == NULL) \
|
||||
err(EXIT_FAILURE, "malloc failed"); \
|
||||
} \
|
||||
if (name != NULL && *name != '\0') { \
|
||||
pos = lookup_exact_string(st_buf->B, \
|
||||
st_buf->B##sz, name); \
|
||||
pos = lookup_exact_string(st_buf->B.hash, st_buf->B.buf,\
|
||||
name); \
|
||||
if (pos != -1) \
|
||||
sy_buf->B##SZ[sy_buf->n##B##s].st_name = pos; \
|
||||
else { \
|
||||
sy_buf->B##SZ[sy_buf->n##B##s].st_name = \
|
||||
st_buf->B##sz; \
|
||||
while (st_buf->B##sz + strlen(name) >= \
|
||||
st_buf->B##cap - 1) { \
|
||||
st_buf->B##cap *= 2; \
|
||||
st_buf->B = realloc(st_buf->B, \
|
||||
st_buf->B##cap); \
|
||||
if (st_buf->B == NULL) \
|
||||
st_buf->B.sz; \
|
||||
while (st_buf->B.sz + strlen(name) >= \
|
||||
st_buf->B.cap - 1) { \
|
||||
st_buf->B.cap *= 2; \
|
||||
st_buf->B.buf = realloc(st_buf->B.buf, \
|
||||
st_buf->B.cap); \
|
||||
if (st_buf->B.buf == NULL) \
|
||||
err(EXIT_FAILURE, \
|
||||
"realloc failed"); \
|
||||
} \
|
||||
strncpy(&st_buf->B[st_buf->B##sz], name, \
|
||||
if ((sh = malloc(sizeof(*sh))) == NULL) \
|
||||
err(EXIT_FAILURE, "malloc failed"); \
|
||||
sh->sh_off = st_buf->B.sz; \
|
||||
hash = str_hash(name); \
|
||||
LIST_INSERT_HEAD(&st_buf->B.hash[hash], sh, \
|
||||
sh_next); \
|
||||
strncpy(&st_buf->B.buf[st_buf->B.sz], name, \
|
||||
strlen(name)); \
|
||||
st_buf->B[st_buf->B##sz + strlen(name)] = '\0'; \
|
||||
st_buf->B##sz += strlen(name) + 1; \
|
||||
st_buf->B.buf[st_buf->B.sz + strlen(name)] = '\0'; \
|
||||
st_buf->B.sz += strlen(name) + 1; \
|
||||
} \
|
||||
} else \
|
||||
sy_buf->B##SZ[sy_buf->n##B##s].st_name = 0; \
|
||||
@ -812,7 +849,7 @@ add_to_symtab(struct elfcopy *ecp, const char *name, uint64_t st_value,
|
||||
/* Update section size. */
|
||||
ecp->symtab->sz = (sy_buf->nls + sy_buf->ngs) *
|
||||
(ecp->oec == ELFCLASS32 ? sizeof(Elf32_Sym) : sizeof(Elf64_Sym));
|
||||
ecp->strtab->sz = st_buf->lsz + st_buf->gsz;
|
||||
ecp->strtab->sz = st_buf->l.sz + st_buf->g.sz;
|
||||
|
||||
#undef _ADDSYM
|
||||
}
|
||||
@ -832,9 +869,9 @@ finalize_external_symtab(struct elfcopy *ecp)
|
||||
st_buf = ecp->strtab->buf;
|
||||
for (i = 0; (size_t) i < sy_buf->ngs; i++) {
|
||||
if (ecp->oec == ELFCLASS32)
|
||||
sy_buf->g32[i].st_name += st_buf->lsz;
|
||||
sy_buf->g32[i].st_name += st_buf->l.sz;
|
||||
else
|
||||
sy_buf->g64[i].st_name += st_buf->lsz;
|
||||
sy_buf->g64[i].st_name += st_buf->l.sz;
|
||||
}
|
||||
}
|
||||
|
||||
@ -921,19 +958,19 @@ create_symtab_data(struct elfcopy *ecp)
|
||||
elf_errmsg(-1));
|
||||
lstdata->d_align = 1;
|
||||
lstdata->d_off = 0;
|
||||
lstdata->d_buf = st_buf->l;
|
||||
lstdata->d_size = st_buf->lsz;
|
||||
lstdata->d_buf = st_buf->l.buf;
|
||||
lstdata->d_size = st_buf->l.sz;
|
||||
lstdata->d_type = ELF_T_BYTE;
|
||||
lstdata->d_version = EV_CURRENT;
|
||||
|
||||
if (st_buf->gsz > 0) {
|
||||
if (st_buf->g.sz > 0) {
|
||||
if ((gstdata = elf_newdata(st->os)) == NULL)
|
||||
errx(EXIT_FAILURE, "elf_newdata() failed: %s.",
|
||||
elf_errmsg(-1));
|
||||
gstdata->d_align = 1;
|
||||
gstdata->d_off = lstdata->d_size;
|
||||
gstdata->d_buf = st_buf->g;
|
||||
gstdata->d_size = st_buf->gsz;
|
||||
gstdata->d_buf = st_buf->g.buf;
|
||||
gstdata->d_size = st_buf->g.sz;
|
||||
gstdata->d_type = ELF_T_BYTE;
|
||||
gstdata->d_version = EV_CURRENT;
|
||||
}
|
||||
@ -1023,18 +1060,25 @@ lookup_symop_list(struct elfcopy *ecp, const char *name, unsigned int op)
|
||||
}
|
||||
|
||||
static int
|
||||
lookup_exact_string(const char *buf, size_t sz, const char *s)
|
||||
lookup_exact_string(hash_head *buckets, const char *buf, const char *s)
|
||||
{
|
||||
const char *b;
|
||||
size_t slen;
|
||||
|
||||
slen = strlen(s);
|
||||
for (b = buf; b < buf + sz; b += strlen(b) + 1) {
|
||||
if (strlen(b) != slen)
|
||||
continue;
|
||||
if (!strcmp(b, s))
|
||||
return (b - buf);
|
||||
}
|
||||
struct sthash *sh;
|
||||
uint32_t hash;
|
||||
|
||||
hash = str_hash(s);
|
||||
LIST_FOREACH(sh, &buckets[hash], sh_next)
|
||||
if (strcmp(buf + sh->sh_off, s) == 0)
|
||||
return sh->sh_off;
|
||||
return (-1);
|
||||
}
|
||||
|
||||
uint32_t
|
||||
str_hash(const char *s)
|
||||
{
|
||||
uint32_t hash;
|
||||
|
||||
for (hash = 2166136261; *s; s++)
|
||||
hash = (hash ^ *s) * 16777619;
|
||||
|
||||
return (hash & (STHASHSIZE - 1));
|
||||
}
|
||||
|
@ -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);
|
||||
|
||||
|
@ -247,6 +247,7 @@ constants.
|
||||
.It Fn dwarf_get_VIS_name
|
||||
.Dv DW_VIS_*
|
||||
constants.
|
||||
.El
|
||||
.Sh RETURN VALUES
|
||||
These functions return
|
||||
.Dv DW_DLV_OK on success.
|
||||
|
@ -102,6 +102,7 @@ One of the arguments
|
||||
or
|
||||
.Ar cu_die_offset
|
||||
was NULL.
|
||||
.El
|
||||
.Sh EXAMPLE
|
||||
To loop through all the address lookup table entries, use:
|
||||
.Bd -literal -offset indent
|
||||
|
@ -1,4 +1,4 @@
|
||||
.\" Copyright (c) 2010, Joerg Wunsch
|
||||
.\" Copyright (c) 2014 Kai Wang
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
@ -22,34 +22,52 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $FreeBSD$
|
||||
.\" $Id: dwarf_get_die_infotypes_flag.3 3118 2014-12-20 20:30:06Z jkoshy $
|
||||
.\"
|
||||
.Dd January 24, 2010
|
||||
.Dt TNT4882 4
|
||||
.Dd December 20, 2014
|
||||
.Os
|
||||
.Dt DWARF_GET_DIE_INFOTYPES_FLAG 3
|
||||
.Sh NAME
|
||||
.Nm tnt4882
|
||||
.Nd National Instruments TNT4882A GPIB controller driver
|
||||
.Nm dwarf_get_die_infotypes_flag
|
||||
.Nd indicate the originating DWARF section for a DIE
|
||||
.Sh LIBRARY
|
||||
.Lb libdwarf
|
||||
.Sh SYNOPSIS
|
||||
.Cd "device tnt4882"
|
||||
.In libdwarf.h
|
||||
.Ft Dwarf_Bool
|
||||
.Fo dwarf_get_die_infotypes_flag
|
||||
.Fa "Dwarf_Die die"
|
||||
.Fc
|
||||
.Sh DESCRIPTION
|
||||
The
|
||||
.Nm
|
||||
driver provides support for driving an IEEE-488 bus, also called
|
||||
IEC-625 (or just "IEC bus"), or HP-IB (Hewlett Packard Instrument
|
||||
Bus), or GPIB (General Purpose Instrument Bus).
|
||||
The driver supports National Instruments PCI GPIB cards using
|
||||
the TNT4882 bus interface chip.
|
||||
This chip emulates a NEC \(mcPD7210 controller IC as the main
|
||||
interface between the host computer and the instrument bus.
|
||||
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 gpib 3 ,
|
||||
.Xr gpib 4
|
||||
.Sh HISTORY
|
||||
The
|
||||
.Nm
|
||||
driver was written by Poul-Henning Kamp, and first appeared in
|
||||
.Fx 5.4 .
|
||||
.Sh AUTHORS
|
||||
This manual page was written by
|
||||
.An J\(:org Wunsch .
|
||||
.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
|
@ -85,6 +85,7 @@ Either of argument
|
||||
or
|
||||
.Va ret_bool
|
||||
was NULL.
|
||||
.El
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_attr 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));
|
||||
}
|
@ -72,6 +72,7 @@ Either of argument
|
||||
or
|
||||
.Va retcode
|
||||
was NULL.
|
||||
.El
|
||||
.Sh SEE ALSO
|
||||
.Xr dwarf 3 ,
|
||||
.Xr dwarf_attr 3 ,
|
||||
|
@ -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 *,
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#include "_libdwarf.h"
|
||||
|
||||
ELFTC_VCSID("$Id: libdwarf_abbrev.c 2070 2011-10-27 03:05:32Z jkoshy $");
|
||||
ELFTC_VCSID("$Id: libdwarf_abbrev.c 3136 2014-12-24 16:04:38Z kaiwang27 $");
|
||||
|
||||
int
|
||||
_dwarf_abbrev_add(Dwarf_CU cu, uint64_t entry, uint64_t tag, uint8_t children,
|
||||
@ -180,7 +180,9 @@ _dwarf_abbrev_find(Dwarf_CU cu, uint64_t entry, Dwarf_Abbrev *abp,
|
||||
|
||||
/* Load and search the abbrev table. */
|
||||
ds = _dwarf_find_section(cu->cu_dbg, ".debug_abbrev");
|
||||
assert(ds != NULL);
|
||||
if (ds == NULL)
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
|
||||
offset = cu->cu_abbrev_offset_cur;
|
||||
while (offset < ds->ds_size) {
|
||||
ret = _dwarf_abbrev_parse(cu->cu_dbg, cu, &offset, &ab, error);
|
||||
|
@ -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 @@ _dwarf_frame_section_init(Dwarf_Debug dbg, Dwarf_FrameSec *frame_sec,
|
||||
}
|
||||
|
||||
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 @@ _dwarf_frame_run_inst(Dwarf_Debug dbg, Dwarf_Regtable3 *rt, uint8_t *insts,
|
||||
}
|
||||
|
||||
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 3136 2014-12-24 16:04:38Z 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,23 @@ _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;
|
||||
if (ds == NULL)
|
||||
return (DW_DLE_NO_ENTRY);
|
||||
} 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 +171,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 +195,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 +210,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 +239,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 +266,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 3136 2014-12-24 16:04:38Z 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,13 +91,12 @@ _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")) ==
|
||||
NULL)) {
|
||||
DWARF_SET_ERROR(dbg, error, DW_DLE_DEBUG_INFO_NULL);
|
||||
return (DW_DLE_DEBUG_INFO_NULL);
|
||||
}
|
||||
dbg->dbg_info_sec = _dwarf_find_section(dbg, ".debug_info");
|
||||
|
||||
/* 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 +210,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 +270,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,13 +388,31 @@ 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
|
||||
.TE
|
||||
.Pp
|
||||
Section types in the range
|
||||
.Ns [ Dv SHT_LOOS ,
|
||||
.Dv SHT_HIUSER ]
|
||||
are otherwise considered to be of type
|
||||
.Dv ELF_T_BYTE .
|
||||
.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);
|
||||
}
|
||||
|
@ -32,11 +32,12 @@
|
||||
#include <gelf.h>
|
||||
#include <libelf.h>
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#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 +45,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);
|
||||
@ -59,7 +61,8 @@ _libelf_load_section_headers(Elf *e, void *ehdr)
|
||||
|
||||
#define CHECK_EHDR(E,EH) do { \
|
||||
if (fsz != (EH)->e_shentsize || \
|
||||
shoff + fsz * shnum > e->e_rawsize) { \
|
||||
shnum > SIZE_MAX / fsz || \
|
||||
fsz * shnum > e->e_rawsize - shoff) { \
|
||||
LIBELF_SET_ERROR(HEADER, 0); \
|
||||
return (0); \
|
||||
} \
|
||||
@ -104,8 +107,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 @@ _libelf_compute_section_extents(Elf *e, Elf_Scn *s, off_t rc)
|
||||
* 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"
|
||||
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user