Fixed incorrect SetNamedPipeHandleState implementation to use the actual APIs/Structures it should and added one of the missing ones to NTIFS.

svn path=/trunk/; revision=16129
This commit is contained in:
Alex Ionescu 2005-06-20 01:52:47 +00:00
parent aaad0af903
commit f5e002e1c9
6 changed files with 207 additions and 264 deletions

View file

@ -17,26 +17,100 @@
/* FUNCTIONS *****************************************************************/ /* FUNCTIONS *****************************************************************/
static NTSTATUS static
NpfsQueryPipeInformation(PDEVICE_OBJECT DeviceObject, NTSTATUS
PNPFS_FCB Fcb, NpfsSetPipeInformation(PDEVICE_OBJECT DeviceObject,
PFILE_PIPE_INFORMATION Info, PNPFS_FCB Fcb,
PULONG BufferLength) PFILE_PIPE_INFORMATION Info,
PULONG BufferLength)
{ {
PNPFS_PIPE Pipe; PNPFS_PIPE Pipe;
PFILE_PIPE_INFORMATION Request;
DPRINT("NpfsSetPipeInformation()\n");
DPRINT("NpfsQueryPipeInformation()\n"); /* Get the Pipe and data */
Pipe = Fcb->Pipe;
Request = (PFILE_PIPE_INFORMATION)Info;
Pipe = Fcb->Pipe; /* Set Pipe Data */
Pipe->ReadMode = Request->ReadMode;
Pipe->CompletionMode = Request->CompletionMode;
RtlZeroMemory(Info, /* Return Success */
sizeof(FILE_PIPE_INFORMATION)); return STATUS_SUCCESS;
}
// Info->PipeMode = static
// Info->CompletionMode = NTSTATUS
NpfsSetPipeRemoteInformation(PDEVICE_OBJECT DeviceObject,
PNPFS_FCB Fcb,
PFILE_PIPE_INFORMATION Info,
PULONG BufferLength)
{
PNPFS_PIPE Pipe;
PFILE_PIPE_REMOTE_INFORMATION Request;
DPRINT("NpfsSetPipeRemoteInformation()\n");
*BufferLength -= sizeof(FILE_PIPE_INFORMATION); /* Get the Pipe and data */
return STATUS_SUCCESS; Pipe = Fcb->Pipe;
Request = (PFILE_PIPE_REMOTE_INFORMATION)Info;
/* Set the Settings */
Pipe->TimeOut = Request->CollectDataTime;
Pipe->InboundQuota = Request->MaximumCollectionCount;
/* Return Success */
return STATUS_SUCCESS;
}
static
NTSTATUS
NpfsQueryPipeInformation(PDEVICE_OBJECT DeviceObject,
PNPFS_FCB Fcb,
PFILE_PIPE_INFORMATION Info,
PULONG BufferLength)
{
PNPFS_PIPE Pipe;
DPRINT("NpfsQueryPipeInformation()\n");
/* Get the Pipe */
Pipe = Fcb->Pipe;
/* Clear Info */
RtlZeroMemory(Info, sizeof(FILE_PIPE_INFORMATION));
/* Return Info */
Info->CompletionMode = Pipe->CompletionMode;
Info->ReadMode = Pipe->ReadMode;
/* Return success */
*BufferLength -= sizeof(FILE_PIPE_INFORMATION);
return STATUS_SUCCESS;
}
static
NTSTATUS
NpfsQueryPipeRemoteInformation(PDEVICE_OBJECT DeviceObject,
PNPFS_FCB Fcb,
PFILE_PIPE_REMOTE_INFORMATION Info,
PULONG BufferLength)
{
PNPFS_PIPE Pipe;
DPRINT("NpfsQueryPipeRemoteInformation()\n");
/* Get the Pipe */
Pipe = Fcb->Pipe;
/* Clear Info */
RtlZeroMemory(Info, sizeof(FILE_PIPE_REMOTE_INFORMATION));
/* Return Info */
Info->MaximumCollectionCount = Pipe->InboundQuota;
Info->CollectDataTime = Pipe->TimeOut;
/* Return success */
*BufferLength -= sizeof(FILE_PIPE_REMOTE_INFORMATION);
return STATUS_SUCCESS;
} }
@ -128,7 +202,10 @@ NpfsQueryInformation(PDEVICE_OBJECT DeviceObject,
break; break;
case FilePipeRemoteInformation: case FilePipeRemoteInformation:
Status = STATUS_NOT_IMPLEMENTED; Status = NpfsQueryPipeRemoteInformation(DeviceObject,
Fcb,
SystemBuffer,
&BufferLength);
break; break;
default: default:
@ -176,27 +253,35 @@ NpfsSetInformation(PDEVICE_OBJECT DeviceObject,
DPRINT("SystemBuffer %p\n", SystemBuffer); DPRINT("SystemBuffer %p\n", SystemBuffer);
DPRINT("BufferLength %lu\n", BufferLength); DPRINT("BufferLength %lu\n", BufferLength);
switch (FileInformationClass) switch (FileInformationClass)
{ {
case FilePipeInformation: case FilePipeInformation:
Status = STATUS_NOT_IMPLEMENTED; /* Call the handler */
break; Status = NpfsSetPipeInformation(DeviceObject,
case FilePipeLocalInformation: Fcb,
Status = STATUS_NOT_IMPLEMENTED; SystemBuffer,
break; &BufferLength);
case FilePipeRemoteInformation: break;
Status = STATUS_NOT_IMPLEMENTED;
break; case FilePipeLocalInformation:
default: Status = STATUS_NOT_IMPLEMENTED;
Status = STATUS_NOT_SUPPORTED; break;
case FilePipeRemoteInformation:
/* Call the handler */
Status = NpfsSetPipeRemoteInformation(DeviceObject,
Fcb,
SystemBuffer,
&BufferLength);
break;
default:
Status = STATUS_NOT_SUPPORTED;
} }
Irp->IoStatus.Status = Status; Irp->IoStatus.Status = Status;
Irp->IoStatus.Information = 0; Irp->IoStatus.Information = 0;
IoCompleteRequest(Irp, IoCompleteRequest(Irp, IO_NO_INCREMENT);
IO_NO_INCREMENT); return Status;
return Status;
} }
/* EOF */ /* EOF */

