Alexandre Julliard : kernel32:
Rewrite GetOverlappedResult for the new async I/O behavior.
Alexandre Julliard
julliard at wine.codeweavers.com
Tue Jun 5 05:48:12 CDT 2007
Module: wine
Branch: master
Commit: 35ef5df76cf9d282f3df36eec24b3876039650a3
URL: http://source.winehq.org/git/wine.git/?a=commit;h=35ef5df76cf9d282f3df36eec24b3876039650a3
Author: Alexandre Julliard <julliard at winehq.org>
Date: Mon Jun 4 23:03:15 2007 +0200
kernel32: Rewrite GetOverlappedResult for the new async I/O behavior.
---
dlls/kernel32/file.c | 67 ++++++++++----------------------------------
dlls/kernel32/tests/file.c | 2 -
2 files changed, 15 insertions(+), 54 deletions(-)
diff --git a/dlls/kernel32/file.c b/dlls/kernel32/file.c
index be8ca63..a3d6942 100644
--- a/dlls/kernel32/file.c
+++ b/dlls/kernel32/file.c
@@ -539,17 +539,11 @@ BOOL WINAPI WriteFile( HANDLE hFile, LPCVOID buffer, DWORD bytesToWrite,
*
* If successful (and relevant) lpTransferred will hold the number of
* bytes transferred during the async operation.
- *
- * BUGS
- *
- * Currently only works for WaitCommEvent, ReadFile, WriteFile
- * with communications ports.
- *
*/
BOOL WINAPI GetOverlappedResult(HANDLE hFile, LPOVERLAPPED lpOverlapped,
LPDWORD lpTransferred, BOOL bWait)
{
- DWORD r = WAIT_OBJECT_0;
+ NTSTATUS status;
TRACE( "(%p %p %p %x)\n", hFile, lpOverlapped, lpTransferred, bWait );
@@ -558,57 +552,26 @@ BOOL WINAPI GetOverlappedResult(HANDLE hFile, LPOVERLAPPED lpOverlapped,
ERR("lpOverlapped was null\n");
return FALSE;
}
- if ( bWait )
+
+ status = lpOverlapped->Internal;
+ if (status == STATUS_PENDING)
{
- if ( lpOverlapped->hEvent )
+ if (!bWait)
{
- do
- {
- TRACE( "waiting on %p\n", lpOverlapped );
- r = WaitForSingleObjectEx( lpOverlapped->hEvent, INFINITE, TRUE );
- TRACE( "wait on %p returned %d\n", lpOverlapped, r );
- } while ( r == WAIT_IO_COMPLETION );
+ SetLastError( ERROR_IO_INCOMPLETE );
+ return FALSE;
}
- else
- {
- /* busy loop */
- while ( ((volatile OVERLAPPED*)lpOverlapped)->Internal == STATUS_PENDING )
- Sleep( 10 );
- }
- }
- 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 %d\n", lpOverlapped, r );
- } while ( r == WAIT_IO_COMPLETION );
- if ( r == WAIT_OBJECT_0 && lpOverlapped->hEvent )
- NtSetEvent( lpOverlapped->hEvent, NULL );
- }
- if ( r == WAIT_FAILED )
- {
- WARN("wait operation failed\n");
- return FALSE;
+
+ if (WaitForSingleObject( lpOverlapped->hEvent ? lpOverlapped->hEvent : hFile,
+ INFINITE ) == WAIT_FAILED)
+ return FALSE;
+ status = lpOverlapped->Internal;
}
+
if (lpTransferred) *lpTransferred = lpOverlapped->InternalHigh;
- switch ( lpOverlapped->Internal )
- {
- case STATUS_SUCCESS:
- return TRUE;
- case STATUS_PENDING:
- SetLastError( ERROR_IO_INCOMPLETE );
- if ( bWait ) ERR("PENDING status after waiting!\n");
- return FALSE;
- default:
- SetLastError( RtlNtStatusToDosError( lpOverlapped->Internal ) );
- return FALSE;
- }
+ if (status) SetLastError( RtlNtStatusToDosError(status) );
+ return !status;
}
/***********************************************************************
diff --git a/dlls/kernel32/tests/file.c b/dlls/kernel32/tests/file.c
index 89cf0a2..e9f97f5 100644
--- a/dlls/kernel32/tests/file.c
+++ b/dlls/kernel32/tests/file.c
@@ -1768,9 +1768,7 @@ static void test_overlapped(void)
ov.Internal = STATUS_PENDING;
ov.InternalHigh = 0xabcd;
r = GetOverlappedResult(0, &ov, &result, 0);
- todo_wine {
ok( GetLastError() == ERROR_IO_INCOMPLETE, "wrong error %u\n", GetLastError() );
- }
ok( r == FALSE, "should return false\n");
ok( result == 0, "wrong result %u\n", result );
More information about the wine-cvs
mailing list