Added FSCTL_PIPE_LISTEN support.
This commit is contained in:
parent
28f0c36036
commit
f0db7ab06b
|
@ -1310,50 +1310,34 @@ BOOL WINAPI WaitNamedPipeW (LPCWSTR name, DWORD nTimeOut)
|
|||
|
||||
/***********************************************************************
|
||||
* ConnectNamedPipe (KERNEL32.@)
|
||||
*
|
||||
* Connects to a named pipe
|
||||
*
|
||||
* Parameters
|
||||
* hPipe: A handle to a named pipe returned by CreateNamedPipe
|
||||
* overlapped: Optional OVERLAPPED struct
|
||||
*
|
||||
* Return values
|
||||
* TRUE: Success
|
||||
* FALSE: Failure, GetLastError can be called for further details
|
||||
*/
|
||||
BOOL WINAPI ConnectNamedPipe(HANDLE hPipe, LPOVERLAPPED overlapped)
|
||||
{
|
||||
BOOL ret;
|
||||
LPOVERLAPPED pov;
|
||||
OVERLAPPED ov;
|
||||
NTSTATUS status;
|
||||
IO_STATUS_BLOCK status_block;
|
||||
|
||||
TRACE("(%p,%p)\n", hPipe, overlapped);
|
||||
|
||||
if (!overlapped)
|
||||
{
|
||||
memset(&ov, 0, sizeof(ov));
|
||||
ov.hEvent = CreateEventW(NULL, 0, 0, NULL);
|
||||
if (!ov.hEvent) return FALSE;
|
||||
pov = &ov;
|
||||
}
|
||||
else pov = overlapped;
|
||||
if(overlapped)
|
||||
overlapped->Internal = STATUS_PENDING;
|
||||
|
||||
pov->Internal = STATUS_PENDING;
|
||||
status = NtFsControlFile(hPipe, overlapped ? overlapped->hEvent : NULL, NULL, NULL,
|
||||
overlapped ? (IO_STATUS_BLOCK *)overlapped : &status_block,
|
||||
FSCTL_PIPE_LISTEN, NULL, 0, NULL, 0);
|
||||
|
||||
SERVER_START_REQ( connect_named_pipe )
|
||||
{
|
||||
req->handle = hPipe;
|
||||
req->overlapped = pov;
|
||||
req->func = PIPE_CompletionWait;
|
||||
ret = !wine_server_call_err( req );
|
||||
}
|
||||
SERVER_END_REQ;
|
||||
|
||||
if (ret)
|
||||
{
|
||||
if (overlapped)
|
||||
{
|
||||
SetLastError( ERROR_IO_PENDING );
|
||||
ret = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = GetOverlappedResult(hPipe, &ov, NULL, TRUE);
|
||||
CloseHandle(ov.hEvent);
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
if (status == STATUS_SUCCESS) return TRUE;
|
||||
SetLastError( RtlNtStatusToDosError(status) );
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/***********************************************************************
|
||||
|
|
|
@ -862,24 +862,90 @@ NTSTATUS WINAPI NtDeviceIoControlFile(HANDLE DeviceHandle, HANDLE hEvent,
|
|||
return IoStatusBlock->u.Status;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* NtFsControlFile [NTDLL.@]
|
||||
* ZwFsControlFile [NTDLL.@]
|
||||
/***********************************************************************
|
||||
* pipe_completion_wait (Internal)
|
||||
*/
|
||||
static void CALLBACK pipe_completion_wait(HANDLE event, PIO_STATUS_BLOCK iosb, ULONG status)
|
||||
{
|
||||
TRACE("for %p/%p, status=%08lx\n", event, iosb, status);
|
||||
|
||||
if (iosb)
|
||||
iosb->u.Status = status;
|
||||
NtSetEvent(event, NULL);
|
||||
TRACE("done\n");
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
* NtFsControlFile [NTDLL.@]
|
||||
* ZwFsControlFile [NTDLL.@]
|
||||
*
|
||||
* Perform a file system control operation on an open file handle.
|
||||
*
|
||||
* PARAMS
|
||||
* DeviceHandle [I] Handle returned from ZwOpenFile() or ZwCreateFile()
|
||||
* Event [I] Event to signal upon completion (or NULL)
|
||||
* ApcRoutine [I] Callback to call upon completion (or NULL)
|
||||
* ApcContext [I] Context for ApcRoutine (or NULL)
|
||||
* IoStatusBlock [O] Receives information about the operation on return
|
||||
* FsControlCode [I] Control code for the operation to perform
|
||||
* InputBuffer [I] Source for any input data required (or NULL)
|
||||
* InputBufferSize [I] Size of InputBuffer
|
||||
* OutputBuffer [O] Source for any output data returned (or NULL)
|
||||
* OutputBufferSize [I] Size of OutputBuffer
|
||||
*
|
||||
* RETURNS
|
||||
* Success: 0. IoStatusBlock is updated.
|
||||
* Failure: An NTSTATUS error code describing the error.
|
||||
*/
|
||||
NTSTATUS WINAPI NtFsControlFile(HANDLE DeviceHandle, HANDLE Event OPTIONAL, PIO_APC_ROUTINE ApcRoutine,
|
||||
PVOID ApcContext, PIO_STATUS_BLOCK IoStatusBlock, ULONG IoControlCode,
|
||||
PVOID ApcContext, PIO_STATUS_BLOCK IoStatusBlock, ULONG FsControlCode,
|
||||
PVOID InputBuffer, ULONG InputBufferSize, PVOID OutputBuffer, ULONG OutputBufferSize)
|
||||
{
|
||||
NTSTATUS ret;
|
||||
|
||||
TRACE("(%p,%p,%p,%p,%p,0x%08lx,%p,0x%08lx,%p,0x%08lx)\n",
|
||||
DeviceHandle,Event,ApcRoutine,ApcContext,IoStatusBlock,IoControlCode,
|
||||
DeviceHandle,Event,ApcRoutine,ApcContext,IoStatusBlock,FsControlCode,
|
||||
InputBuffer,InputBufferSize,OutputBuffer,OutputBufferSize);
|
||||
|
||||
if(!IoStatusBlock) return STATUS_INVALID_PARAMETER;
|
||||
|
||||
switch(IoControlCode)
|
||||
switch(FsControlCode)
|
||||
{
|
||||
case FSCTL_PIPE_LISTEN :
|
||||
{
|
||||
HANDLE internal_event;
|
||||
|
||||
if(!Event)
|
||||
{
|
||||
OBJECT_ATTRIBUTES obj;
|
||||
InitializeObjectAttributes(&obj, NULL, 0, 0, NULL);
|
||||
ret = NtCreateEvent(&internal_event, EVENT_ALL_ACCESS, &obj, FALSE, FALSE);
|
||||
if(ret != STATUS_SUCCESS) return ret;
|
||||
}
|
||||
|
||||
SERVER_START_REQ(connect_named_pipe)
|
||||
{
|
||||
req->handle = DeviceHandle;
|
||||
req->event = Event ? Event : internal_event;
|
||||
req->func = pipe_completion_wait;
|
||||
ret = wine_server_call(req);
|
||||
}
|
||||
SERVER_END_REQ;
|
||||
|
||||
if(ret == STATUS_SUCCESS)
|
||||
{
|
||||
if(Event)
|
||||
ret = STATUS_PENDING;
|
||||
else
|
||||
{
|
||||
do
|
||||
ret = NtWaitForSingleObject(internal_event, TRUE, NULL);
|
||||
while(ret == STATUS_USER_APC);
|
||||
NtClose(internal_event);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case FSCTL_PIPE_DISCONNECT :
|
||||
SERVER_START_REQ(disconnect_named_pipe)
|
||||
{
|
||||
|
@ -888,11 +954,14 @@ NTSTATUS WINAPI NtFsControlFile(HANDLE DeviceHandle, HANDLE Event OPTIONAL, PIO_
|
|||
if (!ret && reply->fd != -1) close(reply->fd);
|
||||
}
|
||||
SERVER_END_REQ;
|
||||
return ret;
|
||||
break;
|
||||
default :
|
||||
FIXME("Unsupported IoControlCode %lx\n", IoControlCode);
|
||||
return STATUS_NOT_SUPPORTED;
|
||||
FIXME("Unsupported FsControlCode %lx\n", FsControlCode);
|
||||
ret = STATUS_NOT_SUPPORTED;
|
||||
break;
|
||||
}
|
||||
IoStatusBlock->u.Status = ret;
|
||||
return ret;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
|
|
|
@ -2408,7 +2408,7 @@ struct connect_named_pipe_request
|
|||
{
|
||||
struct request_header __header;
|
||||
obj_handle_t handle;
|
||||
void* overlapped;
|
||||
obj_handle_t event;
|
||||
void* func;
|
||||
};
|
||||
struct connect_named_pipe_reply
|
||||
|
@ -4206,6 +4206,6 @@ union generic_reply
|
|||
struct set_mailslot_info_reply set_mailslot_info_reply;
|
||||
};
|
||||
|
||||
#define SERVER_PROTOCOL_VERSION 191
|
||||
#define SERVER_PROTOCOL_VERSION 192
|
||||
|
||||
#endif /* __WINE_WINE_SERVER_PROTOCOL_H */
|
||||
|
|
|
@ -671,7 +671,7 @@ DECL_HANDLER(connect_named_pipe)
|
|||
assert( !server->fd );
|
||||
server->state = ps_wait_open;
|
||||
create_async( current, NULL, &server->wait_q,
|
||||
req->func, req->overlapped, NULL );
|
||||
req->func, req->event, NULL );
|
||||
async_terminate_queue( &server->pipe->waiters, STATUS_SUCCESS );
|
||||
break;
|
||||
case ps_connected_server:
|
||||
|
|
|
@ -1712,7 +1712,7 @@ enum message_type
|
|||
/* Connect to a named pipe */
|
||||
@REQ(connect_named_pipe)
|
||||
obj_handle_t handle;
|
||||
void* overlapped;
|
||||
obj_handle_t event;
|
||||
void* func;
|
||||
@END
|
||||
|
||||
|
|
|
@ -2173,7 +2173,7 @@ static void dump_open_named_pipe_reply( const struct open_named_pipe_reply *req
|
|||
static void dump_connect_named_pipe_request( const struct connect_named_pipe_request *req )
|
||||
{
|
||||
fprintf( stderr, " handle=%p,", req->handle );
|
||||
fprintf( stderr, " overlapped=%p,", req->overlapped );
|
||||
fprintf( stderr, " event=%p,", req->event );
|
||||
fprintf( stderr, " func=%p", req->func );
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue