?? deviceio.c
字號:
/* $Id: deviceio.c 21253 2006-03-08 21:33:04Z audit $
*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS system libraries
* FILE: lib/kernel32/file/deviceio.c
* PURPOSE: Device I/O and Overlapped Result functions
* PROGRAMMER: Ariadne (ariadne@xs4all.nl)
* UPDATE HISTORY:
* Created 01/11/98
*/
#include <k32.h>
#define NDEBUG
#include "../include/debug.h"
/*
* @implemented
*/
BOOL
STDCALL
DeviceIoControl(IN HANDLE hDevice,
IN DWORD dwIoControlCode,
IN LPVOID lpInBuffer OPTIONAL,
IN DWORD nInBufferSize OPTIONAL,
OUT LPVOID lpOutBuffer OPTIONAL,
IN DWORD nOutBufferSize OPTIONAL,
OUT LPDWORD lpBytesReturned OPTIONAL,
IN LPOVERLAPPED lpOverlapped OPTIONAL)
{
BOOL FsIoCtl;
NTSTATUS Status;
FsIoCtl = ((dwIoControlCode >> 16) == FILE_DEVICE_FILE_SYSTEM);
if (lpBytesReturned != NULL)
{
*lpBytesReturned = 0;
}
if (lpOverlapped != NULL)
{
PVOID ApcContext;
lpOverlapped->Internal = STATUS_PENDING;
ApcContext = (((ULONG_PTR)lpOverlapped->hEvent & 0x1) ? NULL : lpOverlapped);
if (FsIoCtl)
{
Status = NtFsControlFile(hDevice,
lpOverlapped->hEvent,
NULL,
ApcContext,
(PIO_STATUS_BLOCK)lpOverlapped,
dwIoControlCode,
lpInBuffer,
nInBufferSize,
lpOutBuffer,
nOutBufferSize);
}
else
{
Status = NtDeviceIoControlFile(hDevice,
lpOverlapped->hEvent,
NULL,
ApcContext,
(PIO_STATUS_BLOCK)lpOverlapped,
dwIoControlCode,
lpInBuffer,
nInBufferSize,
lpOutBuffer,
nOutBufferSize);
}
/* return FALSE in case of failure and pending operations! */
if (!NT_SUCCESS(Status) || Status == STATUS_PENDING)
{
SetLastErrorByStatus(Status);
return FALSE;
}
if (lpBytesReturned != NULL)
{
*lpBytesReturned = lpOverlapped->InternalHigh;
}
}
else
{
IO_STATUS_BLOCK Iosb;
if (FsIoCtl)
{
Status = NtFsControlFile(hDevice,
NULL,
NULL,
NULL,
&Iosb,
dwIoControlCode,
lpInBuffer,
nInBufferSize,
lpOutBuffer,
nOutBufferSize);
}
else
{
Status = NtDeviceIoControlFile(hDevice,
NULL,
NULL,
NULL,
&Iosb,
dwIoControlCode,
lpInBuffer,
nInBufferSize,
lpOutBuffer,
nOutBufferSize);
}
/* wait in case operation is pending */
if (Status == STATUS_PENDING)
{
Status = NtWaitForSingleObject(hDevice,
FALSE,
NULL);
if (NT_SUCCESS(Status))
{
Status = Iosb.Status;
}
}
if (NT_SUCCESS(Status))
{
/* lpBytesReturned must not be NULL here, in fact Win doesn't
check that case either and crashes (only after the operation
completed) */
*lpBytesReturned = Iosb.Information;
}
else
{
SetLastErrorByStatus(Status);
return FALSE;
}
}
return TRUE;
}
/*
* @implemented
*/
BOOL
STDCALL
GetOverlappedResult (
IN HANDLE hFile,
IN LPOVERLAPPED lpOverlapped,
OUT LPDWORD lpNumberOfBytesTransferred,
IN BOOL bWait
)
{
DWORD WaitStatus;
HANDLE hObject;
if (lpOverlapped->Internal == STATUS_PENDING)
{
if (!bWait)
{
/* can't use SetLastErrorByStatus(STATUS_PENDING) here,
since STATUS_PENDING translates to ERROR_IO_PENDING */
SetLastError(ERROR_IO_INCOMPLETE);
return FALSE;
}
hObject = lpOverlapped->hEvent ? lpOverlapped->hEvent : hFile;
/* Wine delivers pending APC's while waiting, but Windows does
not, nor do we... */
WaitStatus = WaitForSingleObject(hObject, INFINITE);
if (WaitStatus == WAIT_FAILED)
{
DPRINT("Wait failed!\n");
/* WaitForSingleObjectEx sets the last error */
return FALSE;
}
}
*lpNumberOfBytesTransferred = lpOverlapped->InternalHigh;
if (!NT_SUCCESS(lpOverlapped->Internal))
{
SetLastErrorByStatus(lpOverlapped->Internal);
return FALSE;
}
return TRUE;
}
/* EOF */
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -