build shared versions of libraries

building defaults to off until clang is updated.

current clang does not handle -shared, necessary to change the ld
invocation to build shared libraries properly. a new clang should be
installed and MKPIC defaults to no unless the newer clang is detected.

changes:

	. mainly small imports of a Makefile or two and small fixes
	  (turning things back on that were turned off in Makefiles)
	. e.g.: dynamic librefuse now depends on dynamic
	  libpuffs, so libpuffs has to be built dynamically too
	  and a make dependency barrier is needed in lib/Makefile
	. all library objects now have a PIC (for .so) and non-PIC
	  version, so everything is built twice.
	. generate PIC versions of the compat (un-RENAMEd) jump files,
	  include function type annotation in generated assembly
	. build progs with -static by default for now
	. also build ld.elf_so
	. also import NetBSD ldd
This commit is contained in:
Ben Gras 2012-03-31 02:28:03 +02:00
parent 53002f6f6c
commit 4b999f1962
49 changed files with 1051 additions and 53 deletions

2
.gitignore vendored
View file

@ -10,7 +10,9 @@ cscope.*
*.[1-9].gz *.[1-9].gz
*.o *.o
*.[psS]o *.[psS]o
lib*.so*
*.a *.a
*.so.*
*.d *.d
.depend .depend
nbsdsrc/* nbsdsrc/*

View file

@ -4,7 +4,7 @@ FILESDIR= /usr/lib/keymaps
.src.map: .src.map:
${_MKTARGET_CREATE} ${_MKTARGET_CREATE}
$(CC) -DKEYSRC=\"$<\" -o $<_genmap ${.CURDIR}/genmap.c $(CC) $(LDFLAGS) -DKEYSRC=\"$<\" -o $<_genmap ${.CURDIR}/genmap.c
./$<_genmap > $@ ./$<_genmap > $@
@rm -f $<_genmap @rm -f $<_genmap

View file

@ -1,5 +1,7 @@
755 root operator / 755 root operator /
755 root operator /bin 755 root operator /bin
755 root operator /lib
755 root operator /libexec
755 root operator /sbin 755 root operator /sbin
755 root operator /dev 755 root operator /dev
/dev/mouse -> /dev/kbdaux /dev/mouse -> /dev/kbdaux

View file

@ -1,13 +1,23 @@
.include <bsd.own.mk> .include <bsd.own.mk>
SUBDIR= csu libcompat_minix libc libblockdriver libchardriver \ SUBDIR= csu
SUBDIR+= .WAIT
SUBDIR+= libc
SUBDIR+= .WAIT
SUBDIR+= libcompat_minix libc libblockdriver libchardriver \
libnetdriver libedit libm libsys libtimers libutil \ libnetdriver libedit libm libsys libtimers libutil \
libl libz libfetch libvtreefs libaudiodriver libmthread \ libl libz libfetch libvtreefs libaudiodriver libmthread \
libexec libdevman libusb libminlib libasyn \ libexec libdevman libusb libminlib libasyn \
libddekit libminixfs libbdev libelf libminc libcrypt libterminfo \ libddekit libminixfs libbdev libelf libminc libcrypt libterminfo \
libcurses libvassert libutil libpuffs librefuse libbz2 libarchive \ libvassert libutil libbz2 libarchive libprop \
libprop libnetsock libsffs libhgfs libvboxfs libnetsock libpuffs libsffs libhgfs libvboxfs
SUBDIR+= ../external/public-domain/xz/lib SUBDIR+= ../external/public-domain/xz/lib
# libraries that follow depend on earlier ones
SUBDIR+= .WAIT
SUBDIR+= librefuse
SUBDIR+= libcurses
.include <bsd.subdir.mk> .include <bsd.subdir.mk>

20
lib/generateasm.mk Normal file
View file

@ -0,0 +1,20 @@
${ASM}:
${_MKTARGET_CREATE}
printf '/* MINIX3 */ \n\
/* \n\
* Compatibility jump table for renamed symbols. \n\
* \n\
* DO NOT EDIT: this file is automatically generated. \n\
*/ \n\
#include <machine/asm.h> \n\
.global ${.PREFIX:S/^compat__//:C/([0-9]{2})$//}; \n\
.global ${.PREFIX:S/^compat//}; \n\
.type ${.PREFIX:S/^compat__//:C/([0-9]{2})$//},@function \n\
${.PREFIX:S/^compat__//:C/([0-9]{2})$//}: \n\
#ifdef PIC \n\
jmpl *PIC_PLT(${.PREFIX:S/^compat//}) \n\
#else \n\
jmp ${.PREFIX:S/^compat//} \n\
#endif \n\
\n ' >${.TARGET}

View file

@ -159,9 +159,9 @@ FILESDIR= /var/db
# workaround for I18N stuffs: build singlebyte setlocale() for libc.a, # workaround for I18N stuffs: build singlebyte setlocale() for libc.a,
# multibyte for libc.so. the quirk should be removed when we support # multibyte for libc.so. the quirk should be removed when we support
# dlopen() from within statically linked binaries. # dlopen() from within statically linked binaries.
.if (${CITRUS} == "yes") #.if (${CITRUS} == "yes")
CSHLIBFLAGS+= -D_I18N_DYNAMIC #CSHLIBFLAGS+= -D_I18N_DYNAMIC
.endif #.endif
.include <bsd.lib.mk> .include <bsd.lib.mk>

View file

@ -19,11 +19,7 @@
USE_FORT?= yes USE_FORT?= yes
.if defined(__MINIX)
USE_SHLIBDIR= no
.else
USE_SHLIBDIR= yes USE_SHLIBDIR= yes
.endif
CITRUS?= yes CITRUS?= yes

View file

@ -11,7 +11,7 @@ ASM= compat__opendir230.S compat__alphasort30.S compat__ctime50.S \
compat__getutmp50.S compat__getutmpx50.S compat__getutxent50.S \ compat__getutmp50.S compat__getutmpx50.S compat__getutxent50.S \
compat__getutxid50.S compat__getutxline50.S compat__glob30.S \ compat__getutxid50.S compat__getutxline50.S compat__glob30.S \
compat__globfree30.S compat__gmtime50.S compat__gmtime_r50.S \ compat__globfree30.S compat__gmtime50.S compat__gmtime_r50.S \
compat__localtime50.S compat__localtime_r50.S compat__localtime_rz50.S \ compat__localtime_r50.S compat__localtime_rz50.S \
compat__longjmp14.S compat__mknod50.S compat__mktime50.S \ compat__longjmp14.S compat__mknod50.S compat__mktime50.S \
compat__mktime_z50.S compat__nanosleep50.S compat__offtime50.S \ compat__mktime_z50.S compat__nanosleep50.S compat__offtime50.S \
compat__offtime_r50.S compat__opendir30.S compat__posix2time50.S \ compat__offtime_r50.S compat__opendir30.S compat__posix2time50.S \
@ -33,7 +33,5 @@ ASM= compat__opendir230.S compat__alphasort30.S compat__ctime50.S \
compat__vfork14.S compat__vfork14.S
SRCS+= ${ASM} SRCS+= ${ASM}
${ASM}: .include "../generateasm.mk"
${_MKTARGET_CREATE}
printf '/* MINIX3 */\n\n/*\n * Compatibility jump table for renamed symbols.\n *\n * DO NOT EDIT: this file is automatically generated.\n */\n.global ${.PREFIX:S/^compat__//:C/([0-9]{2})$//};\n.global ${.PREFIX:S/^compat//};\n${.PREFIX:S/^compat__//:C/([0-9]{2})$//}: jmp ${.PREFIX:S/^compat//}\n' >${.TARGET}

View file

@ -48,12 +48,7 @@ __RCSID("$NetBSD: dlfcn_elf.c,v 1.7 2010/10/16 10:27:07 skrll Exp $");
#define dl_iterate_phdr ___dl_iterate_phdr #define dl_iterate_phdr ___dl_iterate_phdr
#define ELFSIZE ARCH_ELFSIZE #define ELFSIZE ARCH_ELFSIZE
#ifdef __minix
#include <sys/null.h>
#include <dlfcn.h>
#else
#include "rtld.h" #include "rtld.h"
#endif
#ifdef __weak_alias #ifdef __weak_alias
__weak_alias(dlopen,___dlopen) __weak_alias(dlopen,___dlopen)
@ -133,7 +128,6 @@ dlinfo(void *handle, int req, void *v)
return -1; return -1;
} }
#ifndef __minix
/*ARGSUSED*/ /*ARGSUSED*/
int int
dl_iterate_phdr(int (*callback)(struct dl_phdr_info *, size_t, void *), dl_iterate_phdr(int (*callback)(struct dl_phdr_info *, size_t, void *),
@ -142,4 +136,3 @@ dl_iterate_phdr(int (*callback)(struct dl_phdr_info *, size_t, void *),
return 0; return 0;
} }
#endif

View file

@ -1,6 +1,5 @@
NETBSDSRCDIR= ${MINIXSRCDIR} NETBSDSRCDIR= ${MINIXSRCDIR}
NETBSDINCLUDES= /usr/include/ NETBSDINCLUDES= /usr/include/
MACHINE_ARCH?= i386
CITRUS=yes CITRUS=yes
USE_INET6=no USE_INET6=no

View file

@ -3,6 +3,7 @@
LIB= compat_minix LIB= compat_minix
CPPFLAGS+= -D_MINIX_COMPAT CPPFLAGS+= -D_MINIX_COMPAT
MACHINE_ARCH= ${ARCH} MACHINE_ARCH= ${ARCH}
USE_SHLIBDIR= yes
.PATH: ${.CURDIR} .PATH: ${.CURDIR}

View file

@ -0,0 +1,2 @@
major=1
minor=0

View file

@ -3,6 +3,8 @@
INCSDIR= /usr/include INCSDIR= /usr/include
LIB= minlib LIB= minlib
USE_SHLIBDIR= yes
CPPFLAGS.fslib.c+= -I${MINIXSRCDIR}/servers CPPFLAGS.fslib.c+= -I${MINIXSRCDIR}/servers
CPPFLAGS.fsversion.c+= -I${MINIXSRCDIR}/servers CPPFLAGS.fsversion.c+= -I${MINIXSRCDIR}/servers
SRCS+= fslib.c fsversion.c SRCS+= fslib.c fsversion.c

View file

@ -0,0 +1,2 @@
major=1
minor=0

View file

@ -0,0 +1,3 @@
major=1
minor=1

View file

@ -2,10 +2,8 @@
.if defined(__MINIX) .if defined(__MINIX)
.include "minix-config.inc" .include "minix-config.inc"
USE_SHLIBDIR= no
.else
USE_SHLIBDIR= yes
.endif .endif
USE_SHLIBDIR= yes
LIB= terminfo LIB= terminfo
WARNS= 4 WARNS= 4
@ -59,9 +57,7 @@ man: terminfo.5
gen: hash compiled_terms man gen: hash compiled_terms man
.include <bsd.own.mk> .include <bsd.own.mk>
.if !defined(__MINIX)
.include <bsd.shlib.mk> .include <bsd.shlib.mk>
.endif
.if ${MKLINKLIB} != "no" .if ${MKLINKLIB} != "no"
SYMLINKS+= libterminfo.a ${LIBDIR}/libtermcap.a SYMLINKS+= libterminfo.a ${LIBDIR}/libtermcap.a

View file

@ -1,10 +1,6 @@
NETBSDSRCDIR= ${MINIXSRCDIR} NETBSDSRCDIR= ${MINIXSRCDIR}
NETBSDINCLUDES= /usr/include/ NETBSDINCLUDES= /usr/include/
MACHINE_ARCH?= i386
CPPFLAGS+= -D_NETBSD_SOURCE CPPFLAGS+= -D_NETBSD_SOURCE
MKLINKLIB= yes MKLINKLIB= yes
MKPROFILE= no
MKPIC= no

View file

@ -4,7 +4,4 @@ ASM= compat__login_getpwclass50.S compat__login50.S compat__loginx50.S \
compat__pw_getpwconf50.S compat__setusercontext50.S compat__pw_getpwconf50.S compat__setusercontext50.S
SRCS+= ${ASM} SRCS+= ${ASM}
${ASM}: .include "../generateasm.mk"
${_MKTARGET_CREATE}
printf '/* MINIX3 */\n\n/*\n * Compatibility jump table for renamed symbols.\n *\n * DO NOT EDIT: this file is automatically generated.\n */\n.global ${.PREFIX:S/^compat__//:C/([0-9]{2})$//};\n.global ${.PREFIX:S/^compat//};\n${.PREFIX:S/^compat__//:C/([0-9]{2})$//}: jmp ${.PREFIX:S/^compat//}\n' >${.TARGET}

2
lib/libz/shlib_version Normal file
View file

@ -0,0 +1,2 @@
major=1
minor=0

View file

@ -3,6 +3,6 @@
.include <bsd.own.mk> .include <bsd.own.mk>
# NetBSD imports # NetBSD imports
SUBDIR= makewhatis SUBDIR= makewhatis ld.elf_so
.include <bsd.subdir.mk> .include <bsd.subdir.mk>

View file

@ -5,6 +5,12 @@
WARNS?=4 WARNS?=4
# This executable needs to be linked dynamically
MINIXDYNAMIC=yes
# And the minix gcc currently references /libexec/ld-elf.so.1
SYMLINKS+= ${SHLINKINSTALLDIR}/${PROG} /libexec/ld-elf.so.1
# This needs to be before bsd.init.mk # This needs to be before bsd.init.mk
.if defined(BSD_MK_COMPAT_FILE) .if defined(BSD_MK_COMPAT_FILE)
.include <${BSD_MK_COMPAT_FILE}> .include <${BSD_MK_COMPAT_FILE}>
@ -75,7 +81,7 @@ SRCS+= stack_protector.c
.PATH.c: ${NETBSDSRCDIR}/lib/libc/stdlib .PATH.c: ${NETBSDSRCDIR}/lib/libc/stdlib
SRCS+= exit.c SRCS+= exit.c
errlist_concat.h: ${NETBSDSRCDIR}/lib/libc/gen/errlist.awk ${NETBSDSRCDIR}/sys/sys/errno.h errlist_concat.h: ${NETBSDSRCDIR}/lib/libc/gen/errlist.awk ${NETBSDSRCDIR}/include/sys/errno.h
${TOOL_AWK} -v concat=1 -f ${.ALLSRC} > ${.TARGET}.tmp && \ ${TOOL_AWK} -v concat=1 -f ${.ALLSRC} > ${.TARGET}.tmp && \
mv -f ${.TARGET}.tmp ${.TARGET} mv -f ${.TARGET}.tmp ${.TARGET}
@ -93,8 +99,8 @@ CPPFLAGS+= -DCOMBRELOC
#CPPFLAGS+= -DDEBUG #CPPFLAGS+= -DDEBUG
#CPPFLAGS+= -DRTLD_DEBUG #CPPFLAGS+= -DRTLD_DEBUG
#CPPFLAGS+= -DRTLD_DEBUG_RELOC #CPPFLAGS+= -DRTLD_DEBUG_RELOC
#DBG= -g DBG= -g
DBG= -O3 -fomit-frame-pointer #DBG= -O3 -fomit-frame-pointer
.if ${SHLIBDIR} != ${LIBDIR} .if ${SHLIBDIR} != ${LIBDIR}
CPPFLAGS+= -DRTLD_DEFAULT_LIBRARY_PATH=\"${SHLIBDIR}:${LIBDIR}\" CPPFLAGS+= -DRTLD_DEFAULT_LIBRARY_PATH=\"${SHLIBDIR}:${LIBDIR}\"

View file

@ -62,15 +62,20 @@ static const struct {
ADD(PLATFORM) /* uname -p */ ADD(PLATFORM) /* uname -p */
}; };
#ifndef __minix
static int mib[3][2] = { static int mib[3][2] = {
{ CTL_KERN, KERN_OSTYPE }, { CTL_KERN, KERN_OSTYPE },
{ CTL_KERN, KERN_OSRELEASE }, { CTL_KERN, KERN_OSRELEASE },
{ CTL_HW, HW_MACHINE_ARCH }, { CTL_HW, HW_MACHINE_ARCH },
}; };
#endif
static size_t static size_t
expand(char *buf, const char *execname, int what, size_t bl) expand(char *buf, const char *execname, int what, size_t bl)
{ {
#ifdef __minix
return 0;
#else
const char *p, *ep; const char *p, *ep;
char *bp = buf; char *bp = buf;
size_t len; size_t len;
@ -106,6 +111,7 @@ expand(char *buf, const char *execname, int what, size_t bl)
*bp++ = *p++, bl--; *bp++ = *p++, bl--;
return bp - buf; return bp - buf;
#endif
} }

View file

@ -57,6 +57,10 @@ __RCSID("$NetBSD: load.c,v 1.42 2010/12/24 12:41:43 skrll Exp $");
#include <sys/sysctl.h> #include <sys/sysctl.h>
#include <dirent.h> #include <dirent.h>
#ifdef __minix
#define munmap minix_munmap
#endif
#include "debug.h" #include "debug.h"
#include "rtld.h" #include "rtld.h"
@ -211,6 +215,9 @@ _rtld_load_by_name(const char *name, Obj_Entry *obj, Needed_Entry **needed,
dbg(("load by name %s %p", name, x)); dbg(("load by name %s %p", name, x));
for (; x; x = x->next) { for (; x; x = x->next) {
#ifdef __minix
continue;
#else
if (strcmp(x->name, name) != 0) if (strcmp(x->name, name) != 0)
continue; continue;
@ -274,6 +281,7 @@ _rtld_load_by_name(const char *name, Obj_Entry *obj, Needed_Entry **needed,
} }
#endif
} }
if (got) if (got)

View file

@ -119,6 +119,7 @@ _rtld_map_object(const char *path, int fd, const struct stat *sb)
int nsegs; int nsegs;
caddr_t mapbase = MAP_FAILED; caddr_t mapbase = MAP_FAILED;
size_t mapsize = 0; size_t mapsize = 0;
size_t bsssize = 0;
int mapflags; int mapflags;
Elf_Off base_offset; Elf_Off base_offset;
#ifdef MAP_ALIGNED #ifdef MAP_ALIGNED
@ -367,22 +368,29 @@ _rtld_map_object(const char *path, int fd, const struct stat *sb)
goto bad; goto bad;
} }
bsssize= base_vlimit - data_vlimit;
if(bsssize > 0) {
/* Overlay the bss segment onto the proper region. */ /* Overlay the bss segment onto the proper region. */
if (mmap(mapbase + data_vlimit - base_vaddr, base_vlimit - data_vlimit, if (mmap(mapbase + data_vlimit - base_vaddr, bsssize,
data_flags, MAP_ANON | MAP_PRIVATE | MAP_FIXED, -1, 0) == data_flags, MAP_ANON | MAP_PRIVATE | MAP_FIXED, -1, 0) ==
MAP_FAILED) { MAP_FAILED) {
_rtld_error("mmap of bss failed: %s", xstrerror(errno)); _rtld_error("mmap of bss (at 0x%lx, 0x%lx bytes) failed: %s",
mapbase + data_vlimit - base_vaddr, bsssize, xstrerror(errno));
goto bad; goto bad;
} }
}
/* Unmap the gap between the text and data. */ /* Unmap the gap between the text and data. */
gap_addr = mapbase + round_up(text_vlimit - base_vaddr); gap_addr = mapbase + round_up(text_vlimit - base_vaddr);
gap_size = data_addr - gap_addr; gap_size = data_addr - gap_addr;
#ifndef __minix
if (gap_size != 0 && mprotect(gap_addr, gap_size, PROT_NONE) == -1) { if (gap_size != 0 && mprotect(gap_addr, gap_size, PROT_NONE) == -1) {
_rtld_error("mprotect of text -> data gap failed: %s", _rtld_error("mprotect of text -> data gap failed: %s",
xstrerror(errno)); xstrerror(errno));
goto bad; goto bad;
} }
#endif
#ifdef RTLD_LOADER #ifdef RTLD_LOADER
/* Clear any BSS in the last page of the data segment. */ /* Clear any BSS in the last page of the data segment. */

View file

@ -49,7 +49,9 @@ __RCSID("$NetBSD: paths.c,v 1.40 2009/05/19 20:44:52 christos Exp $");
#include <sys/gmon.h> #include <sys/gmon.h>
#include <sys/socket.h> #include <sys/socket.h>
#include <sys/mount.h> #include <sys/mount.h>
#ifndef __minix
#include <sys/mbuf.h> #include <sys/mbuf.h>
#endif
#include <sys/resource.h> #include <sys/resource.h>
#include <machine/cpu.h> #include <machine/cpu.h>
@ -336,13 +338,17 @@ void
_rtld_process_hints(const char *execname, Search_Path **path_p, _rtld_process_hints(const char *execname, Search_Path **path_p,
Library_Xform **lib_p, const char *fname) Library_Xform **lib_p, const char *fname)
{ {
#ifdef __minix
/* Minix doesn't support MAP_SHARED. */
return;
#else
int fd; int fd;
char *buf, small[128]; char *buf, small[128];
const char *b, *ep, *ptr; const char *b, *ep, *ptr;
struct stat st; struct stat st;
ssize_t sz; ssize_t sz;
Search_Path **head_p = path_p; Search_Path **head_p = path_p;
if ((fd = open(fname, O_RDONLY)) == -1) { if ((fd = open(fname, O_RDONLY)) == -1) {
/* Don't complain */ /* Don't complain */
return; return;
@ -406,8 +412,10 @@ _rtld_process_hints(const char *execname, Search_Path **path_p,
if (buf != small) if (buf != small)
(void)munmap(buf, sz); (void)munmap(buf, sz);
#endif
} }
#ifndef __minix
/* Basic name -> sysctl MIB translation */ /* Basic name -> sysctl MIB translation */
int int
_rtld_sysctl(const char *name, void *oldp, size_t *oldlen) _rtld_sysctl(const char *name, void *oldp, size_t *oldlen)
@ -476,3 +484,4 @@ bad:
xfree(result); xfree(result);
return (-1); return (-1);
} }
#endif

View file

@ -166,6 +166,7 @@ _rtld_relocate_objects(Obj_Entry *first, bool bind_now)
(long)(obj->pltrellim - obj->pltrel), (long)(obj->pltrellim - obj->pltrel),
(long)(obj->pltrelalim - obj->pltrela))); (long)(obj->pltrelalim - obj->pltrela)));
#ifndef __minix
if (obj->textrel) { if (obj->textrel) {
/* /*
* There are relocations to the write-protected text * There are relocations to the write-protected text
@ -178,9 +179,13 @@ _rtld_relocate_objects(Obj_Entry *first, bool bind_now)
return -1; return -1;
} }
} }
#endif
dbg(("doing non-PLT relocations")); dbg(("doing non-PLT relocations"));
if (_rtld_relocate_nonplt_objects(obj) < 0) if (_rtld_relocate_nonplt_objects(obj) < 0)
ok = 0; ok = 0;
#ifndef __minix
if (obj->textrel) { /* Re-protected the text segment. */ if (obj->textrel) { /* Re-protected the text segment. */
if (mprotect(obj->mapbase, obj->textsize, if (mprotect(obj->mapbase, obj->textsize,
PROT_READ | PROT_EXEC) == -1) { PROT_READ | PROT_EXEC) == -1) {
@ -189,6 +194,8 @@ _rtld_relocate_objects(Obj_Entry *first, bool bind_now)
return -1; return -1;
} }
} }
#endif
dbg(("doing lazy PLT binding")); dbg(("doing lazy PLT binding"));
if (_rtld_relocate_plt_lazy(obj) < 0) if (_rtld_relocate_plt_lazy(obj) < 0)
ok = 0; ok = 0;

View file

@ -38,6 +38,10 @@
* John Polstra <jdp@polstra.com>. * John Polstra <jdp@polstra.com>.
*/ */
#ifdef __minix
#define munmap minix_munmap
#endif
#include <sys/cdefs.h> #include <sys/cdefs.h>
#ifndef lint #ifndef lint
__RCSID("$NetBSD: rtld.c,v 1.137 2010/12/24 12:41:43 skrll Exp $"); __RCSID("$NetBSD: rtld.c,v 1.137 2010/12/24 12:41:43 skrll Exp $");

View file

@ -47,7 +47,7 @@
#if defined(_RTLD_SOURCE) #if defined(_RTLD_SOURCE)
#ifndef RTLD_DEFAULT_LIBRARY_PATH #ifndef RTLD_DEFAULT_LIBRARY_PATH
#define RTLD_DEFAULT_LIBRARY_PATH "/usr/lib" #define RTLD_DEFAULT_LIBRARY_PATH "/lib:/usr/lib:/libexec"
#endif #endif
#define _PATH_LD_HINTS "/etc/ld.so.conf" #define _PATH_LD_HINTS "/etc/ld.so.conf"

View file

@ -60,6 +60,10 @@
* SUCH DAMAGE. * SUCH DAMAGE.
*/ */
#ifdef __minix
#define munmap minix_munmap
#endif
#if defined(LIBC_SCCS) && !defined(lint) #if defined(LIBC_SCCS) && !defined(lint)
/*static char *sccsid = "from: @(#)malloc.c 5.11 (Berkeley) 2/23/91";*/ /*static char *sccsid = "from: @(#)malloc.c 5.11 (Berkeley) 2/23/91";*/
#endif /* LIBC_SCCS and not lint */ #endif /* LIBC_SCCS and not lint */
@ -409,6 +413,10 @@ mstats(char *s)
} }
#endif #endif
/* Minix mmap can do this. */
#ifdef __minix
#define mmap minix_mmap
#endif
static int static int
morepages(int n) morepages(int n)

View file

@ -8,7 +8,7 @@ FILES= bsd.dep.mk bsd.files.mk \
bsd.init.mk bsd.kinc.mk bsd.klinks.mk bsd.lib.mk \ bsd.init.mk bsd.kinc.mk bsd.klinks.mk bsd.lib.mk \
bsd.links.mk bsd.man.mk bsd.obj.mk bsd.own.mk \ bsd.links.mk bsd.man.mk bsd.obj.mk bsd.own.mk \
bsd.prog.mk bsd.subdir.mk bsd.sys.mk bsd.doc.mk \ bsd.prog.mk bsd.subdir.mk bsd.sys.mk bsd.doc.mk \
sys.mk bsd.shlib.mk sys.mk
# MINIX-specific files # MINIX-specific files
FILES+= minix.bootprog.mk minix.service.mk \ FILES+= minix.bootprog.mk minix.service.mk \

22
share/mk/bsd.gcc.mk Normal file
View file

@ -0,0 +1,22 @@
# $NetBSD: bsd.gcc.mk,v 1.3 2008/10/25 19:11:28 mrg Exp $
.if !defined(_BSD_GCC_MK_)
_BSD_GCC_MK_=1
.if defined(EXTERNAL_TOOLCHAIN)
_GCC_CRTBEGIN!= ${CC} --print-file-name=crtbegin.o
_GCC_CRTBEGINS!= ${CC} --print-file-name=crtbeginS.o
_GCC_CRTEND!= ${CC} --print-file-name=crtend.o
_GCC_CRTENDS!= ${CC} --print-file-name=crtendS.o
_GCC_CRTDIR!= dirname ${_GCC_CRTBEGIN}
_GCC_LIBGCCDIR!= dirname `${CC} --print-libgcc-file-name`
.else
_GCC_CRTBEGIN?= ${DESTDIR}/usr/lib/crtbegin.o
_GCC_CRTBEGINS?= ${DESTDIR}/usr/lib/crtbeginS.o
_GCC_CRTEND?= ${DESTDIR}/usr/lib/crtend.o
_GCC_CRTENDS?= ${DESTDIR}/usr/lib/crtendS.o
_GCC_CRTDIR?= ${DESTDIR}/usr/lib
_GCC_LIBGCCDIR?= ${DESTDIR}/usr/lib
.endif
.endif # ! defined(_BSD_GCC_MK_)

View file

@ -2,7 +2,7 @@
# @(#)bsd.lib.mk 8.3 (Berkeley) 4/22/94 # @(#)bsd.lib.mk 8.3 (Berkeley) 4/22/94
.include <bsd.init.mk> .include <bsd.init.mk>
#.include <bsd.shlib.mk> .include <bsd.shlib.mk>
#.include <bsd.gcc.mk> #.include <bsd.gcc.mk>
# Pull in <bsd.sys.mk> here so we can override its .c.o rule # Pull in <bsd.sys.mk> here so we can override its .c.o rule
.include <bsd.sys.mk> .include <bsd.sys.mk>
@ -11,11 +11,15 @@ LIBISMODULE?= no
LIBISPRIVATE?= no LIBISPRIVATE?= no
LIBISCXX?= no LIBISCXX?= no
# Some tough Minix defaults # Build shared libraries if not set to no by now
MKPROFILE:= no MKPIC?= yes
MKSTATICLIB:= yes
MKPIC:= no # If we're making a library but aren't making shared
MKLINT:= no # libraries and it's because there's a non-shared-aware clang
# installed, warn the user that that's the reason.
.if $(MKPIC) == "no" && defined(NONPICCLANG)
.warning Old clang, not building shared.
.endif
_LIB_PREFIX= lib _LIB_PREFIX= lib
@ -518,7 +522,7 @@ DPLIBC ?= ${DESTDIR}${LIBC_SO}
.else .else
LDLIBC ?= -nodefaultlibs LDLIBC ?= -nodefaultlibs
.if ${LIB} == "c" .if ${LIB} == "c"
LDADD+= -lgcc_pic #LDADD+= -lgcc_pic
.endif .endif
.endif .endif
.endif .endif

