Bugzilla bug #45181: improvement for imported fd's on NT.
Modified files: _winnt.h, prsocket.c, ntio.c
This commit is contained in:
Родитель
114b9e923f
Коммит
341173dcbf
|
@ -69,7 +69,7 @@
|
|||
#define _PR_HAVE_PEEK_BUFFER
|
||||
#define _PR_PEEK_BUFFER_MAX (32 * 1024)
|
||||
#define _PR_FD_NEED_EMULATE_MSG_PEEK(fd) \
|
||||
(!(fd)->secret->nonblocking && !(fd)->secret->inheritable)
|
||||
(!(fd)->secret->nonblocking && (fd)->secret->inheritable != _PR_TRI_TRUE)
|
||||
|
||||
/* --- Common User-Thread/Native-Thread Definitions --------------------- */
|
||||
|
||||
|
|
|
@ -422,8 +422,7 @@ PRIntervalTime timeout)
|
|||
fd2->secret->nonblocking = fd->secret->nonblocking;
|
||||
fd2->secret->inheritable = fd->secret->inheritable;
|
||||
#ifdef WINNT
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd2->secret->inheritable);
|
||||
if (!fd2->secret->nonblocking && !fd2->secret->inheritable) {
|
||||
if (!fd2->secret->nonblocking && fd2->secret->inheritable != _PR_TRI_TRUE) {
|
||||
/*
|
||||
* The new socket has been associated with an I/O
|
||||
* completion port. There is no going back.
|
||||
|
|
|
@ -119,6 +119,21 @@ static PRInt32 _nt_nonblock_writev(PRFileDesc *fd, const PRIOVec *iov, int size,
|
|||
static PRInt32 _nt_nonblock_sendto(PRFileDesc *, const char *, int, const struct sockaddr *, int, PRIntervalTime);
|
||||
static PRInt32 _nt_nonblock_recvfrom(PRFileDesc *, char *, int, struct sockaddr *, int *, PRIntervalTime);
|
||||
|
||||
/*
|
||||
* We cannot associate a fd (a socket) with an I/O completion port
|
||||
* if the fd is nonblocking or inheritable.
|
||||
*
|
||||
* Nonblocking socket I/O won't work if the socket is associated with
|
||||
* an I/O completion port.
|
||||
*
|
||||
* An inheritable fd cannot be associated with an I/O completion port
|
||||
* because the completion notification of async I/O initiated by the
|
||||
* child process is still posted to the I/O completion port in the
|
||||
* parent process.
|
||||
*/
|
||||
#define _NT_USE_NB_IO(fd) \
|
||||
((fd)->secret->nonblocking || (fd)->secret->inheritable == _PR_TRI_TRUE)
|
||||
|
||||
/*
|
||||
* UDP support
|
||||
*
|
||||
|
@ -1260,8 +1275,7 @@ _PR_MD_FAST_ACCEPT(PRFileDesc *fd, PRNetAddr *raddr, PRUint32 *rlen,
|
|||
PRUint32 llen, err;
|
||||
int rv;
|
||||
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (fd->secret->nonblocking || fd->secret->inheritable) {
|
||||
if (_NT_USE_NB_IO(fd)) {
|
||||
if (!fd->secret->md.io_model_committed) {
|
||||
rv = _md_MakeNonblock((HANDLE)osfd);
|
||||
PR_ASSERT(0 != rv);
|
||||
|
@ -1678,8 +1692,7 @@ _PR_MD_RECV(PRFileDesc *fd, void *buf, PRInt32 amount, PRIntn flags,
|
|||
int bytes;
|
||||
int rv, err;
|
||||
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (fd->secret->nonblocking || fd->secret->inheritable) {
|
||||
if (_NT_USE_NB_IO(fd)) {
|
||||
if (!fd->secret->md.io_model_committed) {
|
||||
rv = _md_MakeNonblock((HANDLE)osfd);
|
||||
PR_ASSERT(0 != rv);
|
||||
|
@ -1778,8 +1791,7 @@ _PR_MD_SEND(PRFileDesc *fd, const void *buf, PRInt32 amount, PRIntn flags,
|
|||
int bytes;
|
||||
int rv, err;
|
||||
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (fd->secret->nonblocking || fd->secret->inheritable) {
|
||||
if (_NT_USE_NB_IO(fd)) {
|
||||
if (!fd->secret->md.io_model_committed) {
|
||||
rv = _md_MakeNonblock((HANDLE)osfd);
|
||||
PR_ASSERT(0 != rv);
|
||||
|
@ -1877,11 +1889,10 @@ _PR_MD_SENDTO(PRFileDesc *fd, const void *buf, PRInt32 amount, PRIntn flags,
|
|||
PR_ASSERT(0 != rv);
|
||||
fd->secret->md.io_model_committed = PR_TRUE;
|
||||
}
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (!fd->secret->nonblocking && !fd->secret->inheritable)
|
||||
return pt_SendTo(osfd, buf, amount, flags, addr, addrlen, timeout);
|
||||
else
|
||||
if (_NT_USE_NB_IO(fd))
|
||||
return _nt_nonblock_sendto(fd, buf, amount, (struct sockaddr *)addr, addrlen, timeout);
|
||||
else
|
||||
return pt_SendTo(osfd, buf, amount, flags, addr, addrlen, timeout);
|
||||
}
|
||||
|
||||
PRInt32
|
||||
|
@ -1896,11 +1907,10 @@ _PR_MD_RECVFROM(PRFileDesc *fd, void *buf, PRInt32 amount, PRIntn flags,
|
|||
PR_ASSERT(0 != rv);
|
||||
fd->secret->md.io_model_committed = PR_TRUE;
|
||||
}
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (!fd->secret->nonblocking && !fd->secret->inheritable)
|
||||
return pt_RecvFrom(osfd, buf, amount, flags, addr, addrlen, timeout);
|
||||
else
|
||||
if (_NT_USE_NB_IO(fd))
|
||||
return _nt_nonblock_recvfrom(fd, buf, amount, (struct sockaddr *)addr, addrlen, timeout);
|
||||
else
|
||||
return pt_RecvFrom(osfd, buf, amount, flags, addr, addrlen, timeout);
|
||||
}
|
||||
|
||||
/* XXXMB - for now this is a sockets call only */
|
||||
|
@ -1912,8 +1922,7 @@ _PR_MD_WRITEV(PRFileDesc *fd, const PRIOVec *iov, PRInt32 iov_size, PRIntervalTi
|
|||
int sent = 0;
|
||||
int rv;
|
||||
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (fd->secret->nonblocking || fd->secret->inheritable) {
|
||||
if (_NT_USE_NB_IO(fd)) {
|
||||
if (!fd->secret->md.io_model_committed) {
|
||||
rv = _md_MakeNonblock((HANDLE)osfd);
|
||||
PR_ASSERT(0 != rv);
|
||||
|
@ -2170,7 +2179,6 @@ _PR_MD_READ(PRFileDesc *fd, void *buf, PRInt32 len)
|
|||
LONG hiOffset = 0;
|
||||
LONG loOffset;
|
||||
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (!fd->secret->md.sync_file_io) {
|
||||
PRThread *me = _PR_MD_CURRENT_THREAD();
|
||||
|
||||
|
@ -2184,7 +2192,7 @@ _PR_MD_READ(PRFileDesc *fd, void *buf, PRInt32 len)
|
|||
me->md.overlapped.overlapped.Offset = SetFilePointer((HANDLE)f, 0, &me->md.overlapped.overlapped.OffsetHigh, FILE_CURRENT);
|
||||
PR_ASSERT((me->md.overlapped.overlapped.Offset != 0xffffffff) || (GetLastError() == NO_ERROR));
|
||||
|
||||
if (fd->secret->inheritable) {
|
||||
if (fd->secret->inheritable == _PR_TRI_TRUE) {
|
||||
rv = ReadFile((HANDLE)f,
|
||||
(LPVOID)buf,
|
||||
len,
|
||||
|
@ -2322,7 +2330,6 @@ _PR_MD_WRITE(PRFileDesc *fd, void *buf, PRInt32 len)
|
|||
LONG hiOffset = 0;
|
||||
LONG loOffset;
|
||||
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN != fd->secret->inheritable);
|
||||
if (!fd->secret->md.sync_file_io) {
|
||||
PRThread *me = _PR_MD_CURRENT_THREAD();
|
||||
|
||||
|
@ -2336,7 +2343,7 @@ _PR_MD_WRITE(PRFileDesc *fd, void *buf, PRInt32 len)
|
|||
me->md.overlapped.overlapped.Offset = SetFilePointer((HANDLE)f, 0, &me->md.overlapped.overlapped.OffsetHigh, FILE_CURRENT);
|
||||
PR_ASSERT((me->md.overlapped.overlapped.Offset != 0xffffffff) || (GetLastError() == NO_ERROR));
|
||||
|
||||
if (fd->secret->inheritable) {
|
||||
if (fd->secret->inheritable == _PR_TRI_TRUE) {
|
||||
rv = WriteFile((HANDLE)f,
|
||||
(LPVOID)buf,
|
||||
len,
|
||||
|
@ -2648,20 +2655,10 @@ _PR_MD_SET_FD_INHERITABLE(PRFileDesc *fd, PRBool inheritable)
|
|||
void
|
||||
_PR_MD_INIT_FD_INHERITABLE(PRFileDesc *fd, PRBool imported)
|
||||
{
|
||||
DWORD flags;
|
||||
|
||||
/*
|
||||
* On NT, fd->secret->inheritable is used to decide whether
|
||||
* we can associate the file handle with the I/O completion
|
||||
* port, so we must not set it to _PR_TRI_UNKNOWN.
|
||||
*/
|
||||
fd->secret->inheritable = _PR_TRI_FALSE;
|
||||
if (imported) {
|
||||
if (GetHandleInformation((HANDLE)fd->secret->md.osfd, &flags)) {
|
||||
if (flags & HANDLE_FLAG_INHERIT) {
|
||||
fd->secret->inheritable = _PR_TRI_TRUE;
|
||||
}
|
||||
}
|
||||
fd->secret->inheritable = _PR_TRI_UNKNOWN;
|
||||
} else {
|
||||
fd->secret->inheritable = _PR_TRI_FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2670,6 +2667,10 @@ _PR_MD_QUERY_FD_INHERITABLE(PRFileDesc *fd)
|
|||
{
|
||||
DWORD flags;
|
||||
|
||||
PR_ASSERT(_PR_TRI_UNKNOWN == fd->secret->inheritable);
|
||||
if (fd->secret->md.io_model_committed) {
|
||||
return;
|
||||
}
|
||||
if (GetHandleInformation((HANDLE)fd->secret->md.osfd, &flags)) {
|
||||
if (flags & HANDLE_FLAG_INHERIT) {
|
||||
fd->secret->inheritable = _PR_TRI_TRUE;
|
||||
|
|
Загрузка…
Ссылка в новой задаче