View file

@ -272,12 +272,12 @@ NpfsWaitPipe(PIRP Irp,
PNPFS_PIPE Pipe; PNPFS_PIPE Pipe;
PLIST_ENTRY current_entry; PLIST_ENTRY current_entry;
PNPFS_FCB ServerFcb; PNPFS_FCB ServerFcb;
PNPFS_WAIT_PIPE WaitPipe; PFILE_PIPE_WAIT_FOR_BUFFER WaitPipe;
NTSTATUS Status; NTSTATUS Status;
DPRINT("NpfsWaitPipe\n"); DPRINT("NpfsWaitPipe\n");
WaitPipe = (PNPFS_WAIT_PIPE)Irp->AssociatedIrp.SystemBuffer; WaitPipe = (PFILE_PIPE_WAIT_FOR_BUFFER)Irp->AssociatedIrp.SystemBuffer;
Pipe = Fcb->Pipe; Pipe = Fcb->Pipe;
if (Fcb->PipeState != 0) if (Fcb->PipeState != 0)
@ -326,82 +326,6 @@ NpfsWaitPipe(PIRP Irp,
* RETURNS: * RETURNS:
* Status of operation * Status of operation
*/ */
static NTSTATUS
NpfsGetState(PIRP Irp,
PIO_STACK_LOCATION IrpSp)
{
PNPFS_GET_STATE Reply;
PNPFS_PIPE Pipe;
PNPFS_FCB Fcb;
/* Validate parameters */
if (IrpSp->Parameters.DeviceIoControl.OutputBufferLength < sizeof(NPFS_GET_STATE))
{
DPRINT("Status (0x%X).\n", STATUS_INVALID_PARAMETER);
return STATUS_INVALID_PARAMETER;
}
Fcb = IrpSp->FileObject->FsContext;
Reply = (PNPFS_GET_STATE)Irp->AssociatedIrp.SystemBuffer;
Pipe = Fcb->Pipe;
Reply->WriteModeMessage = (Pipe->WriteMode == FILE_PIPE_MESSAGE_MODE);
Reply->ReadModeMessage = (Pipe->ReadMode == FILE_PIPE_MESSAGE_MODE);
Reply->NonBlocking = (Pipe->CompletionMode == FILE_PIPE_QUEUE_OPERATION);
Reply->InBufferSize = Pipe->InboundQuota;
Reply->OutBufferSize = Pipe->OutboundQuota;
Reply->Timeout = Pipe->TimeOut;
Irp->IoStatus.Information = sizeof(NPFS_GET_STATE);
DPRINT("Status (0x%X).\n", STATUS_SUCCESS);
return STATUS_SUCCESS;
}
/*
* FUNCTION: Set state of a pipe
* ARGUMENTS:
* Irp = Pointer to I/O request packet
* IrpSp = Pointer to current stack location of Irp
* RETURNS:
* Status of operation
*/
static NTSTATUS
NpfsSetState(PIRP Irp,
PIO_STACK_LOCATION IrpSp)
{
PNPFS_SET_STATE Request;
PNPFS_PIPE Pipe;
PNPFS_FCB Fcb;
/* Validate parameters */
if (IrpSp->Parameters.DeviceIoControl.InputBufferLength < sizeof(NPFS_SET_STATE))
{
DPRINT("Status (0x%X).\n", STATUS_INVALID_PARAMETER);
return STATUS_INVALID_PARAMETER;
}
Fcb = IrpSp->FileObject->FsContext;
Request = (PNPFS_SET_STATE)Irp->AssociatedIrp.SystemBuffer;
Pipe = Fcb->Pipe;
Pipe->WriteMode =
Request->WriteModeMessage ? FILE_PIPE_MESSAGE_MODE : FILE_PIPE_BYTE_STREAM_MODE;
Pipe->ReadMode =
Request->WriteModeMessage ? FILE_PIPE_MESSAGE_MODE : FILE_PIPE_BYTE_STREAM_MODE;
Pipe->CompletionMode =
Request->NonBlocking ? FILE_PIPE_QUEUE_OPERATION : FILE_PIPE_COMPLETE_OPERATION;
Pipe->InboundQuota = Request->InBufferSize;
Pipe->OutboundQuota = Request->OutBufferSize;
Pipe->TimeOut = Request->Timeout;
DPRINT("Status (0x%X).\n", STATUS_SUCCESS);
return STATUS_SUCCESS;
}
/* /*
* FUNCTION: Peek at a pipe (get information about messages) * FUNCTION: Peek at a pipe (get information about messages)
@ -520,16 +444,6 @@ NpfsFileSystemControl(PDEVICE_OBJECT DeviceObject,
Status = STATUS_NOT_IMPLEMENTED; Status = STATUS_NOT_IMPLEMENTED;
break; break;
case FSCTL_PIPE_GET_STATE:
DPRINT("Get state\n");
Status = NpfsGetState(Irp, (PIO_STACK_LOCATION)IoStack);
break;
case FSCTL_PIPE_SET_STATE:
DPRINT("Set state\n");
Status = NpfsSetState(Irp, (PIO_STACK_LOCATION)IoStack);
break;
case FSCTL_PIPE_INTERNAL_READ: case FSCTL_PIPE_INTERNAL_READ:
DPRINT("Internal read\n"); DPRINT("Internal read\n");
Status = STATUS_NOT_IMPLEMENTED; Status = STATUS_NOT_IMPLEMENTED;

View file

@ -35,12 +35,6 @@
#define FSCTL_PIPE_QUERY_CLIENT_PROCESS \ #define FSCTL_PIPE_QUERY_CLIENT_PROCESS \
CTL_CODE(FILE_DEVICE_NAMED_PIPE, 9, METHOD_BUFFERED, FILE_ANY_ACCESS) CTL_CODE(FILE_DEVICE_NAMED_PIPE, 9, METHOD_BUFFERED, FILE_ANY_ACCESS)
#define FSCTL_PIPE_GET_STATE \
CTL_CODE(FILE_DEVICE_NAMED_PIPE, 10, METHOD_BUFFERED, FILE_ANY_ACCESS)
#define FSCTL_PIPE_SET_STATE \
CTL_CODE(FILE_DEVICE_NAMED_PIPE, 11, METHOD_BUFFERED, FILE_ANY_ACCESS)
#define FSCTL_PIPE_INTERNAL_READ \ #define FSCTL_PIPE_INTERNAL_READ \
CTL_CODE(FILE_DEVICE_NAMED_PIPE, 2045, METHOD_BUFFERED, FILE_READ_DATA) CTL_CODE(FILE_DEVICE_NAMED_PIPE, 2045, METHOD_BUFFERED, FILE_READ_DATA)
@ -54,46 +48,6 @@
CTL_CODE(FILE_DEVICE_NAMED_PIPE, 2048, METHOD_BUFFERED, FILE_READ_DATA) CTL_CODE(FILE_DEVICE_NAMED_PIPE, 2048, METHOD_BUFFERED, FILE_READ_DATA)
typedef struct _NPFS_WAIT_PIPE
{
LARGE_INTEGER Timeout;
} NPFS_WAIT_PIPE, *PNPFS_WAIT_PIPE;
#ifdef __GNUC__ /* robd */
typedef struct _NPFS_LISTEN
{
} NPFS_LISTEN, *PNPFS_LISTEN;
#endif
typedef struct _NPFS_SET_STATE
{
BOOLEAN WriteModeMessage;
BOOLEAN ReadModeMessage;
BOOLEAN NonBlocking;
ULONG InBufferSize;
ULONG OutBufferSize;
LARGE_INTEGER Timeout;
} NPFS_SET_STATE, *PNPFS_SET_STATE;
typedef struct _NPFS_GET_STATE
{
BOOLEAN WriteModeMessage;
BOOLEAN ReadModeMessage;
BOOLEAN NonBlocking;
ULONG InBufferSize;
ULONG OutBufferSize;
LARGE_INTEGER Timeout;
} NPFS_GET_STATE, *PNPFS_GET_STATE;
typedef struct _FILE_PIPE_PEEK_BUFFER
{
ULONG NamedPipeState;
ULONG ReadDataAvailable;
ULONG NumberOfMessages;
ULONG MessageLength;
CHAR Data[1];
} FILE_PIPE_PEEK_BUFFER, *PFILE_PIPE_PEEK_BUFFER;
#define FILE_PIPE_BYTE_STREAM_TYPE 0x00000000 #define FILE_PIPE_BYTE_STREAM_TYPE 0x00000000
#define FILE_PIPE_MESSAGE_TYPE 0x00000001 #define FILE_PIPE_MESSAGE_TYPE 0x00000001

View file

@ -28,7 +28,7 @@
typedef struct _KERNEL32_FIND_FILE_DATA typedef struct _KERNEL32_FIND_FILE_DATA
{ {
HANDLE DirectoryHandle; HANDLE DirectoryHandle;
PFILE_BOTH_DIRECTORY_INFORMATION pFileInfo; PFILE_BOTH_DIR_INFORMATION pFileInfo;
} KERNEL32_FIND_FILE_DATA, *PKERNEL32_FIND_FILE_DATA; } KERNEL32_FIND_FILE_DATA, *PKERNEL32_FIND_FILE_DATA;

View file

@ -243,7 +243,7 @@ WaitNamedPipeW(LPCWSTR lpNamedPipeName,
BOOL r; BOOL r;
NTSTATUS Status; NTSTATUS Status;
OBJECT_ATTRIBUTES ObjectAttributes; OBJECT_ATTRIBUTES ObjectAttributes;
NPFS_WAIT_PIPE WaitPipe; FILE_PIPE_WAIT_FOR_BUFFER WaitPipe;
HANDLE FileHandle; HANDLE FileHandle;
IO_STATUS_BLOCK Iosb; IO_STATUS_BLOCK Iosb;
@ -371,112 +371,93 @@ ConnectNamedPipe(IN HANDLE hNamedPipe,
/* /*
* @implemented * @implemented
*/ */
BOOL STDCALL BOOL
STDCALL
SetNamedPipeHandleState(HANDLE hNamedPipe, SetNamedPipeHandleState(HANDLE hNamedPipe,
LPDWORD lpMode, LPDWORD lpMode,
LPDWORD lpMaxCollectionCount, LPDWORD lpMaxCollectionCount,
LPDWORD lpCollectDataTimeout) LPDWORD lpCollectDataTimeout)
{ {
NPFS_GET_STATE GetState; IO_STATUS_BLOCK Iosb;
NPFS_SET_STATE SetState; NTSTATUS Status;
IO_STATUS_BLOCK Iosb;
NTSTATUS Status;
Status = NtFsControlFile(hNamedPipe, /* Check if the Mode is being changed */
NULL, if (lpMode)
NULL, {
NULL, FILE_PIPE_INFORMATION Settings;
&Iosb,
FSCTL_PIPE_GET_STATE,
NULL,
0,
&GetState,
sizeof(NPFS_GET_STATE));
if (Status == STATUS_PENDING)
{
Status = NtWaitForSingleObject(hNamedPipe,
FALSE,
NULL);
if (!NT_SUCCESS(Status))
{
SetLastErrorByStatus(Status);
return(FALSE);
}
}
if (lpMode != NULL) /* Set the Completion Mode */
{ Settings.CompletionMode = (*lpMode & PIPE_NOWAIT) ?
if ((*lpMode) & PIPE_READMODE_MESSAGE) FILE_PIPE_COMPLETE_OPERATION : FILE_PIPE_QUEUE_OPERATION;
{
SetState.ReadModeMessage = TRUE;
}
else
{
SetState.ReadModeMessage = FALSE;
}
if ((*lpMode) & PIPE_NOWAIT)
{
SetState.NonBlocking = TRUE;
}
else
{
SetState.NonBlocking = FALSE;
}
SetState.WriteModeMessage = GetState.WriteModeMessage;
}
else
{
SetState.ReadModeMessage = GetState.ReadModeMessage;
SetState.WriteModeMessage = GetState.WriteModeMessage;
SetState.NonBlocking = SetState.NonBlocking;
}
if (lpMaxCollectionCount != NULL) /* Set the Read Mode */
{ Settings.ReadMode = (*lpMode & PIPE_READMODE_MESSAGE) ?
SetState.InBufferSize = *lpMaxCollectionCount; FILE_PIPE_MESSAGE_MODE: FILE_PIPE_BYTE_STREAM_MODE;
}
else
{
SetState.InBufferSize = GetState.InBufferSize;
}
SetState.OutBufferSize = GetState.OutBufferSize; /* Send the changes to the Driver */
Status = NtSetInformationFile(hNamedPipe,
&Iosb,
&Settings,
sizeof(FILE_PIPE_INFORMATION),
FilePipeInformation);
if (!NT_SUCCESS(Status))
{
SetLastErrorByStatus(Status);
return(FALSE);
}
}
if (lpCollectDataTimeout != NULL) /* Check if the Collection count or Timeout are being changed */
{ if (lpMaxCollectionCount || lpCollectDataTimeout)
SetState.Timeout.QuadPart = (*lpCollectDataTimeout) * -10000LL; {
} FILE_PIPE_REMOTE_INFORMATION RemoteSettings;
else
{
SetState.Timeout = GetState.Timeout;
}
Status = NtFsControlFile(hNamedPipe, /* Setting one without the other would delete it, so we read old one */
NULL, if (!lpMaxCollectionCount || !lpCollectDataTimeout)
NULL, {
NULL, Status = NtQueryInformationFile(hNamedPipe,
&Iosb, &Iosb,
FSCTL_PIPE_SET_STATE, &RemoteSettings,
&SetState, sizeof(FILE_PIPE_REMOTE_INFORMATION),
sizeof(NPFS_SET_STATE), FilePipeRemoteInformation);
NULL,
0);
if (Status == STATUS_PENDING)
{
Status = NtWaitForSingleObject(hNamedPipe,
FALSE,
NULL);
if (!NT_SUCCESS(Status))
{
SetLastErrorByStatus(Status);
return(FALSE);
}
}
return(TRUE); if (!NT_SUCCESS(Status))
{
SetLastErrorByStatus(Status);
return(FALSE);
}
}
/* Now set the new settings */
RemoteSettings.MaximumCollectionCount = (lpMaxCollectionCount) ?
*lpMaxCollectionCount :
RemoteSettings.MaximumCollectionCount;
if (lpCollectDataTimeout)
{
/* Convert it to Quad */
RemoteSettings.CollectDataTime.QuadPart = -(LONGLONG)
UInt32x32To64(10000,
*lpCollectDataTimeout);
}
/* Tell the driver to change them */
Status = NtSetInformationFile(hNamedPipe,
&Iosb,
&RemoteSettings,
sizeof(FILE_PIPE_REMOTE_INFORMATION),
FilePipeRemoteInformation);
if (!NT_SUCCESS(Status))
{
SetLastErrorByStatus(Status);
return(FALSE);
}
}
/* All done */
return TRUE;
} }
/* /*
* @implemented * @implemented
*/ */

View file

@ -1124,6 +1124,15 @@ typedef struct _FILE_PIPE_EVENT_BUFFER {
ULONG NumberRequests; ULONG NumberRequests;
} FILE_PIPE_EVENT_BUFFER, *PFILE_PIPE_EVENT_BUFFER; } FILE_PIPE_EVENT_BUFFER, *PFILE_PIPE_EVENT_BUFFER;
typedef struct _FILE_PIPE_PEEK_BUFFER
{
ULONG NamedPipeState;
ULONG ReadDataAvailable;
ULONG NumberOfMessages;
ULONG MessageLength;
CHAR Data[1];
} FILE_PIPE_PEEK_BUFFER, *PFILE_PIPE_PEEK_BUFFER;
typedef struct _FILE_PIPE_INFORMATION { typedef struct _FILE_PIPE_INFORMATION {
ULONG ReadMode; ULONG ReadMode;
ULONG CompletionMode; ULONG CompletionMode;