View file

@ -66,6 +66,8 @@ USE_COMPILERCRTSTUFF?= no
.endif .endif
USE_COMPILERCRTSTUFF?= yes USE_COMPILERCRTSTUFF?= yes
USE_FORT?= no
# default to GDB6 # default to GDB6
HAVE_GDB?= 6 HAVE_GDB?= 6
@ -732,6 +734,20 @@ MKBINUTILS?= ${MKBFD}
MKZFS?= yes MKZFS?= yes
.endif .endif
# Some tough Minix defaults
MKPROFILE?= no
MKSTATICLIB:= yes
MKLINT:= no
# Is a clang installed that understands what to do with -shared,
# needed to build shared libraries? If not then default to no
# to build them. (It could still be done with gcc though so MKPIC
# might be set to yes by the user.)
.if !exists(/usr/pkg/bin/clang.dynok)
NONPICCLANG= yes # Hint to other Makefiles
MKPIC?= no
.endif
# #
# MK* options which default to "yes". # MK* options which default to "yes".
# #

View file

@ -369,4 +369,10 @@ ${TARGETS}: # ensure existence
${.CURDIR}/.gitignore: Makefile ${.CURDIR}/.gitignore: Makefile
echo $(CLEANFILES) $(PROGS) | tr ' ' '\n' >${.TARGET} echo $(CLEANFILES) $(PROGS) | tr ' ' '\n' >${.TARGET}
.if defined(MINIXDYNAMIC)
LDFLAGS += -dynamic
.else
LDFLAGS += -static
.endif
.endif # HOSTPROG .endif # HOSTPROG

40
share/mk/bsd.shlib.mk Normal file
View file

@ -0,0 +1,40 @@
# $NetBSD: bsd.shlib.mk,v 1.6 2007/08/29 21:34:17 hira Exp $
.if !defined(_BSD_SHLIB_MK_)
_BSD_SHLIB_MK_=1
.if ${MKDYNAMICROOT} == "no"
SHLIBINSTALLDIR?= /usr/lib
.else
SHLIBINSTALLDIR?= /lib
.endif
.if ${MKDYNAMICROOT} == "no" || \
(${BINDIR:Ux} != "/bin" && ${BINDIR:Ux} != "/sbin" && \
${BINDIR:Ux} != "/libexec" && ${USE_SHLIBDIR:Uno} == "no")
SHLIBDIR?= /usr/lib
.else
SHLIBDIR?= /lib
.endif
.if ${USE_SHLIBDIR:Uno} != "no"
_LIBSODIR?= ${SHLIBINSTALLDIR}
.else
_LIBSODIR?= ${LIBDIR}
.endif
.if ${MKDYNAMICROOT} == "no"
SHLINKINSTALLDIR?= /usr/libexec
.else
SHLINKINSTALLDIR?= /libexec
.endif
.if ${MKDYNAMICROOT} == "no" || \
(${BINDIR:Ux} != "/bin" && ${BINDIR:Ux} != "/sbin" && \
${BINDIR:Ux} != "/libexec")
SHLINKDIR?= /usr/libexec
.else
SHLINKDIR?= /libexec
.endif
.endif # !defined(_BSD_SHLIB_MK_)

View file

@ -2,6 +2,7 @@
# Timestamp in UTC,minixpath,netbsdpath # Timestamp in UTC,minixpath,netbsdpath
# minixpath: path in Minix source tree (starting from /usr/src/) # minixpath: path in Minix source tree (starting from /usr/src/)
# netbsdpath: path in BSD source tree (starting from src/) # netbsdpath: path in BSD source tree (starting from src/)
2011/01/17 18:11:10,usr.bin/ldd
2011/01/17 18:11:10,external/bsd/file 2011/01/17 18:11:10,external/bsd/file
2011/01/17 18:11:10,lib/csu 2011/01/17 18:11:10,lib/csu
2011/01/17 18:11:10,libexec/ld.elf_so 2011/01/17 18:11:10,libexec/ld.elf_so

View file

@ -4,7 +4,8 @@
# NetBSD imports # NetBSD imports
SUBDIR= login indent m4 stat tic sed mkdep uniq seq du man \ SUBDIR= login indent m4 stat tic sed mkdep uniq seq du man \
apropos chpass newgrp passwd bzip2 bzip2recover gzip su genassym apropos chpass newgrp passwd bzip2 bzip2recover gzip su genassym \
ldd/elf32 .WAIT ldd
# Non-NetBSD imports # Non-NetBSD imports
SUBDIR+= ministat SUBDIR+= ministat

44
usr.bin/ldd/Makefile Normal file
View file

@ -0,0 +1,44 @@
# $NetBSD: Makefile,v 1.15 2009/12/15 04:06:43 mrg Exp $
WARNS?= 3 # XXX: -Wsign-compare issues ld.elf_so source
.include <bsd.own.mk> # for MKDYNAMICROOT definition
PROG= ldd
SRCS= ldd.c
MAN= ldd.1
SUBDIR+= elf32 elf64 elf32_compat
.if (${MACHINE_ARCH} != "alpha")
LIB_ELF32DIR!= cd ${.CURDIR}/elf32 && ${PRINTOBJDIR}
EXTRA_LIBS+= ${LIB_ELF32DIR}/libldd_elf32.a
.endif
.if (${MACHINE_ARCH} == "mips64el") || (${MACHINE_ARCH} == "mips64eb")
LIB_ELF32COMPATDIR!= cd ${.CURDIR}/elf32_compat && ${PRINTOBJDIR}
EXTRA_LIBS+= ${LIB_ELF32COMPATDIR}/libldd_elf32_compat.a
.endif
.if (${MACHINE_ARCH} == "alpha") || (${MACHINE_ARCH} == "sparc64") || \
(${MACHINE_ARCH} == "x86_64") || (${MACHINE_ARCH} == "powerpc64") || \
(${MACHINE_ARCH} == "mips64el") || (${MACHINE_ARCH} == "mips64eb")
LIB_ELF64DIR!= cd ${.CURDIR}/elf64 && ${PRINTOBJDIR}
EXTRA_LIBS+= ${LIB_ELF64DIR}/libldd_elf64.a
CPPFLAGS.ldd.c= -DELFSIZE=64
.else
CPPFLAGS.ldd.c= -DELFSIZE=32
.endif
LDADD+= ${EXTRA_LIBS}
DPADD+= ${EXTRA_LIBS}
.include "Makefile.common"
.if (${MKDYNAMICROOT} == "no")
LDSTATIC?= -static
.endif
.include <bsd.prog.mk>
.include <bsd.subdir.mk>

View file

@ -0,0 +1,13 @@
# $NetBSD: Makefile.common,v 1.1 2009/01/06 03:59:56 mrg Exp $
LDELFSO=${NETBSDSRCDIR}/libexec/ld.elf_so
CPPFLAGS+= -I${LDELFSO} -DLIBDIR=\"${LIBDIR}\"
CPPFLAGS+= -D_RTLD_SOURCE
#CPPFLAGS+= -DDEBUG
.PATH: ${LDELFSO}
.if (${MACHINE_ARCH} == "sparc") || (${MACHINE_ARCH} == "sparc64") || \
(${MACHINE_ARCH} == "arm") || (${MACHINE_ARCH} == "m68k") || \
(${MACHINE_ARCH} == "powerpc")
CPPFLAGS+= -DVARPSZ
.endif

10
usr.bin/ldd/Makefile.elf Normal file
View file

@ -0,0 +1,10 @@
# $NetBSD: Makefile.elf,v 1.3 2009/01/07 07:52:28 mrg Exp $
# Makefile fragment to build a (32 or 64 bit) libldd_elfxx.a.
# Expects CPPFLAGS to have ELFSIZE set, and LIB to be set.
SRCS= ldd_elfxx.c
SRCS+= xmalloc.c debug.c expand.c map_object.c load.c search.c \
headers.c paths.c
.include "Makefile.common"

26
usr.bin/ldd/Makefile.inc Normal file
View file

@ -0,0 +1,26 @@
# $NetBSD: Makefile.inc,v 1.4 2009/12/15 04:06:43 mrg Exp $
WARNS?= 3 # XXX: -Wsign-compare issues ld.elf_so source
.if ${MACHINE_ARCH} == "sparc64"
MLIBDIR= sparc
.endif
.if ${MACHINE_ARCH} == "x86_64"
MLIBDIR= i386
.endif
.if ${MACHINE_ARCH} == "powerpc64"
MLIBDIR= powerpc
.endif
# For now make "elf32" look for native (n32)
.if (${MACHINE_ARCH} == "mips64eb") || (${MACHINE_ARCH} == "mips64el")
MLIBDIR= 64
COMPAT_MLIBDIR= o32
CPPFLAGS+= -DLDD_ELF64
.endif
.if exists(${.CURDIR}/../../Makefile.inc)
.include "${.CURDIR}/../../Makefile.inc"
.endif

3
usr.bin/ldd/dummy.c Normal file
View file

@ -0,0 +1,3 @@
/* $NetBSD: dummy.c,v 1.1 2009/01/07 00:39:24 mrg Exp $ */
/* This file left intentially blank. */

View file

@ -0,0 +1,23 @@
# $NetBSD: Makefile,v 1.7 2009/12/13 08:50:56 mrg Exp $
.include <bsd.own.mk>
.include <bsd.init.mk>
CPPFLAGS+= -DELFSIZE=32
LIB= ldd_elf32
# XXX Force one member
SRCS= dummy.c
LIBISPRIVATE= yes
.PATH: ${.CURDIR}/..
.ifdef MLIBDIR
CPPFLAGS+= -DRTLD_ARCH_SUBDIR=\"${MLIBDIR}\"
.endif
.if ${MACHINE_ARCH} != "alpha"
.include "../Makefile.elf"
.endif
.include <bsd.lib.mk>

View file

@ -0,0 +1,24 @@
# $NetBSD: Makefile,v 1.1 2009/12/13 08:50:56 mrg Exp $
.include <bsd.own.mk>
.include <bsd.init.mk>
CPPFLAGS+= -DELFSIZE=32 -DELF32_COMPAT
LIB= ldd_elf32_compat
# XXX Force one member
SRCS= dummy.c
LIBISPRIVATE= yes
.PATH: ${.CURDIR}/..
.ifdef COMPAT_MLIBDIR
MLIBDIR= ${COMPAT_MLIBDIR}
CPPFLAGS+= -DRTLD_ARCH_SUBDIR=\"${MLIBDIR}\"
.endif
.ifdef MLIBDIR
.include "../Makefile.elf"
.endif
.include <bsd.lib.mk>

View file

@ -0,0 +1,47 @@
# $NetBSD: Makefile,v 1.5 2009/12/13 08:50:57 mrg Exp $
.include <bsd.own.mk>
CPPFLAGS+= -DELFSIZE=64
LIB= ldd_elf64
# XXX Force one member
SRCS= dummy.c
LIBISPRIVATE= yes
.PATH: ${.CURDIR}/..
.if (${MACHINE_ARCH} == "alpha") || (${MACHINE_ARCH} == "sparc64") || \
(${MACHINE_ARCH} == "x86_64") || (${MACHINE_ARCH} == "powerpc64") || \
(${MACHINE_ARCH} == "mips64el") || (${MACHINE_ARCH} == "mips64eb")
# XXX we need to make sure that we don't accidentally get the elf32
# XXX versions of these.
RTLD_FUNCS = \
_rtld_expand_path \
_rtld_digest_dynamic \
_rtld_digest_phdr \
_rtld_load_needed_objects \
_rtld_load_object \
_rtld_map_object \
_rtld_obj_free \
_rtld_obj_new \
_rtld_add_paths \
_rtld_process_hints \
_rtld_sysctl \
_rtld_load_library
.for _d in ${RTLD_FUNCS}
CPPFLAGS+= -D${_d}=_elf64_${_d}
.endfor
.if (${MACHINE_ARCH} == "mips64el") || (${MACHINE_ARCH} == "mips64eb")
CPPFLAGS+= -DRTLD_ARCH_SUBDIR=\"${MLIBDIR}\"
.endif
.include "../Makefile.elf"
.endif
.include <bsd.lib.mk>

