aboutsummaryrefslogtreecommitdiff
path: root/sysdeps/mach/hurd/dup2.c
diff options
context:
space:
mode:
authorRoland McGrath <roland@gnu.org>1995-05-04 09:00:10 +0000
committerRoland McGrath <roland@gnu.org>1995-05-04 09:00:10 +0000
commite4448b6f58406744ff1a5f400b492ba27e466b56 (patch)
tree84725f363a935ae8498d5f0eaa3a44239af3b5df /sysdeps/mach/hurd/dup2.c
parentd66e34cd423425c348bcc83df127dd19711b0b9a (diff)
downloadglibc-e4448b6f58406744ff1a5f400b492ba27e466b56.tar
glibc-e4448b6f58406744ff1a5f400b492ba27e466b56.tar.gz
glibc-e4448b6f58406744ff1a5f400b492ba27e466b56.tar.bz2
glibc-e4448b6f58406744ff1a5f400b492ba27e466b56.zip
Wed May 3 11:56:35 1995 Roland McGrath <roland@churchy.gnu.ai.mit.edu>
* sysdeps/mach/hurd/dup2.c: Fixed broken test in last change. * elf/dl-error.c (_dl_catch_error): Actually call the OPERATE function. Duh. * hurd/Makefile (distribute): Added hurdstartup.h. * hurd/hurd.h: Remove _hurd_startup decl. * hurd/hurd/ioctl.h (_HURD_HANDLE_IOCTLS): Use __attribute__ ((__unused__)) instead of gratuitous self reference. * sysdeps/mach/hurd/dup2.c: Call _hurd_alloc_fd to expand the table if FD2 doesn't fit. * sysdeps/mach/hurd/getdtsz.c: Return the RLIM_NOFILE soft limit, not the current table size. * sysdeps/i386/init-first.c: New file. * sysdeps/stub/init-first.c: New file.
Diffstat (limited to 'sysdeps/mach/hurd/dup2.c')
-rw-r--r--sysdeps/mach/hurd/dup2.c40
1 files changed, 30 insertions, 10 deletions
diff --git a/sysdeps/mach/hurd/dup2.c b/sysdeps/mach/hurd/dup2.c
index f4ec623b05..c4b16698b8 100644
--- a/sysdeps/mach/hurd/dup2.c
+++ b/sysdeps/mach/hurd/dup2.c
@@ -58,8 +58,7 @@ DEFUN(__dup2, (fd, fd2), int fd AND int fd2)
io_t ctty = _hurd_port_get (&d->ctty, &ctty_ulink);
io_t port = _hurd_port_locked_get (&d->port, &ulink); /* Unlocks D. */
- __mutex_lock (&_hurd_dtable_lock);
- if (fd2 < 0 || fd2 >= _hurd_dtablesize)
+ if (fd2 < 0)
{
errno = EBADF;
fd2 = -1;
@@ -67,16 +66,37 @@ DEFUN(__dup2, (fd, fd2), int fd AND int fd2)
else
{
/* Get a hold of the destination descriptor. */
- struct hurd_fd *d2 = _hurd_dtable[fd2];
- if (d2 == NULL)
+ struct hurd_fd *d2;
+
+ if (fd2 >= _hurd_dtablesize)
+ {
+ /* The table is not large enough to hold the destination
+ descriptor. Enlarge it as necessary to allocate this
+ descriptor. */
+ __mutex_unlock (&_hurd_dtable_lock);
+ /* We still hold FD1's lock, but this is safe because
+ _hurd_alloc_fd will only examine the cells starting
+ at FD2. */
+ d2 = _hurd_alloc_fd (NULL, fd2);
+ if (d2)
+ __spin_unlock (&d2->port.lock);
+ __mutex_lock (&_hurd_dtable_lock);
+ }
+ else
{
- /* Must allocate a new one. We don't initialize the port cells
- with this call so that if it fails (out of memory), we will
- not have already added user references for the ports, which we
- would then have to deallocate. */
- d2 = _hurd_dtable[fd2] = _hurd_new_fd (MACH_PORT_NULL,
- MACH_PORT_NULL);
+ d2 = _hurd_dtable[fd2];
+ if (d2 == NULL)
+ {
+ /* Must allocate a new one. We don't initialize the port
+ cells with this call so that if it fails (out of
+ memory), we will not have already added user
+ references for the ports, which we would then have to
+ deallocate. */
+ d2 = _hurd_dtable[fd2] = _hurd_new_fd (MACH_PORT_NULL,
+ MACH_PORT_NULL);
+ }
}
+
if (d2 == NULL)
{
fd2 = -1;