aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoland McGrath <roland@gnu.org>1995-10-09 07:06:29 +0000
committerRoland McGrath <roland@gnu.org>1995-10-09 07:06:29 +0000
commitb122c7038e826eeabbc0118612b988c1a0f5b991 (patch)
tree1f3963026427771b6504b8afb91216895d95ba45
parent80fd73873bd51e58039983a9416ef3bb97bdac57 (diff)
downloadglibc-b122c7038e826eeabbc0118612b988c1a0f5b991.tar
glibc-b122c7038e826eeabbc0118612b988c1a0f5b991.tar.gz
glibc-b122c7038e826eeabbc0118612b988c1a0f5b991.tar.bz2
glibc-b122c7038e826eeabbc0118612b988c1a0f5b991.zip
Mon Oct 9 02:54:14 1995 Roland McGrath <roland@churchy.gnu.ai.mit.edu>
* Makeconfig (config-LDFLAGS): Define to -Wl-dynamic-linker=$(libdir)$(rtld-installed-name). (rtld-installed-name): New variable. * elf/Makefile (install-lib): Variable removed. (install-others): Define this instead, to $(libdir)(rtld-installed-name). ($(libdir)(rtld-installed-name)): New target; install from ld.so. * elf/ldd.sh.in: New file. * elf/Makefile (distribute): Add ldd.sh.in. (install-bin): Add ldd. ($(objpfx)ldd: ldd.sh.in): New rule. * sysdeps/mach/hurd/dl-sysdep.c: Use __hurd_fail throughout. * hurd/hurd.h (__hurd_fail): Replace macro with inline function. Translate some Mach errors to Hurd errors. * elf/rtld.c (dl_main): Under --list, print msg if executable is statically linked. * elf/dl-load.c (_dl_map_object_from_fd): Rewrote program header table processing. Sat Oct 7 01:25:48 1995 Roland McGrath <roland@churchy.gnu.ai.mit.edu> * sysdeps/stub/machine-gmon.h: Add #error. Fri Oct 6 01:49:48 1995 Roland McGrath <roland@churchy.gnu.ai.mit.edu> * elf/dynamic-link.h (elf_get_dynamic_info): If DYN is null, don't examine it.
-rw-r--r--ChangeLog34
-rw-r--r--Makeconfig11
-rw-r--r--elf/Makefile12
-rw-r--r--elf/dl-load.c240
-rw-r--r--elf/dynamic-link.h3
-rw-r--r--elf/ldd.sh.in26
-rw-r--r--elf/rtld.c7
-rw-r--r--hurd/hurd.h28
-rw-r--r--sysdeps/mach/hurd/dl-sysdep.c91
-rw-r--r--sysdeps/stub/machine-gmon.h2
-rwxr-xr-xsysdeps/unix/configure16
11 files changed, 299 insertions, 171 deletions
diff --git a/ChangeLog b/ChangeLog
index d600df2beb..b6935c1fa5 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,37 @@
+Mon Oct 9 02:54:14 1995 Roland McGrath <roland@churchy.gnu.ai.mit.edu>
+
+ * Makeconfig (config-LDFLAGS): Define to
+ -Wl-dynamic-linker=$(libdir)$(rtld-installed-name).
+ (rtld-installed-name): New variable.
+ * elf/Makefile (install-lib): Variable removed.
+ (install-others): Define this instead, to
+ $(libdir)(rtld-installed-name).
+ ($(libdir)(rtld-installed-name)): New target; install from ld.so.
+
+ * elf/ldd.sh.in: New file.
+ * elf/Makefile (distribute): Add ldd.sh.in.
+ (install-bin): Add ldd.
+ ($(objpfx)ldd: ldd.sh.in): New rule.
+
+ * sysdeps/mach/hurd/dl-sysdep.c: Use __hurd_fail throughout.
+ * hurd/hurd.h (__hurd_fail): Replace macro with inline function.
+ Translate some Mach errors to Hurd errors.
+
+ * elf/rtld.c (dl_main): Under --list, print msg if executable is
+ statically linked.
+
+ * elf/dl-load.c (_dl_map_object_from_fd): Rewrote program header
+ table processing.
+
+Sat Oct 7 01:25:48 1995 Roland McGrath <roland@churchy.gnu.ai.mit.edu>
+
+ * sysdeps/stub/machine-gmon.h: Add #error.
+
+Fri Oct 6 01:49:48 1995 Roland McGrath <roland@churchy.gnu.ai.mit.edu>
+
+ * elf/dynamic-link.h (elf_get_dynamic_info): If DYN is null, don't
+ examine it.
+
Fri Sep 29 03:43:51 1995 Paul Eggert <eggert@twinsun.com>
Rewrite mktime from scratch for performance, and for correctness
diff --git a/Makeconfig b/Makeconfig
index 5dd6d544d0..e0ec754883 100644
--- a/Makeconfig
+++ b/Makeconfig
@@ -272,6 +272,11 @@ ifndef +link
$(^:$(common-objpfx)libc.a=$(link-libc)) \
$(addprefix $(csu-objpfx),$(+postinit))
endif
+ifndef config-LDFLAGS
+ifeq (yes,$(build-shared))
+config-LDFLAGS = -Wl,-dynamic-linker=$(libdir)$(rtld-installed-name)
+endif
+endif
ifndef link-libc
ifeq (yes,$(build-shared))
link-libc = -L$(common-objdir) -lc $(gnulib)
@@ -292,6 +297,12 @@ else
csu-objpfx = $(..)csu/
endif
+ifeq (yes,$(build-shared))
+ifndef rtld-installed-name
+rtld-installed-name = ld.so
+endif
+endif
+
ifndef LD
LD := ld -X
endif
diff --git a/elf/Makefile b/elf/Makefile
index 0065d2ba47..203406d805 100644
--- a/elf/Makefile
+++ b/elf/Makefile
@@ -27,18 +27,18 @@ extra-libs = libelf libdl
libelf-routines := elf_hash
libdl-routines := dlopen dlclose dlsym dlerror
libdl-inhibit-o = $(filter-out .so,$(object-suffixes)) # Build only shared.
-LDFLAGS-dl.so := -e 0 # work around ld bug
rtld-routines := rtld $(addprefix dl-,load lookup object reloc \
runtime sysdep error init fini)
distribute = $(rtld-routines:=.c) dynamic-link.h do-rel.h \
- soinit.c sofini.c
+ soinit.c sofini.c ldd.sh.in
include ../Makeconfig
ifeq (yes,$(build-shared))
extra-objs = $(rtld-routines:=.so) soinit.so sofini.so
-install-lib = ld.so
+install-others = $(libdir)(rtld-installed-name)
+install-bin = ldd
endif
include ../Rules
@@ -54,3 +54,9 @@ $(objpfx)libdl.so: $(objpfx)libdl_pic.a $(common-objpfx)libc.so $(objpfx)ld.so
$(LINK.o) -shared -o $(@:$(objpfx)%=%) \
$(LDFLAGS.so) $(LDFLAGS-dl.so) \
-Wl,--whole-archive $(^:$(objpfx)%=%)
+
+$(libdir)$(rtld-installed-name): $(objpfx)ld.so; $(do-install-program)
+
+$(objpfx)ldd: ldd.sh.in
+ sed 's%@RTLD@%$(libdir)/$(rtld-installed-name)%g' < $< > $@.new
+ mv -f $@.new $@
diff --git a/elf/dl-load.c b/elf/dl-load.c
index 12b945a185..b70ba5590a 100644
--- a/elf/dl-load.c
+++ b/elf/dl-load.c
@@ -166,6 +166,7 @@ _dl_map_object_from_fd (const char *name, int fd, char *realname)
void *file_mapping = NULL;
size_t mapping_size = 0;
+#define LOSE(s) lose (0, (s))
void lose (int code, const char *msg)
{
(void) close (fd);
@@ -174,6 +175,17 @@ _dl_map_object_from_fd (const char *name, int fd, char *realname)
_dl_signal_error (code, l ? l->l_name : name, msg);
}
+ inline caddr_t map_segment (Elf32_Addr mapstart, size_t len,
+ int prot, int fixed, off_t offset)
+ {
+ caddr_t mapat = mmap ((caddr_t) mapstart, len, prot,
+ fixed|MAP_COPY|MAP_FILE|MAP_INHERIT,
+ fd, offset);
+ if (mapat == (caddr_t) -1)
+ lose (errno, "failed to map segment from shared object");
+ return mapat;
+ }
+
/* Make sure LOCATION is mapped in. */
void *map (off_t location, size_t size)
{
@@ -194,6 +206,9 @@ _dl_map_object_from_fd (const char *name, int fd, char *realname)
}
const Elf32_Ehdr *header;
+ const Elf32_Phdr *phdr;
+ const Elf32_Phdr *ph;
+ int type;
/* Look again to see if the real name matched another already loaded. */
for (l = _dl_loaded; l; l = l->l_next)
@@ -210,8 +225,6 @@ _dl_map_object_from_fd (const char *name, int fd, char *realname)
/* Map in the first page to read the header. */
header = map (0, sizeof *header);
-#undef LOSE
-#define LOSE(s) lose (0, (s))
/* Check the header for basic validity. */
if (*(Elf32_Word *) &header->e_ident != ((ELFMAG0 << (EI_MAG0 * 8)) |
(ELFMAG1 << (EI_MAG1 * 8)) |
@@ -242,27 +255,26 @@ _dl_map_object_from_fd (const char *name, int fd, char *realname)
_dl_signal_error (errno, NULL, "cannot open zero fill device");
}
- {
- /* Copy the program header table into stack space so we can then unmap
- the headers. */
- Elf32_Phdr phdr[header->e_phnum];
- const Elf32_Phdr *ph;
- int anywhere, type;
+ /* Extract the remaining details we need from the ELF header
+ and then map in the program header table. */
+ l->l_entry = header->e_entry;
+ type = header->e_type;
+ l->l_phnum = header->e_phnum;
+ phdr = map (header->e_phoff, l->l_phnum * sizeof (Elf32_Phdr));
- type = header->e_type;
- anywhere = type == ET_DYN || type == ET_REL;
- l->l_entry = header->e_entry;
-
- ph = map (header->e_phoff, header->e_phnum * sizeof (Elf32_Phdr));
- memcpy (phdr, ph, sizeof phdr);
- l->l_phnum = header->e_phnum;
-
- /* We are done reading the file's headers now. Unmap them. */
- munmap (file_mapping, mapping_size);
+ {
+ /* Scan the program header table, collecting its load commands. */
+ struct loadcmd
+ {
+ Elf32_Addr mapstart, mapend, dataend, allocend;
+ off_t mapoff;
+ int prot;
+ } loadcmds[l->l_phnum], *c;
+ size_t nloadcmds = 0;
- /* Scan the program header table, processing its load commands. */
- l->l_addr = 0;
l->l_ld = 0;
+ l->l_phdr = 0;
+ l->l_addr = 0;
for (ph = phdr; ph < &phdr[l->l_phnum]; ++ph)
switch (ph->p_type)
{
@@ -277,114 +289,126 @@ _dl_map_object_from_fd (const char *name, int fd, char *realname)
break;
case PT_LOAD:
- /* A load command tells us to map in part of the file. */
+ /* A load command tells us to map in part of the file.
+ We record the load commands and process them all later. */
if (ph->p_align % pagesize != 0)
LOSE ("ELF load command alignment not page-aligned");
if ((ph->p_vaddr - ph->p_offset) % ph->p_align)
LOSE ("ELF load command address/offset not properly aligned");
{
- Elf32_Addr mapstart = ph->p_vaddr & ~(ph->p_align - 1);
- Elf32_Addr mapend = ((ph->p_vaddr + ph->p_filesz + ph->p_align - 1)
- & ~(ph->p_align - 1));
- off_t mapoff = ph->p_offset & ~(ph->p_align - 1);
- caddr_t mapat;
- int prot = 0;
+ struct loadcmd *c = &loadcmds[nloadcmds++];
+ c->mapstart = ph->p_vaddr & ~(ph->p_align - 1);
+ c->mapend = ((ph->p_vaddr + ph->p_filesz + ph->p_align - 1)
+ & ~(ph->p_align - 1));
+ c->dataend = ph->p_vaddr + ph->p_filesz;
+ c->allocend = ph->p_vaddr + ph->p_memsz;
+ c->mapoff = ph->p_offset & ~(ph->p_align - 1);
+ c->prot = 0;
if (ph->p_flags & PF_R)
- prot |= PROT_READ;
+ c->prot |= PROT_READ;
if (ph->p_flags & PF_W)
- prot |= PROT_WRITE;
+ c->prot |= PROT_WRITE;
if (ph->p_flags & PF_X)
- prot |= PROT_EXEC;
+ c->prot |= PROT_EXEC;
+ break;
+ }
+ }
- if (anywhere)
- {
- /* XXX this loses if the first segment mmap call puts
- it someplace where the later segments cannot fit. */
- mapat = mmap ((caddr_t) (l->l_addr + mapstart),
- mapend - mapstart,
- prot, MAP_COPY|MAP_FILE|MAP_INHERIT |
- /* Let the system choose any convenient
- location if this is the first segment.
- Following segments must be contiguous in
- virtual space with the first. */
- (l->l_addr == 0 ? 0 : MAP_FIXED),
- fd, mapoff);
- if (l->l_addr == 0)
- /* This was the first segment mapped, so MAPAT is
- the address the system chose for us. Record it. */
- l->l_addr = (Elf32_Addr) mapat - mapstart;
- }
- else
- {
- mapat = mmap ((caddr_t) mapstart, mapend - mapstart,
- prot, MAP_COPY|MAP_FILE|MAP_INHERIT|MAP_FIXED,
- fd, mapoff);
- /* This file refers to absolute addresses. So consider its
- "load base" to be zero, since that is what we add to the
- file's addresses to find them in our memory. */
- l->l_addr = 0;
- }
- if (mapat == (caddr_t) -1)
- lose (errno, "failed to map segment from shared object");
+ /* We are done reading the file's headers now. Unmap them. */
+ munmap (file_mapping, mapping_size);
+
+ /* Now process the load commands and map segments into memory. */
+ c = loadcmds;
+
+ if (type == ET_DYN || type == ET_REL)
+ {
+ /* This is a position-independent shared object. We can let the
+ kernel map it anywhere it likes, but we must have space for all
+ the segments in their specified positions relative to the first.
+ So we map the first segment without MAP_FIXED, but with its
+ extent increased to cover all the segments. Then we unmap the
+ excess portion, and there is known sufficient space there to map
+ the later segments. */
+ caddr_t mapat;
+ mapat = map_segment (c->mapstart,
+ loadcmds[nloadcmds - 1].allocend - c->mapstart,
+ c->prot, 0, c->mapoff);
+ l->l_addr = (Elf32_Addr) mapat - c->mapstart;
+
+ /* Unmap the excess portion, and then jump into the normal
+ segment-mapping loop to handle the portion of the segment past
+ the end of the file mapping. */
+ munmap (mapat + c->mapend,
+ loadcmds[nloadcmds - 1].allocend - c->mapend);
+ goto postmap;
+ }
+
+ while (c < &loadcmds[nloadcmds])
+ {
+ if (c->mapend > c->mapstart)
+ /* Map the segment contents from the file. */
+ map_segment (l->l_addr + c->mapstart, c->mapend - c->mapstart,
+ c->prot, MAP_FIXED, c->mapoff);
+
+ postmap:
+ if (c->allocend > c->dataend)
+ {
+ /* Extra zero pages should appear at the end of this segment,
+ after the data mapped from the file. */
+ Elf32_Addr zero, zeroend, zeropage;
+
+ zero = l->l_addr + c->dataend;
+ zeroend = l->l_addr + c->allocend;
+ zeropage = (zero + pagesize - 1) & ~(pagesize - 1);
- if (ph->p_memsz > ph->p_filesz)
+ if (zeroend < zeropage)
+ /* All the extra data is in the last page of the segment.
+ We can just zero it. */
+ zeropage = zeroend;
+
+ if (zeropage > zero)
{
- /* Extra zero pages should appear at the end of this segment,
- after the data mapped from the file. */
- caddr_t zero, zeroend, zeropage;
-
- mapat += ph->p_vaddr - mapstart;
- zero = mapat + ph->p_filesz;
- zeroend = mapat + ph->p_memsz;
- zeropage = (caddr_t) ((Elf32_Addr) (zero + pagesize - 1)
- & ~(pagesize - 1));
-
- if (zeroend < zeropage)
- /* All the extra data is in the last page of the segment.
- We can just zero it. */
- zeropage = zeroend;
- if (zeropage > zero)
+ /* Zero the final part of the last page of the segment. */
+ if ((c->prot & PROT_WRITE) == 0)
{
- /* Zero the final part of the last page of the segment. */
- if ((prot & PROT_WRITE) == 0)
- {
- /* Dag nab it. */
- if (mprotect ((caddr_t) ((Elf32_Addr) zero
- & ~(pagesize - 1)),
- pagesize,
- prot|PROT_WRITE) < 0)
- lose (errno, "cannot change memory protections");
- }
- memset (zero, 0, zeropage - zero);
- if ((prot & PROT_WRITE) == 0)
- mprotect ((caddr_t) ((Elf32_Addr) zero
- & ~(pagesize - 1)),
- pagesize, prot);
+ /* Dag nab it. */
+ if (mprotect ((caddr_t) (zero & ~(pagesize - 1)),
+ pagesize, c->prot|PROT_WRITE) < 0)
+ lose (errno, "cannot change memory protections");
}
+ memset ((void *) zero, 0, zeropage - zero);
+ if ((c->prot & PROT_WRITE) == 0)
+ mprotect ((caddr_t) (zero & ~(pagesize - 1)),
+ pagesize, c->prot);
+ }
- if (zeroend > zeropage)
- /* Map the remaining zero pages in from the zero fill FD. */
- mapat = mmap (zeropage, zeroend - zeropage, prot,
- MAP_ANON|MAP_PRIVATE|MAP_FIXED|MAP_INHERIT,
- _dl_zerofd, 0);
+ if (zeroend > zeropage)
+ {
+ /* Map the remaining zero pages in from the zero fill FD. */
+ caddr_t mapat;
+ mapat = mmap ((caddr_t) zeropage, zeroend - zeropage, c->prot,
+ MAP_ANON|MAP_PRIVATE|MAP_FIXED|MAP_INHERIT,
+ _dl_zerofd, 0);
+ if (mapat == (caddr_t) -1)
+ lose (errno, "cannot map zero pages");
}
}
- }
- if (l->l_ld == 0)
- {
- if (type == ET_DYN)
- LOSE ("object file has no dynamic section");
+ ++c;
}
- else
- (Elf32_Addr) l->l_ld += l->l_addr;
+ }
- if (l->l_phdr == 0)
- l->l_phdr = (void *) ((const Elf32_Ehdr *) l->l_addr)->e_phoff;
- (Elf32_Addr) l->l_phdr += l->l_addr;
+ if (l->l_ld == 0)
+ {
+ if (type == ET_DYN)
+ LOSE ("object file has no dynamic section");
+ }
+ else
+ (Elf32_Addr) l->l_ld += l->l_addr;
- l->l_entry += l->l_addr;
- }
+ if (l->l_phdr == 0)
+ l->l_phdr = (void *) ((const Elf32_Ehdr *) l->l_addr)->e_phoff;
+ (Elf32_Addr) l->l_phdr += l->l_addr;
elf_get_dynamic_info (l->l_ld, l->l_info);
if (l->l_info[DT_HASH])
diff --git a/elf/dynamic-link.h b/elf/dynamic-link.h
index a7316eefe8..84d440ec5b 100644
--- a/elf/dynamic-link.h
+++ b/elf/dynamic-link.h
@@ -32,6 +32,9 @@ elf_get_dynamic_info (Elf32_Dyn *dyn, Elf32_Dyn *info[DT_NUM])
for (i = 0; i < DT_NUM; ++i)
info[i] = NULL;
+ if (! dyn)
+ return;
+
while (dyn->d_tag != DT_NULL)
{
assert (dyn->d_tag < DT_NUM);
diff --git a/elf/ldd.sh.in b/elf/ldd.sh.in
new file mode 100644
index 0000000000..58ae501e53
--- /dev/null
+++ b/elf/ldd.sh.in
@@ -0,0 +1,26 @@
+#! /bin/sh
+
+# This is the `ldd' command, which lists what shared libraries are
+# used by given dynamically-linked executables. It works by invoking the
+# run-time dynamic linker as a command and giving it the special `--list'
+# switch.
+
+RTLD=@RTLD@
+
+case $# in
+0)
+ echo >&2 "Usage: $0 FILE..."
+ exit 1 ;;
+1)
+ # We don't list the file name when there is only one.
+ exec ${RTLD} --list "$1" && exit 1
+ exit ;;
+*)
+ set -e # Bail out immediately if ${RTLD} loses on any argument.
+ for file; do
+ echo "${file}:"
+ ${RTLD} --list "$file"
+ done
+esac
+
+exit 0
diff --git a/elf/rtld.c b/elf/rtld.c
index 6be05eb299..d780fcb870 100644
--- a/elf/rtld.c
+++ b/elf/rtld.c
@@ -281,6 +281,13 @@ of this helper program; chances are you did not intend to run this program.\n",
if (list_only)
{
+ if (! _dl_loaded->l_info[DT_NEEDED])
+ {
+ _dl_sysdep_message (_dl_loaded->l_name, ": statically linked\n",
+ NULL);
+ _exit (1);
+ }
+
for (l = _dl_loaded->l_next; l; l = l->l_next)
{
char buf[20], *bp;
diff --git a/hurd/hurd.h b/hurd/hurd.h
index 1b4db17efe..acad15b8c4 100644
--- a/hurd/hurd.h
+++ b/hurd/hurd.h
@@ -42,7 +42,33 @@ Cambridge, MA 02139, USA. */
#include <hurd/port.h>
#include <errno.h>
-#define __hurd_fail(err) (errno = (err), -1)
+
+_EXTERN_INLINE int
+__hurd_fail (error_t err)
+{
+ switch (err)
+ {
+ case EMACH_SEND_INVALID_DEST:
+ case EMIG_SERVER_DIED:
+ /* The server has disappeared! */
+ err = EIEIO;
+ break;
+
+ case KERN_NO_SPACE:
+ err = ENOMEM;
+ break;
+ case KERN_INVALID_ARGUMENT:
+ err = EINVAL;
+ break;
+
+ case 0:
+ return 0;
+ default:
+ }
+
+ errno = err;
+ return -1;
+}
/* Basic ports and info, initialized by startup. */
diff --git a/sysdeps/mach/hurd/dl-sysdep.c b/sysdeps/mach/hurd/dl-sysdep.c
index 8e1ef174e2..10380753cd 100644
--- a/sysdeps/mach/hurd/dl-sysdep.c
+++ b/sysdeps/mach/hurd/dl-sysdep.c
@@ -262,41 +262,38 @@ open (const char *file_name, int mode, ...)
file_t startdir, newpt, fileport;
int dealloc_dir;
int nloops;
-
+ error_t err;
assert (mode == O_RDONLY);
-
startdir = _dl_hurd_data->portarray[file_name[0] == '/' ?
INIT_PORT_CRDIR : INIT_PORT_CWDIR];
while (file_name[0] == '/')
file_name++;
- if (errno = __dir_lookup (startdir, file_name, mode, 0,
- &doretry, retryname, &fileport))
- return -1;
+ if (err = __dir_lookup (startdir, file_name, mode, 0,
+ &doretry, retryname, &fileport))
+ return __hurd_fail (err);
dealloc_dir = 0;
nloops = 0;
- errno = 0;
while (1)
{
if (dealloc_dir)
__mach_port_deallocate (__mach_task_self (), startdir);
- if (errno)
- return -1;
+ if (err)
+ return __hurd_fail (err);
switch (doretry)
{
case FS_RETRY_REAUTH:
{
mach_port_t ref = __mach_reply_port ();
- errno = __io_reauthenticate
- (fileport, ref, MACH_MSG_TYPE_MAKE_SEND);
- if (! errno)
- errno = __auth_user_authenticate
+ err = __io_reauthenticate (fileport, ref, MACH_MSG_TYPE_MAKE_SEND);
+ if (! err)
+ err = __auth_user_authenticate
(_dl_hurd_data->portarray[INIT_PORT_AUTH],
fileport,
ref, MACH_MSG_TYPE_MAKE_SEND,
@@ -304,18 +301,15 @@ open (const char *file_name, int mode, ...)
__mach_port_destroy (__mach_task_self (), ref);
}
__mach_port_deallocate (__mach_task_self (), fileport);
- if (errno)
- return -1;
+ if (err)
+ return __hurd_fail (err);
fileport = newpt;
/* Fall through. */
case FS_RETRY_NORMAL:
#ifdef SYMLOOP_MAX
if (nloops++ >= SYMLOOP_MAX)
- {
- errno = ELOOP;
- return -1;
- }
+ return __hurd_fail (ELOOP);
#endif
/* An empty RETRYNAME indicates we have the final port. */
@@ -327,11 +321,11 @@ open (const char *file_name, int mode, ...)
opened:
/* We have the file open. Now map it. */
- errno = __io_map (fileport, &memobj_rd, &memobj_wr);
+ err = __io_map (fileport, &memobj_rd, &memobj_wr);
if (dealloc_dir)
__mach_port_deallocate (__mach_task_self (), fileport);
- if (errno)
- return -1;
+ if (err)
+ return __hurd_fail (err);
if (memobj_wr != MACH_PORT_NULL)
__mach_port_deallocate (__mach_task_self (), memobj_wr);
@@ -359,26 +353,20 @@ open (const char *file_name, int mode, ...)
{
int fd;
char *end;
- errno = 0;
+ err = 0;
fd = (int) strtol (retryname, &end, 10);
- if (end == NULL || errno || /* Malformed number. */
+ if (end == NULL || err || /* Malformed number. */
/* Check for excess text after the number. A slash
is valid; it ends the component. Anything else
does not name a numeric file descriptor. */
(*end != '/' && *end != '\0'))
- {
- errno = ENOENT;
- return -1;
- }
+ return __hurd_fail (ENOENT);
if (fd < 0 || fd >= _dl_hurd_data->dtablesize ||
_dl_hurd_data->dtable[fd] == MACH_PORT_NULL)
- {
- /* If the name was a proper number, but the file
- descriptor does not exist, we return EBADF instead
- of ENOENT. */
- errno = EBADF;
- return -1;
- }
+ /* If the name was a proper number, but the file
+ descriptor does not exist, we return EBADF instead
+ of ENOENT. */
+ return __hurd_fail (EBADF);
fileport = _dl_hurd_data->dtable[fd];
if (*end == '\0')
{
@@ -459,13 +447,13 @@ open (const char *file_name, int mode, ...)
}
case '\0':
- if (errno = opentty (&fileport))
- return -1;
+ if (err = opentty (&fileport))
+ return __hurd_fail (err);
dealloc_dir = 1;
goto opened;
case '/':
- if (errno = opentty (&startdir))
- return -1;
+ if (err = opentty (&startdir))
+ return __hurd_fail (err);
dealloc_dir = 1;
strcpy (retryname, &retryname[4]);
break;
@@ -478,18 +466,16 @@ open (const char *file_name, int mode, ...)
default:
bad_magic:
- errno = EGRATUITOUS;
- return -1;
+ return __hurd_fail (EGRATUITOUS);
}
break;
default:
- errno = EGRATUITOUS;
- return -1;
+ return __hurd_fail (EGRATUITOUS);
}
- errno = __dir_lookup (startdir, file_name, mode, 0,
- &doretry, retryname, &fileport);
+ err = __dir_lookup (startdir, file_name, mode, 0,
+ &doretry, retryname, &fileport);
}
}
@@ -504,6 +490,7 @@ close (int fd)
caddr_t
mmap (caddr_t addr, size_t len, int prot, int flags, int fd, off_t offset)
{
+ error_t err;
vm_prot_t vmprot;
vm_address_t mapaddr;
@@ -516,14 +503,14 @@ mmap (caddr_t addr, size_t len, int prot, int flags, int fd, off_t offset)
vmprot |= VM_PROT_EXECUTE;
mapaddr = (vm_address_t) addr;
- errno = __vm_map (__mach_task_self (),
- &mapaddr, (vm_size_t) len, 0 /*ELF_MACHINE_USER_ADDRESS_MASK*/,
- !(flags & MAP_FIXED),
- (mach_port_t) fd, (vm_offset_t) offset,
- flags & (MAP_COPY|MAP_PRIVATE),
- vmprot, VM_PROT_ALL,
- (flags & MAP_INHERIT) ? VM_INHERIT_COPY : VM_INHERIT_NONE);
- return errno ? (caddr_t) -1 : (caddr_t) mapaddr;
+ err = __vm_map (__mach_task_self (),
+ &mapaddr, (vm_size_t) len, 0 /*ELF_MACHINE_USER_ADDRESS_MASK*/,
+ !(flags & MAP_FIXED),
+ (mach_port_t) fd, (vm_offset_t) offset,
+ flags & (MAP_COPY|MAP_PRIVATE),
+ vmprot, VM_PROT_ALL,
+ (flags & MAP_INHERIT) ? VM_INHERIT_COPY : VM_INHERIT_NONE);
+ return err ? (caddr_t) __hurd_fail (err) : (caddr_t) mapaddr;
}
void
diff --git a/sysdeps/stub/machine-gmon.h b/sysdeps/stub/machine-gmon.h
index a6edbc062d..166faedab6 100644
--- a/sysdeps/stub/machine-gmon.h
+++ b/sysdeps/stub/machine-gmon.h
@@ -26,3 +26,5 @@ void mcount (u_long arg) \
{ \
_mcount (caller return PC, my return PC); \
}
+
+#error "sysdeps/MACHINE/machine-gmon.h missing"
diff --git a/sysdeps/unix/configure b/sysdeps/unix/configure
index 4fb599a72c..dfc1c22960 100755
--- a/sysdeps/unix/configure
+++ b/sysdeps/unix/configure
@@ -65,7 +65,7 @@ for unix_function in \
getitimer setitimer \
getdomainname/getdomain=bsd/bsd4.4 \
setdomainname/setdomain=bsd/bsd4.4 \
- profil=bsd \
+ profil=bsd readv=bsd writev=bsd \
getpriority setpriority \
getrlimit setrlimit
do
@@ -78,7 +78,7 @@ do
eval "unix_syscall=`echo $unix_function | \
sed -e 's@=\(.*\)$@ unix_srcdir=\1@' \
-e 's@/\(.*\)$@ unix_srcname=\1@'`"
- test -z "$unix_srcname" && unix_srcname=$unix_function
+ test -z "$unix_srcname" && unix_srcname=$unix_syscall
unix_implementor=none
for unix_dir in $sysnames; do
@@ -90,11 +90,13 @@ do
fi
done
- # mkdir and rmdir have implementations in unix/sysv, but
- # the simple syscall versions are preferable if available.
- test $unix_syscall = mkdir -o $unix_syscall = rmdir && \
- test $unix_implementor = unix/sysv && \
- unix_implementor=generic
+ case $unix_syscall in
+ mkdir|rmdir)
+ # mkdir and rmdir have implementations in unix/sysv, but
+ # the simple syscall versions are preferable if available.
+ test $unix_implementor = unix/sysv && unix_implementor=generic
+ ;;
+ esac
case $unix_implementor in
none|stub|generic|posix)