124
usr.bin/ldd/ldd.1 Normal file
View file

@ -0,0 +1,124 @@
.\" $NetBSD: ldd.1,v 1.18 2009/09/07 20:06:21 wiz Exp $
.\"
.\" Copyright (c) 1998 The NetBSD Foundation, Inc.
.\" All rights reserved.
.\"
.\" This code is derived from software contributed to The NetBSD Foundation
.\" by Paul Kranenburg.
.\"
.\" 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 NETBSD FOUNDATION, INC. 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 FOUNDATION 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.
.\"
.Dd September 7, 2009
.Dt LDD 1
.Os
.Sh NAME
.Nm ldd
.Nd list dynamic object dependencies
.Sh SYNOPSIS
.Nm
.Op Fl o
.Op Fl f Ar format
.Ar program ...
.Sh DESCRIPTION
.Nm
displays all shared objects that are needed to run the given program.
Contrary to
.Xr nm 1 ,
the list includes
.Dq indirect
dependencies that are the result of needed shared objects which themselves
depend on yet other shared objects.
Zero, one or two
.Fl f
options may be given.
The argument is a format string passed to
.Xr rtld 1
and allows customization of
.Nm ldd Ns 's
output.
The first format argument is used for library objects and defaults to
.Qq "\et-l%o.%m =\*[Gt] %p\en" .
The second format argument is used for non-library objects and defaults to
.Qq "\et%o =\*[Gt] %p\en" .
.Pp
These arguments are interpreted as format strings a la
.Xr printf 3
to customize the trace output and allow
.Nm
to be operated as a filter more conveniently.
The following conversions can be used:
.Bl -tag -width xxxx
.It \&%a
The main program's name
.Po also known as
.Dq __progname
.Pc .
.It \&%A
The value of the environment variable
.Ev LD_TRACE_LOADED_OBJECTS_PROGNAME
in a.out and the program name from the argument vector from elf.
.It \&%o
The library name.
.It \&%m
The library's major version number.
.It \&%n
The library's minor version number (a.out only, ignored in elf).
.It \&%p
The full pathname as determined by
.Nm rtld Ns 's
library search rules.
.It \&%x
The library's load address
.El
.Pp
Additionally,
.Sy \en
and
.Sy \et
are recognized and have their usual meaning.
.Pp
The
.Fl o
option is an alias for
.Fl f
.Ar \&%a:-l\&%o.\&%m =\*[Gt] \&%p\en ,
which makes
.Nm
behave analogously to
.Ic nm Fl o .
.Sh SEE ALSO
.Xr ld 1 ,
.Xr ld.elf_so 1 ,
.Xr nm 1 ,
.Xr rtld 1
.Sh HISTORY
A
.Nm
utility first appeared in SunOS 4.0, it appeared in its current form
in
.Nx 0.9a .
.Sh BUGS
The
a.out
.Nm
actually runs the program it has been requested to analyze which in specially
constructed environments can have security implications.

305
usr.bin/ldd/ldd.c Normal file
View file

@ -0,0 +1,305 @@
/* $NetBSD: ldd.c,v 1.15 2010/10/16 10:27:08 skrll Exp $ */
/*-
* Copyright (c) 1998, 2000 The NetBSD Foundation, Inc.
* All rights reserved.
*
* This code is derived from software contributed to The NetBSD Foundation
* by Paul Kranenburg.
*
* 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 NETBSD FOUNDATION, INC. 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 FOUNDATION 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.
*/
/*
* Copyright 1996 John D. Polstra.
* Copyright 1996 Matt Thomas <matt@3am-software.com>
* 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.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by John Polstra.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 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 <sys/cdefs.h>
#ifndef lint
__RCSID("$NetBSD: ldd.c,v 1.15 2010/10/16 10:27:08 skrll Exp $");
#endif /* not lint */
#include <sys/types.h>
#include <sys/mman.h>
#include <sys/wait.h>
#include <dirent.h>
#include <err.h>
#include <errno.h>
#include <fcntl.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <ctype.h>
#include "debug.h"
#include "rtld.h"
#include "ldd.h"
/*
* Data declarations.
*/
static char *error_message; /* Message for dlopen(), or NULL */
bool _rtld_trust; /* False for setuid and setgid programs */
Obj_Entry *_rtld_objlist; /* Head of linked list of shared objects */
Obj_Entry **_rtld_objtail = &_rtld_objlist;
/* Link field of last object in list */
u_int _rtld_objcount; /* Number of shared objects */
u_int _rtld_objloads; /* Number of objects loaded */
Obj_Entry *_rtld_objmain; /* The main program shared object */
size_t _rtld_pagesz;
Search_Path *_rtld_default_paths;
Search_Path *_rtld_paths;
Library_Xform *_rtld_xforms;
static void usage(void) __dead;
char *main_local;
char *main_progname;
static void
usage(void)
{
fprintf(stderr, "Usage: %s [-f <format 1>] [-f <format 2>] <filename>"
" ...\n", getprogname());
exit(1);
}
int
main(int argc, char **argv)
{
const char *fmt1 = NULL, *fmt2 = NULL;
int c;
#ifdef DEBUG
debug = 1;
#endif
while ((c = getopt(argc, argv, "f:o")) != -1) {
switch (c) {
case 'f':
if (fmt1) {
if (fmt2)
errx(1, "Too many formats");
fmt2 = optarg;
} else
fmt1 = optarg;
break;
case 'o':
if (fmt1 || fmt2)
errx(1, "Cannot use -o and -f together");
fmt1 = "%a:-l%o.%m => %p\n";
break;
default:
usage();
/*NOTREACHED*/
}
}
argc -= optind;
argv += optind;
if (argc <= 0) {
usage();
/*NOTREACHED*/
}
for (; argc != 0; argc--, argv++) {
int fd;
fd = open(*argv, O_RDONLY);
if (fd == -1) {
warn("%s", *argv);
continue;
}
if (elf_ldd(fd, *argv, fmt1, fmt2) == -1
/* Alpha never had 32 bit support. */
#if defined(_LP64) && !defined(__alpha__)
&& elf32_ldd(fd, *argv, fmt1, fmt2) == -1
#ifdef __mips__
&& elf32_ldd_compat(fd, *argv, fmt1, fmt2) == -1
#endif
#endif
)
warnx("%s", error_message);
close(fd);
}
return 0;
}
/*
* Error reporting function. Use it like printf. If formats the message
* into a buffer, and sets things up so that the next call to dlerror()
* will return the message.
*/
void
_rtld_error(const char *fmt, ...)
{
static char buf[512];
va_list ap;
va_start(ap, fmt);
xvsnprintf(buf, sizeof buf, fmt, ap);
error_message = buf;
va_end(ap);
}
char *
dlerror()
{
char *msg = error_message;
error_message = NULL;
return msg;
}
void
fmtprint(const char *libname, Obj_Entry *obj, const char *fmt1,
const char *fmt2)
{
const char *libpath = obj ? obj->path : "not found";
char libnamebuf[200];
char *libmajor = NULL;
const char *fmt;
char *cp;
int c;
if (strncmp(libname, "lib", 3) == 0 &&
(cp = strstr(libname, ".so")) != NULL) {
int i = cp - (libname + 3);
if (i >= sizeof(libnamebuf))
i = sizeof(libnamebuf) - 1;
(void)memcpy(libnamebuf, libname + 3, i);
libnamebuf[i] = '\0';
if (cp[3] && isdigit((unsigned char)cp[4]))
libmajor = &cp[4];
libname = libnamebuf;
}
if (fmt1 == NULL)
fmt1 = libmajor != NULL ?
"\t-l%o.%m => %p\n" :
"\t-l%o => %p\n";
if (fmt2 == NULL)
fmt2 = "\t%o => %p\n";
fmt = libname == libnamebuf ? fmt1 : fmt2;
while ((c = *fmt++) != '\0') {
switch (c) {
default:
putchar(c);
continue;
case '\\':
switch (c = *fmt) {
case '\0':
continue;
case 'n':
putchar('\n');
break;
case 't':
putchar('\t');
break;
}
break;
case '%':
switch (c = *fmt) {
case '\0':
continue;
case '%':
default:
putchar(c);
break;
case 'A':
printf("%s", main_local);
break;
case 'a':
printf("%s", main_progname);
break;
case 'o':
printf("%s", libname);
break;
case 'm':
printf("%s", libmajor);
break;
case 'n':
/* XXX: not supported for elf */
break;
case 'p':
printf("%s", libpath);
break;
case 'x':
printf("%p", obj ? obj->mapbase : 0);
break;
}
break;
}
++fmt;
}
}
void
print_needed(Obj_Entry *obj, const char *fmt1, const char *fmt2)
{
const Needed_Entry *needed;
for (needed = obj->needed; needed != NULL; needed = needed->next) {
const char *libname = obj->strtab + needed->name;
if (needed->obj != NULL) {
if (!needed->obj->printed) {
fmtprint(libname, needed->obj, fmt1, fmt2);
needed->obj->printed = 1;
print_needed(needed->obj, fmt1, fmt2);
}
} else {
fmtprint(libname, needed->obj, fmt1, fmt2);
}
}
}

