Commit 193667ec authored by Alexandre Julliard's avatar Alexandre Julliard

ntdll: Fix handling of async cancellation for directory changes.

parent 38b7c883
......@@ -1805,19 +1805,20 @@ static NTSTATUS read_changes_apc( void *user, IO_STATUS_BLOCK *iosb,
NTSTATUS status, void **apc, void **arg )
{
struct read_changes_fileio *fileio = user;
NTSTATUS ret;
int size;
int size = 0;
if (status == STATUS_ALERTED)
{
SERVER_START_REQ( read_change )
{
req->handle = wine_server_obj_handle( fileio->io.handle );
wine_server_set_reply( req, fileio->data, fileio->data_size );
ret = wine_server_call( req );
status = wine_server_call( req );
size = wine_server_reply_size( reply );
}
SERVER_END_REQ;
if (ret == STATUS_SUCCESS && fileio->buffer)
if (status == STATUS_SUCCESS && fileio->buffer)
{
FILE_NOTIFY_INFORMATION *pfni = fileio->buffer;
int i, left = fileio->buffer_size;
......@@ -1827,7 +1828,7 @@ static NTSTATUS read_changes_apc( void *user, IO_STATUS_BLOCK *iosb,
while (size && left >= sizeof(*pfni))
{
/* convert to an NT style path */
for (i=0; i<event->len; i++)
for (i = 0; i < event->len; i++)
if (event->name[i] == '/') event->name[i] = '\\';
pfni->Action = event->action;
......@@ -1851,27 +1852,31 @@ static NTSTATUS read_changes_apc( void *user, IO_STATUS_BLOCK *iosb,
if (size)
{
ret = STATUS_NOTIFY_ENUM_DIR;
status = STATUS_NOTIFY_ENUM_DIR;
size = 0;
}
else
{
*last_entry_offset = 0;
if (last_entry_offset) *last_entry_offset = 0;
size = fileio->buffer_size - left;
}
}
else
{
ret = STATUS_NOTIFY_ENUM_DIR;
status = STATUS_NOTIFY_ENUM_DIR;
size = 0;
}
}
iosb->u.Status = ret;
if (status != STATUS_PENDING)
{
iosb->u.Status = status;
iosb->Information = size;
*apc = fileio->io.apc;
*arg = fileio->io.apc_arg;
release_fileio( &fileio->io );
return ret;
}
return status;
}
#define FILE_NOTIFY_ALL ( \
......
......@@ -99,19 +99,19 @@ static void test_ntncdf(void)
r = pNtNotifyChangeDirectoryFile(hdir,hEvent,NULL,NULL,&iosb,buffer,sizeof buffer,filter,0);
ok(r==STATUS_PENDING, "should return status pending\n");
r = WaitForSingleObject( hEvent, 0 );
r = WaitForSingleObject( hEvent, 100 );
ok( r == STATUS_TIMEOUT, "should timeout\n" );
r = WaitForSingleObject( hdir, 0 );
r = WaitForSingleObject( hdir, 100 );
ok( r == STATUS_TIMEOUT, "should timeout\n" );
r = CreateDirectoryW( subdir, NULL );
ok( r == TRUE, "failed to create directory\n");
r = WaitForSingleObject( hdir, 0 );
r = WaitForSingleObject( hdir, 100 );
ok( r == STATUS_TIMEOUT, "should timeout\n" );
r = WaitForSingleObject( hEvent, 0 );
r = WaitForSingleObject( hEvent, 100 );
ok( r == WAIT_OBJECT_0, "event should be ready\n" );
ok( U(iosb).Status == STATUS_SUCCESS, "information wrong\n");
......@@ -299,7 +299,7 @@ static void test_ntncdf_async(void)
CloseHandle(hdir);
ok(U(iosb).Status == STATUS_SUCCESS, "status wrong\n");
todo_wine ok(U(iosb2).Status == STATUS_CANCELLED, "status wrong\n");
ok(U(iosb2).Status == STATUS_CANCELLED, "status wrong %x\n",U(iosb2).Status);
ok(iosb.Information == 0, "info wrong\n");
ok(iosb2.Information == 0, "info wrong\n");
......
......@@ -272,7 +272,7 @@ void sigio_callback(void)
LIST_FOR_EACH_ENTRY( dir, &change_list, struct dir, entry )
{
if (interlocked_xchg( &dir->notified, 0 ))
fd_async_wake_up( dir->fd, ASYNC_TYPE_WAIT, STATUS_NOTIFY_ENUM_DIR );
fd_async_wake_up( dir->fd, ASYNC_TYPE_WAIT, STATUS_ALERTED );
}
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment