Overlapped I/O without an hEvent

Martin Wilck Martin.Wilck at Fujitsu-Siemens.com
Tue Nov 26 05:01:24 CST 2002


Am Die, 2002-11-26 um 00.33 schrieb Ryan Reading:

> I finally got it working, but not by ignoring the hEvent member in the
> case that it is NULL.  I tried that first (before I understood the
> problem better), but it didn't work.  The GetOverlappedResult()
> implementation was not going to work with hEvent == NULL.  

Please try this patch, where GetOverlappedResult is modified, too:

Index: files/file.c
===================================================================
RCS file: /home/wine/wine/files/file.c,v
retrieving revision 1.170
diff -u -r1.170 file.c
--- files/file.c	21 Nov 2002 03:45:03 -0000	1.170
+++ files/file.c	26 Nov 2002 10:34:21 -0000
@@ -1593,32 +1593,40 @@
         ERR("lpOverlapped was null\n");
         return FALSE;
     }
-    if(!lpOverlapped->hEvent)
+    if( lpOverlapped->hEvent )
     {
-        ERR("lpOverlapped->hEvent was null\n");
-        return FALSE;
+        if ( bWait )
+        {
+            do {
+                TRACE("waiting on %p\n",lpOverlapped);
+                r = WaitForSingleObjectEx(lpOverlapped->hEvent, INFINITE, TRUE);
+                TRACE("wait on %p returned %ld\n",lpOverlapped,r);
+            } while (r==STATUS_USER_APC);
+        }
+        else if ( lpOverlapped->Internal == STATUS_PENDING )
+        {
+            /* Wait in order to give APCs a chance to run. */
+            /* This is cheating, so we must set the event again in case of success -
+               it may be a non-manual reset event. */
+            do {
+                TRACE("waiting on %p\n",lpOverlapped);
+                r = WaitForSingleObjectEx(lpOverlapped->hEvent, 0, TRUE);
+                TRACE("wait on %p returned %ld\n",lpOverlapped,r);
+            } while (r==STATUS_USER_APC);
+            if ( r == WAIT_OBJECT_0 )
+                NtSetEvent ( lpOverlapped->hEvent, NULL );
+        }
     }
-
-    if ( bWait )
+    else
     {
-        do {
-            TRACE("waiting on %p\n",lpOverlapped);
-            r = WaitForSingleObjectEx(lpOverlapped->hEvent, INFINITE, TRUE);
-            TRACE("wait on %p returned %ld\n",lpOverlapped,r);
-        } while (r==STATUS_USER_APC);
-    }
-    else if ( lpOverlapped->Internal == STATUS_PENDING )
-    {
-        /* Wait in order to give APCs a chance to run. */
-        /* This is cheating, so we must set the event again in case of success -
-           it may be a non-manual reset event. */
-        do {
-            TRACE("waiting on %p\n",lpOverlapped);
-            r = WaitForSingleObjectEx(lpOverlapped->hEvent, 0, TRUE);
-            TRACE("wait on %p returned %ld\n",lpOverlapped,r);
-        } while (r==STATUS_USER_APC);
-        if ( r == WAIT_OBJECT_0 )
-            NtSetEvent ( lpOverlapped->hEvent, NULL );
+        /* hEvent == NULL: we cannot wait.
+         * FIXME: According to MSDN, NT, Win2k, and XP use the hFile handle for notification
+         * in this case. */
+        if ( bWait )
+        {
+            SetLastError ( ERROR_INVALID_HANDLE );
+            return FALSE;
+        }
     }
 
     if(lpTransferred)
@@ -1818,7 +1831,7 @@
     if (flags & FD_FLAG_OVERLAPPED)
     {
 	if (unix_handle == -1) return FALSE;
-        if ( (overlapped==NULL) || NtResetEvent( overlapped->hEvent, NULL ) )
+        if ( (overlapped==NULL) || ( overlapped->hEvent && NtResetEvent( overlapped->hEvent, NULL ) ) )
         {
             TRACE("Overlapped not specified or invalid event flag\n");
 	    close(unix_handle);
@@ -2042,7 +2055,7 @@
     if (flags & FD_FLAG_OVERLAPPED)
     {
 	if (unix_handle == -1) return FALSE;
-        if ( (overlapped==NULL) || NtResetEvent( overlapped->hEvent, NULL ) )
+        if ( (overlapped==NULL) || ( overlapped->hEvent && NtResetEvent( overlapped->hEvent, NULL ) ) )
         {
             TRACE("Overlapped not specified or invalid event flag\n");
 	    close(unix_handle);
Index: include/async.h
===================================================================
RCS file: /home/wine/wine/include/async.h,v
retrieving revision 1.5
diff -u -r1.5 async.h
--- include/async.h	4 May 2002 18:37:08 -0000	1.5
+++ include/async.h	26 Nov 2002 10:53:28 -0000
@@ -73,7 +73,7 @@
     ovp->next = ovp->prev = NULL;
 
     close( ovp->fd );
-    if( ovp->event != INVALID_HANDLE_VALUE )
+    if( ovp->event && ovp->event != INVALID_HANDLE_VALUE )
         NtSetEvent( ovp->event, NULL );
 
     if ( ovp->ops->call_completion )

-- 
Martin Wilck                Phone: +49 5251 8 15113
Fujitsu Siemens Computers   Fax:   +49 5251 8 20409
Heinz-Nixdorf-Ring 1	    mailto:Martin.Wilck at Fujitsu-Siemens.com
D-33106 Paderborn           http://www.fujitsu-siemens.com/primergy








More information about the wine-devel mailing list