50
usr.bin/ldd/ldd.h Normal file
View file

@ -0,0 +1,50 @@
/* $NetBSD: ldd.h,v 1.6 2009/12/15 04:06:43 mrg Exp $ */
/*
* Copyright (c) 2008 Matthew R. Green
* 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.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 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.
*/
int elf32_ldd(int, char *, const char *, const char *);
#ifdef _LP64
#define LDD_ELF64
#endif
#ifdef LDD_ELF64
int elf64_ldd(int, char *, const char *, const char *);
#define elf_ldd elf64_ldd
#elif defined(ELF32_COMPAT)
#define elf_ldd elf32_compat_ldd
#else
#define elf_ldd elf32_ldd
#endif
void fmtprint(const char *, Obj_Entry *, const char *, const char *);
void print_needed(Obj_Entry *, const char *, const char *);
extern char *main_local;
extern char *main_progname;

162
usr.bin/ldd/ldd_elfxx.c Normal file
View file

@ -0,0 +1,162 @@
/* $NetBSD: ldd_elfxx.c,v 1.4 2009/09/07 04:49:03 dholland Exp $ */
/*-
* Copyright (c) 1998, 2000 The NetBSD Foundation, Inc.
* All rights reserved.
*
* This code is derived from software contributed to The NetBSD Foundation
* by Paul Kranenburg.
*
* 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 NETBSD FOUNDATION, INC. 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 FOUNDATION 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.
*/
/*
* Copyright 1996 John D. Polstra.
* Copyright 1996 Matt Thomas <matt@3am-software.com>
* 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.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by John Polstra.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 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 <sys/cdefs.h>
#ifndef lint
__RCSID("$NetBSD: ldd_elfxx.c,v 1.4 2009/09/07 04:49:03 dholland Exp $");
#endif /* not lint */
#include <sys/types.h>
#include <sys/mman.h>
#include <sys/wait.h>
#include <dirent.h>
#include <err.h>
#include <errno.h>
#include <fcntl.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <ctype.h>
#include "debug.h"
#include "rtld.h"
#include "ldd.h"
#define munmap minix_munmap
/*
* elfxx_ldd() - bit-size independant ELF ldd implementation.
* returns 0 on success and -1 on failure.
*/
int
ELFNAME(ldd)(int fd, char *path, const char *fmt1, const char *fmt2)
{
struct stat st;
if (lseek(fd, 0, SEEK_SET) < 0 ||
fstat(fd, &st) < 0) {
_rtld_error("%s: %s", path, strerror(errno));
return -1;
}
_rtld_pagesz = sysconf(_SC_PAGESIZE);
#ifdef RTLD_ARCH_SUBDIR
_rtld_add_paths(path, &_rtld_default_paths,
RTLD_DEFAULT_LIBRARY_PATH "/" RTLD_ARCH_SUBDIR);
#endif
_rtld_add_paths(path, &_rtld_default_paths, RTLD_DEFAULT_LIBRARY_PATH);
_rtld_paths = NULL;
_rtld_trust = (st.st_mode & (S_ISUID | S_ISGID)) == 0;
if (_rtld_trust)
_rtld_add_paths(path, &_rtld_paths, getenv("LD_LIBRARY_PATH"));
_rtld_process_hints(path, &_rtld_paths, &_rtld_xforms, _PATH_LD_HINTS);
_rtld_objmain = _rtld_map_object(xstrdup(path), fd, &st);
if (_rtld_objmain == NULL)
return -1;
_rtld_objmain->path = xstrdup(path);
_rtld_digest_dynamic(path, _rtld_objmain);
/* Link the main program into the list of objects. */
*_rtld_objtail = _rtld_objmain;
_rtld_objtail = &_rtld_objmain->next;
++_rtld_objmain->refcount;
(void) _rtld_load_needed_objects(_rtld_objmain, 0);
if (fmt1 == NULL)
printf("%s:\n", _rtld_objmain->path);
main_local = path;
main_progname = _rtld_objmain->path;
print_needed(_rtld_objmain, fmt1, fmt2);
while (_rtld_objlist != NULL) {
Obj_Entry *obj = _rtld_objlist;
_rtld_objlist = obj->next;
while (obj->rpaths != NULL) {
const Search_Path *rpath = obj->rpaths;
obj->rpaths = rpath->sp_next;
xfree(__UNCONST(rpath->sp_path));
xfree(__UNCONST(rpath));
}
while (obj->needed != NULL) {
const Needed_Entry *needed = obj->needed;
obj->needed = needed->next;
xfree(__UNCONST(needed));
}
(void) munmap(obj->mapbase, obj->mapsize);
xfree(obj->path);
xfree(obj);
}
_rtld_objmain = NULL;
_rtld_objtail = &_rtld_objlist;
/* Need to free _rtld_paths? */
return 0;
}