* fhandler.h (fhandler_pipe::hit_eof): New method.
(writepipe_exists): New class element. (orig_pid): Ditto. (id): Ditto. (is_slow): Eliminate. * pipe.cc (fhandler_pipe::set_close_on_exec): Set inheritance on writepipe_exists, if it exists. (fhandler_pipe::hit_eof): New method, modelled after tty. (fhandler_pipe::dup): Duplicate writepipe_exists, if it exists. (make_pipe): Set up a dummy event for pipes on windows 9x. The nonexistence of this event means that the write side of the pipe has closed. (_dup): Move to syscalls.cc (_dup2): Ditto. * dtable.cc (dtable::build_fhandler): Fill out set_names here, if appropriate. * syscalls.cc (_open): Call set_names in build_fhandler.
This commit is contained in:
parent
4367ec036f
commit
35f879a6d0
@ -1,3 +1,25 @@
|
|||||||
|
Mon Sep 24 17:41:03 2001 Christopher Faylor <cgf@redhat.com>
|
||||||
|
|
||||||
|
* fhandler.h (fhandler_pipe::hit_eof): New method.
|
||||||
|
(writepipe_exists): New class element.
|
||||||
|
(orig_pid): Ditto.
|
||||||
|
(id): Ditto.
|
||||||
|
(is_slow): Eliminate.
|
||||||
|
* pipe.cc (fhandler_pipe::set_close_on_exec): Set inheritance on
|
||||||
|
writepipe_exists, if it exists.
|
||||||
|
(fhandler_pipe::hit_eof): New method, modelled after tty.
|
||||||
|
(fhandler_pipe::dup): Duplicate writepipe_exists, if it exists.
|
||||||
|
(make_pipe): Set up a dummy event for pipes on windows 9x. The
|
||||||
|
nonexistence of this event means that the write side of the
|
||||||
|
pipe has closed.
|
||||||
|
(_dup): Move to syscalls.cc
|
||||||
|
(_dup2): Ditto.
|
||||||
|
|
||||||
|
* dtable.cc (dtable::build_fhandler): Fill out set_names here, if
|
||||||
|
appropriate.
|
||||||
|
* syscalls.cc (_open): Call set_names in build_fhandler.
|
||||||
|
|
||||||
|
|
||||||
Sun Sep 23 16:55:00 2001 Corinna Vinschen <corinna@vinschen.de>
|
Sun Sep 23 16:55:00 2001 Corinna Vinschen <corinna@vinschen.de>
|
||||||
|
|
||||||
* syscalls.cc (_open): Set name in fhandler object after successful
|
* syscalls.cc (_open): Set name in fhandler object after successful
|
||||||
|
@ -232,6 +232,7 @@ dtable::build_fhandler (int fd, const char *name, HANDLE handle, path_conv *pc)
|
|||||||
{
|
{
|
||||||
int unit;
|
int unit;
|
||||||
DWORD devn;
|
DWORD devn;
|
||||||
|
fhandler_base *fh;
|
||||||
|
|
||||||
if (!pc)
|
if (!pc)
|
||||||
devn = get_device_number (name, unit);
|
devn = get_device_number (name, unit);
|
||||||
@ -265,7 +266,10 @@ dtable::build_fhandler (int fd, const char *name, HANDLE handle, path_conv *pc)
|
|||||||
devn = FH_DISK;
|
devn = FH_DISK;
|
||||||
}
|
}
|
||||||
|
|
||||||
return build_fhandler (fd, devn, name, unit);
|
fh = build_fhandler (fd, devn, name, unit);
|
||||||
|
if (pc)
|
||||||
|
fh->set_name (name, *pc);
|
||||||
|
return fh;
|
||||||
}
|
}
|
||||||
|
|
||||||
fhandler_base *
|
fhandler_base *
|
||||||
|
@ -368,7 +368,7 @@ public:
|
|||||||
virtual HANDLE& get_handle () { return io_handle; }
|
virtual HANDLE& get_handle () { return io_handle; }
|
||||||
virtual HANDLE& get_io_handle () { return io_handle; }
|
virtual HANDLE& get_io_handle () { return io_handle; }
|
||||||
virtual HANDLE& get_output_handle () { return io_handle; }
|
virtual HANDLE& get_output_handle () { return io_handle; }
|
||||||
virtual BOOL hit_eof () {return FALSE;}
|
virtual bool hit_eof () {return FALSE;}
|
||||||
virtual select_record *select_read (select_record *s);
|
virtual select_record *select_read (select_record *s);
|
||||||
virtual select_record *select_write (select_record *s);
|
virtual select_record *select_write (select_record *s);
|
||||||
virtual select_record *select_except (select_record *s);
|
virtual select_record *select_except (select_record *s);
|
||||||
@ -437,10 +437,12 @@ public:
|
|||||||
class fhandler_pipe: public fhandler_base
|
class fhandler_pipe: public fhandler_base
|
||||||
{
|
{
|
||||||
HANDLE guard;
|
HANDLE guard;
|
||||||
|
HANDLE writepipe_exists;
|
||||||
|
DWORD orig_pid;
|
||||||
|
unsigned id;
|
||||||
public:
|
public:
|
||||||
fhandler_pipe (const char *name = 0, DWORD devtype = FH_PIPE);
|
fhandler_pipe (const char *name = 0, DWORD devtype = FH_PIPE);
|
||||||
off_t lseek (off_t offset, int whence);
|
off_t lseek (off_t offset, int whence);
|
||||||
BOOL is_slow () {return !wincap.has_unreliable_pipes ();}
|
|
||||||
select_record *select_read (select_record *s);
|
select_record *select_read (select_record *s);
|
||||||
select_record *select_write (select_record *s);
|
select_record *select_write (select_record *s);
|
||||||
select_record *select_except (select_record *s);
|
select_record *select_except (select_record *s);
|
||||||
@ -450,6 +452,8 @@ public:
|
|||||||
int close ();
|
int close ();
|
||||||
void create_guard (SECURITY_ATTRIBUTES *sa) {guard = CreateMutex (sa, FALSE, NULL);}
|
void create_guard (SECURITY_ATTRIBUTES *sa) {guard = CreateMutex (sa, FALSE, NULL);}
|
||||||
int dup (fhandler_base *child);
|
int dup (fhandler_base *child);
|
||||||
|
bool hit_eof ();
|
||||||
|
friend int make_pipe (int fildes[2], unsigned int psize, int mode);
|
||||||
};
|
};
|
||||||
|
|
||||||
class fhandler_dev_raw: public fhandler_base
|
class fhandler_dev_raw: public fhandler_base
|
||||||
@ -863,7 +867,7 @@ public:
|
|||||||
char *ptsname ();
|
char *ptsname ();
|
||||||
|
|
||||||
void set_close_on_exec (int val);
|
void set_close_on_exec (int val);
|
||||||
BOOL hit_eof ();
|
bool hit_eof ();
|
||||||
};
|
};
|
||||||
|
|
||||||
class fhandler_tty_master: public fhandler_pty_master
|
class fhandler_tty_master: public fhandler_pty_master
|
||||||
|
@ -223,7 +223,7 @@ process_input (void *)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
BOOL
|
bool
|
||||||
fhandler_pty_master::hit_eof ()
|
fhandler_pty_master::hit_eof ()
|
||||||
{
|
{
|
||||||
if (get_ttyp ()->was_opened && !get_ttyp ()->slave_alive ())
|
if (get_ttyp ()->was_opened && !get_ttyp ()->slave_alive ())
|
||||||
|
@ -28,8 +28,8 @@ the result of a vfork and closes the extra file handles.
|
|||||||
|
|
||||||
This all relies on the fact that the child in a vfork call can affect
|
This all relies on the fact that the child in a vfork call can affect
|
||||||
just about everything in the parent except for the parent's fds.
|
just about everything in the parent except for the parent's fds.
|
||||||
The assumption is that you don't return from the call that invoked the
|
The assumption is that a vfork is always just used as a method for
|
||||||
vfork.
|
starting a program.
|
||||||
|
|
||||||
The assumption is also that all of this is much faster than the
|
The assumption is also that all of this is much faster than the
|
||||||
slow method that cygwin uses to implement fork().
|
slow method that cygwin uses to implement fork().
|
||||||
|
@ -18,9 +18,15 @@ details. */
|
|||||||
#include "dtable.h"
|
#include "dtable.h"
|
||||||
#include "cygheap.h"
|
#include "cygheap.h"
|
||||||
#include "thread.h"
|
#include "thread.h"
|
||||||
|
#include "sigproc.h"
|
||||||
|
#include "pinfo.h"
|
||||||
|
|
||||||
|
static unsigned pipecount;
|
||||||
|
static const NO_COPY char pipeid_fmt[] = "stupid_pipe.%u.%u";
|
||||||
|
|
||||||
fhandler_pipe::fhandler_pipe (const char *name, DWORD devtype) :
|
fhandler_pipe::fhandler_pipe (const char *name, DWORD devtype) :
|
||||||
fhandler_base (devtype, name), guard (0)
|
fhandler_base (devtype, name),
|
||||||
|
guard (0), writepipe_exists(0), orig_pid (0), id (0)
|
||||||
{
|
{
|
||||||
set_cb (sizeof *this);
|
set_cb (sizeof *this);
|
||||||
}
|
}
|
||||||
@ -37,7 +43,10 @@ void
|
|||||||
fhandler_pipe::set_close_on_exec (int val)
|
fhandler_pipe::set_close_on_exec (int val)
|
||||||
{
|
{
|
||||||
this->fhandler_base::set_close_on_exec (val);
|
this->fhandler_base::set_close_on_exec (val);
|
||||||
|
if (guard)
|
||||||
set_inheritance (guard, val);
|
set_inheritance (guard, val);
|
||||||
|
if (writepipe_exists)
|
||||||
|
set_inheritance (writepipe_exists, val);
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
@ -53,9 +62,27 @@ int fhandler_pipe::close ()
|
|||||||
int res = this->fhandler_base::close ();
|
int res = this->fhandler_base::close ();
|
||||||
if (guard)
|
if (guard)
|
||||||
CloseHandle (guard);
|
CloseHandle (guard);
|
||||||
|
if (writepipe_exists)
|
||||||
|
{debug_printf ("writepipe_exists closed");
|
||||||
|
CloseHandle (writepipe_exists);
|
||||||
|
}
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
fhandler_pipe::hit_eof ()
|
||||||
|
{
|
||||||
|
char buf[80];
|
||||||
|
HANDLE ev;
|
||||||
|
if (!orig_pid)
|
||||||
|
return bg_ok;
|
||||||
|
__small_sprintf (buf, pipeid_fmt, orig_pid, id);
|
||||||
|
if ((ev = OpenEvent (EVENT_ALL_ACCESS, FALSE, buf)))
|
||||||
|
CloseHandle (ev);
|
||||||
|
debug_printf ("%s %p", buf, ev);
|
||||||
|
return ev == NULL;
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
fhandler_pipe::dup (fhandler_base *child)
|
fhandler_pipe::dup (fhandler_base *child)
|
||||||
{
|
{
|
||||||
@ -70,10 +97,21 @@ fhandler_pipe::dup (fhandler_base *child)
|
|||||||
else if (!DuplicateHandle (hMainProc, guard, hMainProc, &ftp->guard, 0, 1,
|
else if (!DuplicateHandle (hMainProc, guard, hMainProc, &ftp->guard, 0, 1,
|
||||||
DUPLICATE_SAME_ACCESS))
|
DUPLICATE_SAME_ACCESS))
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
|
if (writepipe_exists == NULL)
|
||||||
|
ftp->writepipe_exists = NULL;
|
||||||
|
else if (!DuplicateHandle (hMainProc, writepipe_exists, hMainProc,
|
||||||
|
&ftp->writepipe_exists, 0, 1,
|
||||||
|
DUPLICATE_SAME_ACCESS))
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
ftp->id = id;
|
||||||
|
ftp->orig_pid = orig_pid;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int
|
|
||||||
|
int
|
||||||
make_pipe (int fildes[2], unsigned int psize, int mode)
|
make_pipe (int fildes[2], unsigned int psize, int mode)
|
||||||
{
|
{
|
||||||
SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "make_pipe");
|
SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "make_pipe");
|
||||||
@ -108,6 +146,15 @@ make_pipe (int fildes[2], unsigned int psize, int mode)
|
|||||||
|
|
||||||
res = 0;
|
res = 0;
|
||||||
fhr->create_guard (sa);
|
fhr->create_guard (sa);
|
||||||
|
if (wincap.has_unreliable_pipes ())
|
||||||
|
{
|
||||||
|
char buf[80];
|
||||||
|
int count = pipecount++; /* FIXME: Should this be InterlockedIncrement? */
|
||||||
|
__small_sprintf (buf, pipeid_fmt, myself->pid, count);
|
||||||
|
fhw->writepipe_exists = CreateEvent (sa, TRUE, FALSE, buf);
|
||||||
|
fhr->orig_pid = myself->pid;
|
||||||
|
fhr->id = count;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
syscall_printf ("%d = make_pipe ([%d, %d], %d, %p)", res, fdr, fdw, psize, mode);
|
syscall_printf ("%d = make_pipe ([%d, %d], %d, %p)", res, fdr, fdw, psize, mode);
|
||||||
@ -131,22 +178,3 @@ _pipe (int filedes[2], unsigned int psize, int mode)
|
|||||||
cygheap->fdtab[filedes[0]]->set_r_no_interrupt (1);
|
cygheap->fdtab[filedes[0]]->set_r_no_interrupt (1);
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
|
||||||
dup (int fd)
|
|
||||||
{
|
|
||||||
int res;
|
|
||||||
SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
|
|
||||||
|
|
||||||
res = dup2 (fd, cygheap->fdtab.find_unused_handle ());
|
|
||||||
|
|
||||||
ReleaseResourceLock(LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
|
|
||||||
|
|
||||||
return res;
|
|
||||||
}
|
|
||||||
|
|
||||||
int
|
|
||||||
dup2 (int oldfd, int newfd)
|
|
||||||
{
|
|
||||||
return cygheap->fdtab.dup2 (oldfd, newfd);
|
|
||||||
}
|
|
||||||
|
@ -420,11 +420,6 @@ peek_pipe (select_record *s, int ignra, HANDLE guard_mutex = NULL)
|
|||||||
gotone = 1;
|
gotone = 1;
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
if (fh->bg_check (SIGTTIN) <= bg_eof)
|
|
||||||
{
|
|
||||||
gotone = s->read_ready = 1;
|
|
||||||
goto out;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (fh->get_device ())
|
switch (fh->get_device ())
|
||||||
{
|
{
|
||||||
@ -444,6 +439,12 @@ peek_pipe (select_record *s, int ignra, HANDLE guard_mutex = NULL)
|
|||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (fh->bg_check (SIGTTIN) <= bg_eof)
|
||||||
|
{
|
||||||
|
gotone = s->read_ready = 1;
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (fh->get_device () == FH_PIPEW)
|
if (fh->get_device () == FH_PIPEW)
|
||||||
|
@ -81,6 +81,25 @@ check_ttys_fds (void)
|
|||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
dup (int fd)
|
||||||
|
{
|
||||||
|
int res;
|
||||||
|
SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
|
||||||
|
|
||||||
|
res = dup2 (fd, cygheap->fdtab.find_unused_handle ());
|
||||||
|
|
||||||
|
ReleaseResourceLock(LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
|
||||||
|
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
dup2 (int oldfd, int newfd)
|
||||||
|
{
|
||||||
|
return cygheap->fdtab.dup2 (oldfd, newfd);
|
||||||
|
}
|
||||||
|
|
||||||
extern "C" int
|
extern "C" int
|
||||||
_unlink (const char *ourname)
|
_unlink (const char *ourname)
|
||||||
{
|
{
|
||||||
@ -489,10 +508,7 @@ _open (const char *unix_path, int flags, ...)
|
|||||||
path_conv pc;
|
path_conv pc;
|
||||||
if (!(fh = cygheap->fdtab.build_fhandler (fd, unix_path, NULL, &pc)))
|
if (!(fh = cygheap->fdtab.build_fhandler (fd, unix_path, NULL, &pc)))
|
||||||
res = -1; // errno already set
|
res = -1; // errno already set
|
||||||
else
|
else if (!fh->open (pc, flags, (mode & 07777) & ~cygheap->umask))
|
||||||
{
|
|
||||||
fh->set_name (unix_path, pc.get_win32 ());
|
|
||||||
if (!fh->open (pc, flags, (mode & 07777) & ~cygheap->umask))
|
|
||||||
{
|
{
|
||||||
cygheap->fdtab.release (fd);
|
cygheap->fdtab.release (fd);
|
||||||
res = -1;
|
res = -1;
|
||||||
@ -500,7 +516,6 @@ _open (const char *unix_path, int flags, ...)
|
|||||||
else if ((res = fd) <= 2)
|
else if ((res = fd) <= 2)
|
||||||
set_std_handle (res);
|
set_std_handle (res);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
ReleaseResourceLock (LOCK_FD_LIST,WRITE_LOCK|READ_LOCK," open");
|
ReleaseResourceLock (LOCK_FD_LIST,WRITE_LOCK|READ_LOCK," open");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user