Commit f6bfb4ce authored by Alexandre Julliard's avatar Alexandre Julliard

ntdll: Move the device I/O control functions to the Unix library.

parent 888d66a2
......@@ -9,7 +9,6 @@ EXTRADLLFLAGS = -nodefaultlibs -Wl,--image-base,0x7bc00000
C_SRCS = \
actctx.c \
atom.c \
cdrom.c \
critsection.c \
crypt.c \
debugbuffer.c \
......@@ -37,7 +36,6 @@ C_SRCS = \
rtlbitmap.c \
rtlstr.c \
sec.c \
serial.c \
server.c \
signal_arm.c \
signal_arm64.c \
......@@ -46,15 +44,16 @@ C_SRCS = \
signal_x86_64.c \
string.c \
sync.c \
tape.c \
thread.c \
threadpool.c \
time.c \
unix/cdrom.c \
unix/debug.c \
unix/env.c \
unix/file.c \
unix/loader.c \
unix/process.c \
unix/serial.c \
unix/server.c \
unix/signal_arm.c \
unix/signal_arm64.c \
......@@ -62,6 +61,7 @@ C_SRCS = \
unix/signal_powerpc.c \
unix/signal_x86_64.c \
unix/sync.c \
unix/tape.c \
unix/thread.c \
unix/virtual.c \
version.c \
......
......@@ -257,38 +257,6 @@ static async_data_t server_async( HANDLE handle, struct async_fileio *user, HAND
return async;
}
static NTSTATUS wait_async( HANDLE handle, BOOL alertable, IO_STATUS_BLOCK *io )
{
if (NtWaitForSingleObject( handle, alertable, NULL )) return STATUS_PENDING;
return io->u.Status;
}
/* callback for irp async I/O completion */
static NTSTATUS irp_completion( void *user, IO_STATUS_BLOCK *io, NTSTATUS status )
{
struct async_irp *async = user;
ULONG information = 0;
if (status == STATUS_ALERTED)
{
SERVER_START_REQ( get_async_result )
{
req->user_arg = wine_server_client_ptr( async );
wine_server_set_reply( req, async->buffer, async->size );
status = unix_funcs->virtual_locked_server_call( req );
information = reply->size;
}
SERVER_END_REQ;
}
if (status != STATUS_PENDING)
{
io->u.Status = status;
io->Information = information;
release_fileio( &async->io );
}
return status;
}
/***********************************************************************
* FILE_GetNtStatus(void)
*
......@@ -430,77 +398,6 @@ NTSTATUS WINAPI NtWriteFileGather( HANDLE file, HANDLE event, PIO_APC_ROUTINE ap
}
/* do an ioctl call through the server */
static NTSTATUS server_ioctl_file( HANDLE handle, HANDLE event,
PIO_APC_ROUTINE apc, PVOID apc_context,
IO_STATUS_BLOCK *io, ULONG code,
const void *in_buffer, ULONG in_size,
PVOID out_buffer, ULONG out_size )
{
struct async_irp *async;
NTSTATUS status;
HANDLE wait_handle;
ULONG options;
if (!(async = (struct async_irp *)alloc_fileio( sizeof(*async), irp_completion, handle )))
return STATUS_NO_MEMORY;
async->buffer = out_buffer;
async->size = out_size;
SERVER_START_REQ( ioctl )
{
req->code = code;
req->async = server_async( handle, &async->io, event, apc, apc_context, io );
wine_server_add_data( req, in_buffer, in_size );
if ((code & 3) != METHOD_BUFFERED)
wine_server_add_data( req, out_buffer, out_size );
wine_server_set_reply( req, out_buffer, out_size );
status = unix_funcs->virtual_locked_server_call( req );
wait_handle = wine_server_ptr_handle( reply->wait );
options = reply->options;
if (wait_handle && status != STATUS_PENDING)
{
io->u.Status = status;
io->Information = wine_server_reply_size( reply );
}
}
SERVER_END_REQ;
if (status == STATUS_NOT_SUPPORTED)
FIXME("Unsupported ioctl %x (device=%x access=%x func=%x method=%x)\n",
code, code >> 16, (code >> 14) & 3, (code >> 2) & 0xfff, code & 3);
if (status != STATUS_PENDING) RtlFreeHeap( GetProcessHeap(), 0, async );
if (wait_handle) status = wait_async( wait_handle, (options & FILE_SYNCHRONOUS_IO_ALERT), io );
return status;
}
/* Tell Valgrind to ignore any holes in structs we will be passing to the
* server */
static void ignore_server_ioctl_struct_holes (ULONG code, const void *in_buffer,
ULONG in_size)
{
#ifdef VALGRIND_MAKE_MEM_DEFINED
# define IGNORE_STRUCT_HOLE(buf, size, t, f1, f2) \
do { \
if (FIELD_OFFSET(t, f1) + sizeof(((t *)0)->f1) < FIELD_OFFSET(t, f2)) \
if ((size) >= FIELD_OFFSET(t, f2)) \
VALGRIND_MAKE_MEM_DEFINED( \
(const char *)(buf) + FIELD_OFFSET(t, f1) + sizeof(((t *)0)->f1), \
FIELD_OFFSET(t, f2) - FIELD_OFFSET(t, f1) + sizeof(((t *)0)->f1)); \
} while (0)
switch (code)
{
case FSCTL_PIPE_WAIT:
IGNORE_STRUCT_HOLE(in_buffer, in_size, FILE_PIPE_WAIT_FOR_BUFFER, TimeoutSpecified, Name);
break;
}
#endif
}
/**************************************************************************
* NtDeviceIoControlFile [NTDLL.@]
* ZwDeviceIoControlFile [NTDLL.@]
......@@ -529,39 +426,8 @@ NTSTATUS WINAPI NtDeviceIoControlFile(HANDLE handle, HANDLE event,
PVOID in_buffer, ULONG in_size,
PVOID out_buffer, ULONG out_size)
{
ULONG device = (code >> 16);
NTSTATUS status = STATUS_NOT_SUPPORTED;
TRACE("(%p,%p,%p,%p,%p,0x%08x,%p,0x%08x,%p,0x%08x)\n",
handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size);
switch(device)
{
case FILE_DEVICE_DISK:
case FILE_DEVICE_CD_ROM:
case FILE_DEVICE_DVD:
case FILE_DEVICE_CONTROLLER:
case FILE_DEVICE_MASS_STORAGE:
status = CDROM_DeviceIoControl(handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size);
break;
case FILE_DEVICE_SERIAL_PORT:
status = COMM_DeviceIoControl(handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size);
break;
case FILE_DEVICE_TAPE:
status = TAPE_DeviceIoControl(handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size);
break;
}
if (status == STATUS_NOT_SUPPORTED || status == STATUS_BAD_DEVICE_TYPE)
return server_ioctl_file( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
if (status != STATUS_PENDING) io->u.Status = status;
return status;
return unix_funcs->NtDeviceIoControlFile( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
}
......@@ -591,71 +457,8 @@ NTSTATUS WINAPI NtFsControlFile(HANDLE handle, HANDLE event, PIO_APC_ROUTINE apc
PVOID apc_context, PIO_STATUS_BLOCK io, ULONG code,
PVOID in_buffer, ULONG in_size, PVOID out_buffer, ULONG out_size)
{
NTSTATUS status;
TRACE("(%p,%p,%p,%p,%p,0x%08x,%p,0x%08x,%p,0x%08x)\n",
handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size);
if (!io) return STATUS_INVALID_PARAMETER;
ignore_server_ioctl_struct_holes( code, in_buffer, in_size );
switch(code)
{
case FSCTL_DISMOUNT_VOLUME:
status = server_ioctl_file( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
if (!status) status = unix_funcs->unmount_device( handle );
return status;
case FSCTL_PIPE_IMPERSONATE:
FIXME("FSCTL_PIPE_IMPERSONATE: impersonating self\n");
status = RtlImpersonateSelf( SecurityImpersonation );
break;
case FSCTL_IS_VOLUME_MOUNTED:
case FSCTL_LOCK_VOLUME:
case FSCTL_UNLOCK_VOLUME:
FIXME("stub! return success - Unsupported fsctl %x (device=%x access=%x func=%x method=%x)\n",
code, code >> 16, (code >> 14) & 3, (code >> 2) & 0xfff, code & 3);
status = STATUS_SUCCESS;
break;
case FSCTL_GET_RETRIEVAL_POINTERS:
{
RETRIEVAL_POINTERS_BUFFER *buffer = (RETRIEVAL_POINTERS_BUFFER *)out_buffer;
FIXME("stub: FSCTL_GET_RETRIEVAL_POINTERS\n");
if (out_size >= sizeof(RETRIEVAL_POINTERS_BUFFER))
{
buffer->ExtentCount = 1;
buffer->StartingVcn.QuadPart = 1;
buffer->Extents[0].NextVcn.QuadPart = 0;
buffer->Extents[0].Lcn.QuadPart = 0;
io->Information = sizeof(RETRIEVAL_POINTERS_BUFFER);
status = STATUS_SUCCESS;
}
else
{
io->Information = 0;
status = STATUS_BUFFER_TOO_SMALL;
}
break;
}
case FSCTL_SET_SPARSE:
TRACE("FSCTL_SET_SPARSE: Ignoring request\n");
io->Information = 0;
status = STATUS_SUCCESS;
break;
default:
return server_ioctl_file( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
}
if (status != STATUS_PENDING) io->u.Status = status;
return status;
return unix_funcs->NtFsControlFile( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
}
......@@ -1547,58 +1350,7 @@ NTSTATUS WINAPI NtSetEaFile( HANDLE hFile, PIO_STATUS_BLOCK iosb, PVOID buffer,
*/
NTSTATUS WINAPI NtFlushBuffersFile( HANDLE hFile, IO_STATUS_BLOCK *io )
{
NTSTATUS ret;
HANDLE wait_handle;
enum server_fd_type type;
int fd, needs_close;
if (!io || !unix_funcs->virtual_check_buffer_for_write( io, sizeof(*io) )) return STATUS_ACCESS_VIOLATION;
ret = unix_funcs->server_get_unix_fd( hFile, FILE_WRITE_DATA, &fd, &needs_close, &type, NULL );
if (ret == STATUS_ACCESS_DENIED)
ret = unix_funcs->server_get_unix_fd( hFile, FILE_APPEND_DATA, &fd, &needs_close, &type, NULL );
if (!ret && (type == FD_TYPE_FILE || type == FD_TYPE_DIR))
{
if (fsync(fd))
ret = FILE_GetNtStatus();
io->u.Status = ret;
io->Information = 0;
}
else if (!ret && type == FD_TYPE_SERIAL)
{
ret = COMM_FlushBuffersFile( fd );
}
else if (ret != STATUS_ACCESS_DENIED)
{
struct async_irp *async;
if (!(async = (struct async_irp *)alloc_fileio( sizeof(*async), irp_completion, hFile )))
return STATUS_NO_MEMORY;
async->buffer = NULL;
async->size = 0;
SERVER_START_REQ( flush )
{
req->async = server_async( hFile, &async->io, NULL, NULL, NULL, io );
ret = wine_server_call( req );
wait_handle = wine_server_ptr_handle( reply->event );
if (wait_handle && ret != STATUS_PENDING)
{
io->u.Status = ret;
io->Information = 0;
}
}
SERVER_END_REQ;
if (ret != STATUS_PENDING) RtlFreeHeap( GetProcessHeap(), 0, async );
if (wait_handle) ret = wait_async( wait_handle, FALSE, io );
}
if (needs_close) close( fd );
return ret;
return unix_funcs->NtFlushBuffersFile( hFile, io );
}
/******************************************************************
......
......@@ -114,30 +114,6 @@ extern const WCHAR syswow64_dir[] DECLSPEC_HIDDEN;
extern const struct unix_funcs *unix_funcs DECLSPEC_HIDDEN;
/* Device IO */
extern NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
ULONG IoControlCode,
LPVOID lpInBuffer, DWORD nInBufferSize,
LPVOID lpOutBuffer, DWORD nOutBufferSize) DECLSPEC_HIDDEN;
extern NTSTATUS COMM_DeviceIoControl(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
ULONG IoControlCode,
LPVOID lpInBuffer, DWORD nInBufferSize,
LPVOID lpOutBuffer, DWORD nOutBufferSize) DECLSPEC_HIDDEN;
extern NTSTATUS TAPE_DeviceIoControl(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
ULONG IoControlCode,
LPVOID lpInBuffer, DWORD nInBufferSize,
LPVOID lpOutBuffer, DWORD nOutBufferSize) DECLSPEC_HIDDEN;
extern NTSTATUS COMM_FlushBuffersFile( int fd ) DECLSPEC_HIDDEN;
/* file I/O */
extern NTSTATUS FILE_GetNtStatus(void) DECLSPEC_HIDDEN;
extern NTSTATUS server_get_unix_name( HANDLE handle, ANSI_STRING *unix_name ) DECLSPEC_HIDDEN;
......
/* -*- tab-width: 8; c-basic-offset: 4 -*- */
/* Main file for CD-ROM support
/*
* CD-ROM support
*
* Copyright 1994 Martin Ayotte
* Copyright 1999, 2001, 2003 Eric Pouech
......@@ -21,6 +21,10 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#if 0
#pragma makedep unix
#endif
#include "config.h"
#include "wine/port.h"
......@@ -128,9 +132,8 @@ typedef struct
#include "ntddcdrm.h"
#include "ddk/ntddcdvd.h"
#include "ntddscsi.h"
#include "ntdll_misc.h"
#include "wine/server.h"
#include "wine/library.h"
#include "unix_private.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(cdrom);
......@@ -276,7 +279,7 @@ struct linux_cdrom_generic_command
/* FIXME: this is needed because we can't open simultaneously several times /dev/cdrom
* this should be removed when a proper device interface is implemented
*
*
* (WS) We need this to keep track of current position and to safely
* detect media changes. Besides this should provide a great speed up
* for toc inquiries.
......@@ -289,7 +292,7 @@ struct cdrom_cache {
SUB_Q_CURRENT_POSITION CurrentPosition;
};
/* who has more than 5 cdroms on his/her machine ?? */
/* FIXME: this should grow depending on the number of cdroms we install/configure
/* FIXME: this should grow depending on the number of cdroms we install/configure
* at startup
*/
#define MAX_CACHE_ENTRIES 5
......@@ -359,7 +362,7 @@ static NTSTATUS get_parent_device( int fd, char *name, size_t len )
CFMutableDictionaryRef dict;
CFTypeRef val;
if (fstat( fd, &st ) == -1) return FILE_GetNtStatus();
if (fstat( fd, &st ) == -1) return errno_to_status( errno );
if (!S_ISCHR( st.st_mode )) return STATUS_OBJECT_TYPE_MISMATCH;
/* create a dictionary with the right major/minor numbers */
......@@ -439,7 +442,7 @@ static NTSTATUS CDROM_SyncCache(int dev, int fd)
if (ioctl(fd, CDROMREADTOCHDR, &hdr) == -1)
{
WARN("(%d) -- Error occurred (%s)!\n", dev, strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
toc->FirstTrack = hdr.cdth_trk0;
......@@ -455,13 +458,13 @@ static NTSTATUS CDROM_SyncCache(int dev, int fd)
{
if (i == toc->LastTrack + 1)
entry.cdte_track = CDROM_LEADOUT;
else
else
entry.cdte_track = i;
entry.cdte_format = CDROM_MSF;
if (ioctl(fd, CDROMREADTOCENTRY, &entry) == -1)
{
WARN("error read entry (%s)\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
toc->TrackData[i - toc->FirstTrack].Control = entry.cdte_ctrl;
toc->TrackData[i - toc->FirstTrack].Adr = entry.cdte_adr;
......@@ -488,7 +491,7 @@ static NTSTATUS CDROM_SyncCache(int dev, int fd)
if (ioctl(fd, CDIOREADTOCHEADER, &hdr) == -1)
{
WARN("(%d) -- Error occurred (%s)!\n", dev, strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
toc->FirstTrack = hdr.starting_track;
toc->LastTrack = hdr.ending_track;
......@@ -515,7 +518,7 @@ static NTSTATUS CDROM_SyncCache(int dev, int fd)
if (ioctl(fd, CDIOREADTOCENTRYS, &entry) == -1)
{
WARN("error read entry (%s)\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
toc->TrackData[i - toc->FirstTrack].Control = toc_buffer.control;
toc->TrackData[i - toc->FirstTrack].Adr = toc_buffer.addr_type;
......@@ -541,7 +544,7 @@ static NTSTATUS CDROM_SyncCache(int dev, int fd)
if (ioctl(fd, DKIOCCDREADTOC, &hdr) == -1)
{
WARN("(%d) -- Error occurred (%s)!\n", dev, strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
for (i = toc->FirstTrack; i <= toc->LastTrack + 1; i++)
{
......@@ -669,7 +672,7 @@ static NTSTATUS CDROM_Open(int fd, int* dev)
NTSTATUS ret = STATUS_SUCCESS;
int empty = -1;
if (fstat(fd, &st) == -1) return FILE_GetNtStatus();
if (fstat(fd, &st) == -1) return errno_to_status( errno );
RtlEnterCriticalSection( &cache_section );
for (*dev = 0; *dev < MAX_CACHE_ENTRIES; (*dev)++)
......@@ -706,7 +709,7 @@ static NTSTATUS CDROM_Open(int fd, int* dev)
static NTSTATUS CDROM_GetStatusCode(int io)
{
if (io == 0) return STATUS_SUCCESS;
return FILE_GetNtStatus();
return errno_to_status( errno );
}
/******************************************************************
......@@ -759,10 +762,10 @@ static NTSTATUS CDROM_GetDriveGeometry(int dev, int fd, DISK_GEOMETRY* dg)
- FRAME_OF_TOC(toc, 1); /* Total size in frames */
dg->Cylinders.QuadPart = fsize / (64 * 32);
dg->MediaType = RemovableMedia;
dg->TracksPerCylinder = 64;
dg->SectorsPerTrack = 32;
dg->BytesPerSector= 2048;
dg->MediaType = RemovableMedia;
dg->TracksPerCylinder = 64;
dg->SectorsPerTrack = 32;
dg->BytesPerSector= 2048;
return ret;
}
......@@ -933,18 +936,18 @@ static NTSTATUS CDROM_ReadQChannel(int dev, int fd, const CDROM_SUB_Q_DATA_FORMA
RtlEnterCriticalSection( &cache_section );
if (hdr->AudioStatus==AUDIO_STATUS_IN_PROGRESS) {
data->CurrentPosition.FormatCode = IOCTL_CDROM_CURRENT_POSITION;
data->CurrentPosition.Control = sc.cdsc_ctrl;
data->CurrentPosition.ADR = sc.cdsc_adr;
data->CurrentPosition.TrackNumber = sc.cdsc_trk;
data->CurrentPosition.IndexNumber = sc.cdsc_ind;
data->CurrentPosition.Control = sc.cdsc_ctrl;
data->CurrentPosition.ADR = sc.cdsc_adr;
data->CurrentPosition.TrackNumber = sc.cdsc_trk;
data->CurrentPosition.IndexNumber = sc.cdsc_ind;
data->CurrentPosition.AbsoluteAddress[0] = 0;
data->CurrentPosition.AbsoluteAddress[1] = sc.cdsc_absaddr.msf.minute;
data->CurrentPosition.AbsoluteAddress[0] = 0;
data->CurrentPosition.AbsoluteAddress[1] = sc.cdsc_absaddr.msf.minute;
data->CurrentPosition.AbsoluteAddress[2] = sc.cdsc_absaddr.msf.second;
data->CurrentPosition.AbsoluteAddress[3] = sc.cdsc_absaddr.msf.frame;
data->CurrentPosition.TrackRelativeAddress[0] = 0;
data->CurrentPosition.TrackRelativeAddress[1] = sc.cdsc_reladdr.msf.minute;
data->CurrentPosition.TrackRelativeAddress[0] = 0;
data->CurrentPosition.TrackRelativeAddress[1] = sc.cdsc_reladdr.msf.minute;
data->CurrentPosition.TrackRelativeAddress[2] = sc.cdsc_reladdr.msf.second;
data->CurrentPosition.TrackRelativeAddress[3] = sc.cdsc_reladdr.msf.frame;
......@@ -1254,18 +1257,18 @@ static NTSTATUS CDROM_SeekAudioMSF(int dev, int fd, const CDROM_SEEK_AUDIO_MSF*
i--;
RtlEnterCriticalSection( &cache_section );
cp = &cdrom_cache[dev].CurrentPosition;
cp->FormatCode = IOCTL_CDROM_CURRENT_POSITION;
cp->Control = toc.TrackData[i-toc.FirstTrack].Control;
cp->ADR = toc.TrackData[i-toc.FirstTrack].Adr;
cp->FormatCode = IOCTL_CDROM_CURRENT_POSITION;
cp->Control = toc.TrackData[i-toc.FirstTrack].Control;
cp->ADR = toc.TrackData[i-toc.FirstTrack].Adr;
cp->TrackNumber = toc.TrackData[i-toc.FirstTrack].TrackNumber;
cp->IndexNumber = 0; /* FIXME: where do they keep these? */
cp->AbsoluteAddress[0] = 0;
cp->AbsoluteAddress[0] = 0;
cp->AbsoluteAddress[1] = toc.TrackData[i-toc.FirstTrack].Address[1];
cp->AbsoluteAddress[2] = toc.TrackData[i-toc.FirstTrack].Address[2];
cp->AbsoluteAddress[3] = toc.TrackData[i-toc.FirstTrack].Address[3];
frame -= FRAME_OF_TOC(toc,i);
cp->TrackRelativeAddress[0] = 0;
MSF_OF_FRAME(cp->TrackRelativeAddress[1], frame);
MSF_OF_FRAME(cp->TrackRelativeAddress[1], frame);
RtlLeaveCriticalSection( &cache_section );
/* If playing, then issue a seek command, otherwise do nothing */
......@@ -1301,7 +1304,7 @@ static NTSTATUS CDROM_SeekAudioMSF(int dev, int fd, const CDROM_SEEK_AUDIO_MSF*
CDROM_ClearCacheEntry(dev);
return CDROM_GetStatusCode(io);
}
if (sc.header.audio_status==CD_AS_PLAY_IN_PROGRESS)
if (sc.header.audio_status==CD_AS_PLAY_IN_PROGRESS)
{
msf.start_m = audio_msf->M;
......@@ -2126,7 +2129,7 @@ static NTSTATUS DVD_SendKey(int fd, const DVD_COPY_PROTECT_KEY *key)
auth_info.hsk.agid = (int)key->SessionId;
memcpy( auth_info.hsk.key, key->KeyData, DVD_KEY_SIZE );
TRACE("DvdBusKey2\n");
ret = CDROM_GetStatusCode(ioctl( fd, DVD_AUTH, &auth_info ));
break;
......@@ -2183,7 +2186,7 @@ static NTSTATUS DVD_SendKey(int fd, const DVD_COPY_PROTECT_KEY *key)
#else
FIXME("not supported on this O/S\n");
return STATUS_NOT_SUPPORTED;
#endif
#endif
}
/******************************************************************
......@@ -2203,11 +2206,11 @@ static NTSTATUS DVD_ReadKey(int fd, PDVD_COPY_PROTECT_KEY key)
switch (key->KeyType)
{
case DvdDiskKey:
dvd.type = DVD_STRUCT_DISCKEY;
dvd.disckey.agid = (int)key->SessionId;
memset( dvd.disckey.value, 0, DVD_DISCKEY_SIZE );
TRACE("DvdDiskKey\n");
ret = CDROM_GetStatusCode(ioctl( fd, DVD_READ_STRUCT, &dvd ));
if (ret == STATUS_SUCCESS)
......@@ -2218,7 +2221,7 @@ static NTSTATUS DVD_ReadKey(int fd, PDVD_COPY_PROTECT_KEY key)
auth_info.lstk.agid = (int)key->SessionId;
auth_info.lstk.lba = (int)(key->Parameters.TitleOffset.QuadPart>>11);
TRACE("DvdTitleKey session %d Quadpart 0x%08lx offset 0x%08x\n",
(int)key->SessionId, (long)key->Parameters.TitleOffset.QuadPart,
(int)key->SessionId, (long)key->Parameters.TitleOffset.QuadPart,
auth_info.lstk.lba);
ret = CDROM_GetStatusCode(ioctl( fd, DVD_AUTH, &auth_info ));
if (ret == STATUS_SUCCESS)
......@@ -2766,7 +2769,7 @@ static NTSTATUS DVD_ReadStructure(int dev, const DVD_READ_STRUCTURE *structure,
* GetInquiryData
* Implements the IOCTL_GET_INQUIRY_DATA ioctl.
* Returns Inquiry data for all devices on the specified scsi bus
* Returns STATUS_BUFFER_TOO_SMALL if the output buffer is too small,
* Returns STATUS_BUFFER_TOO_SMALL if the output buffer is too small,
* STATUS_INVALID_DEVICE_REQUEST if the given handle isn't to a SCSI device,
* or STATUS_NOT_SUPPORTED if the OS driver is too old
*/
......@@ -2822,29 +2825,21 @@ static NTSTATUS GetInquiryData(int fd, PSCSI_ADAPTER_BUS_INFO BufferOut, DWORD O
}
/******************************************************************
* CDROM_DeviceIoControl
*
*
* cdrom_DeviceIoControl
*/
NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
ULONG dwIoControlCode,
LPVOID lpInBuffer, DWORD nInBufferSize,
LPVOID lpOutBuffer, DWORD nOutBufferSize)
NTSTATUS cdrom_DeviceIoControl( HANDLE device, HANDLE event, PIO_APC_ROUTINE apc, void *apc_user,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer,
ULONG in_size, void *out_buffer, ULONG out_size )
{
DWORD sz = 0;
NTSTATUS status = STATUS_SUCCESS;
int fd, needs_close, dev = 0;
TRACE("%p %s %p %d %p %d %p\n",
hDevice, iocodex(dwIoControlCode), lpInBuffer, nInBufferSize,
lpOutBuffer, nOutBufferSize, piosb);
TRACE( "%p %s %p %d %p %d %p\n", device, iocodex(code), in_buffer, in_size, out_buffer, out_size, io );
piosb->Information = 0;
io->Information = 0;
if ((status = unix_funcs->server_get_unix_fd( hDevice, 0, &fd, &needs_close, NULL, NULL )))
if ((status = server_get_unix_fd( device, 0, &fd, &needs_close, NULL, NULL )))
{
if (status == STATUS_BAD_DEVICE_TYPE) return status; /* no associated fd */
goto error;
......@@ -2868,20 +2863,20 @@ NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
* open the parent if we're trying to eject the disk.
*/
if ((status = get_parent_device( fd, name, sizeof(name) ))) goto error;
if (dwIoControlCode == IOCTL_STORAGE_EJECT_MEDIA)
NtClose( hDevice );
if (code == IOCTL_STORAGE_EJECT_MEDIA)
NtClose( device );
if (needs_close) close( fd );
TRACE("opening parent %s\n", name );
if ((fd = open( name, O_RDONLY )) == -1)
{
status = FILE_GetNtStatus();
status = errno_to_status( errno );
goto error;
}
needs_close = 1;
}
#endif
switch (dwIoControlCode)
switch (code)
{
case IOCTL_CDROM_CHECK_VERIFY:
case IOCTL_DISK_CHECK_VERIFY:
......@@ -2889,7 +2884,7 @@ NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
case IOCTL_STORAGE_CHECK_VERIFY2:
sz = 0;
CDROM_ClearCacheEntry(dev);
if (lpInBuffer != NULL || nInBufferSize != 0 || lpOutBuffer != NULL || nOutBufferSize != 0)
if (in_buffer != NULL || in_size != 0 || out_buffer != NULL || out_size != 0)
status = STATUS_INVALID_PARAMETER;
else status = CDROM_Verify(dev, fd);
break;
......@@ -2903,14 +2898,14 @@ NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
case IOCTL_CDROM_LOAD_MEDIA:
sz = 0;
CDROM_ClearCacheEntry(dev);
if (lpInBuffer != NULL || nInBufferSize != 0 || lpOutBuffer != NULL || nOutBufferSize != 0)
if (in_buffer != NULL || in_size != 0 || out_buffer != NULL || out_size != 0)
status = STATUS_INVALID_PARAMETER;
else status = CDROM_SetTray(fd, FALSE);
break;
case IOCTL_STORAGE_EJECT_MEDIA:
sz = 0;
CDROM_ClearCacheEntry(dev);
if (lpInBuffer != NULL || nInBufferSize != 0 || lpOutBuffer != NULL || nOutBufferSize != 0)
if (in_buffer != NULL || in_size != 0 || out_buffer != NULL || out_size != 0)
status = STATUS_INVALID_PARAMETER;
else
status = CDROM_SetTray(fd, TRUE);
......@@ -2924,216 +2919,216 @@ NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
* lockcount/owner should be handled */
sz = 0;
CDROM_ClearCacheEntry(dev);
if (lpOutBuffer != NULL || nOutBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nInBufferSize < sizeof(PREVENT_MEDIA_REMOVAL)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ControlEjection(fd, lpInBuffer);
if (out_buffer != NULL || out_size != 0) status = STATUS_INVALID_PARAMETER;
else if (in_size < sizeof(PREVENT_MEDIA_REMOVAL)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ControlEjection(fd, in_buffer);
break;
case IOCTL_DISK_GET_MEDIA_TYPES:
case IOCTL_STORAGE_GET_MEDIA_TYPES:
case IOCTL_STORAGE_GET_MEDIA_TYPES_EX:
sz = sizeof(GET_MEDIA_TYPES);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetMediaType(dev, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetMediaType(dev, out_buffer);
break;
case IOCTL_STORAGE_GET_DEVICE_NUMBER:
sz = sizeof(STORAGE_DEVICE_NUMBER);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetDeviceNumber(dev, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetDeviceNumber(dev, out_buffer);
break;
case IOCTL_STORAGE_RESET_DEVICE:
sz = 0;
CDROM_ClearCacheEntry(dev);
if (lpInBuffer != NULL || nInBufferSize != 0 || lpOutBuffer != NULL || nOutBufferSize != 0)
if (in_buffer != NULL || in_size != 0 || out_buffer != NULL || out_size != 0)
status = STATUS_INVALID_PARAMETER;
else status = CDROM_ResetAudio(fd);
break;
case IOCTL_CDROM_GET_CONTROL:
sz = sizeof(CDROM_AUDIO_CONTROL);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetControl(dev, fd, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetControl(dev, fd, out_buffer);
break;
case IOCTL_CDROM_GET_DRIVE_GEOMETRY:
sz = sizeof(DISK_GEOMETRY);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetDriveGeometry(dev, fd, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetDriveGeometry(dev, fd, out_buffer);
break;
case IOCTL_CDROM_DISK_TYPE:
sz = sizeof(CDROM_DISK_DATA);
/* CDROM_ClearCacheEntry(dev); */
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetDiskData(dev, fd, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetDiskData(dev, fd, out_buffer);
break;
/* EPP case IOCTL_CDROM_GET_LAST_SESSION: */
case IOCTL_CDROM_READ_Q_CHANNEL:
sz = sizeof(SUB_Q_CHANNEL_DATA);
if (lpInBuffer == NULL || nInBufferSize < sizeof(CDROM_SUB_Q_DATA_FORMAT))
if (in_buffer == NULL || in_size < sizeof(CDROM_SUB_Q_DATA_FORMAT))
status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ReadQChannel(dev, fd, lpInBuffer, lpOutBuffer);
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ReadQChannel(dev, fd, in_buffer, out_buffer);
break;
case IOCTL_CDROM_READ_TOC:
sz = sizeof(CDROM_TOC);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ReadTOC(dev, fd, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ReadTOC(dev, fd, out_buffer);
break;
/* EPP case IOCTL_CDROM_READ_TOC_EX: */
case IOCTL_CDROM_PAUSE_AUDIO:
sz = 0;
if (lpInBuffer != NULL || nInBufferSize != 0 || lpOutBuffer != NULL || nOutBufferSize != 0)
if (in_buffer != NULL || in_size != 0 || out_buffer != NULL || out_size != 0)
status = STATUS_INVALID_PARAMETER;
else status = CDROM_PauseAudio(fd);
break;
case IOCTL_CDROM_PLAY_AUDIO_MSF:
sz = 0;
if (lpOutBuffer != NULL || nOutBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nInBufferSize < sizeof(CDROM_PLAY_AUDIO_MSF)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_PlayAudioMSF(fd, lpInBuffer);
if (out_buffer != NULL || out_size != 0) status = STATUS_INVALID_PARAMETER;
else if (in_size < sizeof(CDROM_PLAY_AUDIO_MSF)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_PlayAudioMSF(fd, in_buffer);
break;
case IOCTL_CDROM_RESUME_AUDIO:
sz = 0;
if (lpInBuffer != NULL || nInBufferSize != 0 || lpOutBuffer != NULL || nOutBufferSize != 0)
if (in_buffer != NULL || in_size != 0 || out_buffer != NULL || out_size != 0)
status = STATUS_INVALID_PARAMETER;
else status = CDROM_ResumeAudio(fd);
break;
case IOCTL_CDROM_SEEK_AUDIO_MSF:
sz = 0;
if (lpOutBuffer != NULL || nOutBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nInBufferSize < sizeof(CDROM_SEEK_AUDIO_MSF)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_SeekAudioMSF(dev, fd, lpInBuffer);
if (out_buffer != NULL || out_size != 0) status = STATUS_INVALID_PARAMETER;
else if (in_size < sizeof(CDROM_SEEK_AUDIO_MSF)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_SeekAudioMSF(dev, fd, in_buffer);
break;
case IOCTL_CDROM_STOP_AUDIO:
sz = 0;
CDROM_ClearCacheEntry(dev); /* Maybe intention is to change media */
if (lpInBuffer != NULL || nInBufferSize != 0 || lpOutBuffer != NULL || nOutBufferSize != 0)
if (in_buffer != NULL || in_size != 0 || out_buffer != NULL || out_size != 0)
status = STATUS_INVALID_PARAMETER;
else status = CDROM_StopAudio(fd);
break;
case IOCTL_CDROM_GET_VOLUME:
sz = sizeof(VOLUME_CONTROL);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetVolume(fd, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetVolume(fd, out_buffer);
break;
case IOCTL_CDROM_SET_VOLUME:
sz = 0;
CDROM_ClearCacheEntry(dev);
if (lpInBuffer == NULL || nInBufferSize < sizeof(VOLUME_CONTROL) || lpOutBuffer != NULL)
if (in_buffer == NULL || in_size < sizeof(VOLUME_CONTROL) || out_buffer != NULL)
status = STATUS_INVALID_PARAMETER;
else status = CDROM_SetVolume(fd, lpInBuffer);
else status = CDROM_SetVolume(fd, in_buffer);
break;
case IOCTL_CDROM_RAW_READ:
sz = 0;
if (nInBufferSize < sizeof(RAW_READ_INFO)) status = STATUS_INVALID_PARAMETER;
else if (lpOutBuffer == NULL) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_RawRead(fd, lpInBuffer, lpOutBuffer,
nOutBufferSize, &sz);
if (in_size < sizeof(RAW_READ_INFO)) status = STATUS_INVALID_PARAMETER;
else if (out_buffer == NULL) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_RawRead(fd, in_buffer, out_buffer,
out_size, &sz);
break;
case IOCTL_SCSI_GET_ADDRESS:
sz = sizeof(SCSI_ADDRESS);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetAddress(fd, lpOutBuffer);
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_GetAddress(fd, out_buffer);
break;
case IOCTL_SCSI_PASS_THROUGH_DIRECT:
sz = sizeof(SCSI_PASS_THROUGH_DIRECT);
if (lpOutBuffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sizeof(SCSI_PASS_THROUGH_DIRECT)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ScsiPassThroughDirect(fd, lpOutBuffer);
if (out_buffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (out_size < sizeof(SCSI_PASS_THROUGH_DIRECT)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ScsiPassThroughDirect(fd, out_buffer);
break;
case IOCTL_SCSI_PASS_THROUGH:
sz = sizeof(SCSI_PASS_THROUGH);
if (lpOutBuffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sizeof(SCSI_PASS_THROUGH)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ScsiPassThrough(fd, lpOutBuffer);
if (out_buffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (out_size < sizeof(SCSI_PASS_THROUGH)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ScsiPassThrough(fd, out_buffer);
break;
case IOCTL_SCSI_GET_CAPABILITIES:
sz = sizeof(IO_SCSI_CAPABILITIES);
if (lpOutBuffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sizeof(IO_SCSI_CAPABILITIES)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ScsiGetCaps(fd, lpOutBuffer);
if (out_buffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (out_size < sizeof(IO_SCSI_CAPABILITIES)) status = STATUS_BUFFER_TOO_SMALL;
else status = CDROM_ScsiGetCaps(fd, out_buffer);
break;
case IOCTL_DVD_START_SESSION:
sz = sizeof(DVD_SESSION_ID);
if (lpOutBuffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
if (out_buffer == NULL) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else
{
TRACE("before in 0x%08x out 0x%08x\n",(lpInBuffer)?*(PDVD_SESSION_ID)lpInBuffer:0,
*(PDVD_SESSION_ID)lpOutBuffer);
status = DVD_StartSession(fd, lpInBuffer, lpOutBuffer);
TRACE("before in 0x%08x out 0x%08x\n",(lpInBuffer)?*(PDVD_SESSION_ID)lpInBuffer:0,
*(PDVD_SESSION_ID)lpOutBuffer);
TRACE("before in 0x%08x out 0x%08x\n",(in_buffer)?*(PDVD_SESSION_ID)in_buffer:0,
*(PDVD_SESSION_ID)out_buffer);
status = DVD_StartSession(fd, in_buffer, out_buffer);
TRACE("before in 0x%08x out 0x%08x\n",(in_buffer)?*(PDVD_SESSION_ID)in_buffer:0,
*(PDVD_SESSION_ID)out_buffer);
}
break;
case IOCTL_DVD_END_SESSION:
sz = sizeof(DVD_SESSION_ID);
if ((lpInBuffer == NULL) || (nInBufferSize < sz))status = STATUS_INVALID_PARAMETER;
else status = DVD_EndSession(fd, lpInBuffer);
if ((in_buffer == NULL) || (in_size < sz))status = STATUS_INVALID_PARAMETER;
else status = DVD_EndSession(fd, in_buffer);
break;
case IOCTL_DVD_SEND_KEY:
sz = 0;
if (!lpInBuffer ||
(((PDVD_COPY_PROTECT_KEY)lpInBuffer)->KeyLength != nInBufferSize))
if (!in_buffer ||
(((PDVD_COPY_PROTECT_KEY)in_buffer)->KeyLength != in_size))
status = STATUS_INVALID_PARAMETER;
else
{
TRACE("doing DVD_SendKey\n");
status = DVD_SendKey(fd, lpInBuffer);
status = DVD_SendKey(fd, in_buffer);
}
break;
case IOCTL_DVD_READ_KEY:
if (!lpInBuffer ||
(((PDVD_COPY_PROTECT_KEY)lpInBuffer)->KeyLength != nInBufferSize))
if (!in_buffer ||
(((PDVD_COPY_PROTECT_KEY)in_buffer)->KeyLength != in_size))
status = STATUS_INVALID_PARAMETER;
else if (lpInBuffer !=lpOutBuffer) status = STATUS_BUFFER_TOO_SMALL;
else if (in_buffer !=out_buffer) status = STATUS_BUFFER_TOO_SMALL;
else
{
TRACE("doing DVD_READ_KEY\n");
sz = ((PDVD_COPY_PROTECT_KEY)lpInBuffer)->KeyLength;
status = DVD_ReadKey(fd, lpInBuffer);
sz = ((PDVD_COPY_PROTECT_KEY)in_buffer)->KeyLength;
status = DVD_ReadKey(fd, in_buffer);
}
break;
case IOCTL_DVD_GET_REGION:
sz = sizeof(DVD_REGION);
if (lpInBuffer != NULL || nInBufferSize != 0) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz) status = STATUS_BUFFER_TOO_SMALL;
if (in_buffer != NULL || in_size != 0) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz) status = STATUS_BUFFER_TOO_SMALL;
else
{
TRACE("doing DVD_Get_REGION\n");
status = DVD_GetRegion(fd, lpOutBuffer);
status = DVD_GetRegion(fd, out_buffer);
}
break;
case IOCTL_DVD_READ_STRUCTURE:
sz = DVD_ReadStructureSize(lpInBuffer, nInBufferSize);
if (lpInBuffer == NULL || nInBufferSize != sizeof(DVD_READ_STRUCTURE)) status = STATUS_INVALID_PARAMETER;
else if (nOutBufferSize < sz || !lpOutBuffer) status = STATUS_BUFFER_TOO_SMALL;
sz = DVD_ReadStructureSize(in_buffer, in_size);
if (in_buffer == NULL || in_size != sizeof(DVD_READ_STRUCTURE)) status = STATUS_INVALID_PARAMETER;
else if (out_size < sz || !out_buffer) status = STATUS_BUFFER_TOO_SMALL;
else
{
TRACE("doing DVD_READ_STRUCTURE\n");
status = DVD_ReadStructure(fd, lpInBuffer, lpOutBuffer);
status = DVD_ReadStructure(fd, in_buffer, out_buffer);
}
break;
case IOCTL_SCSI_GET_INQUIRY_DATA:
sz = INQ_REPLY_LEN;
status = GetInquiryData(fd, lpOutBuffer, nOutBufferSize);
status = GetInquiryData(fd, out_buffer, out_size);
break;
default:
......@@ -3142,8 +3137,8 @@ NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
}
if (needs_close) close( fd );
error:
piosb->u.Status = status;
piosb->Information = sz;
if (hEvent) NtSetEvent(hEvent, NULL);
io->u.Status = status;
io->Information = sz;
if (event) NtSetEvent(event, NULL);
return status;
}
......@@ -331,7 +331,7 @@ static inline BOOL has_wildcard( const UNICODE_STRING *mask )
return FALSE;
}
static NTSTATUS errno_to_status( int err )
NTSTATUS errno_to_status( int err )
{
TRACE( "errno = %d\n", err );
switch (err)
......@@ -3336,7 +3336,7 @@ NTSTATUS CDECL nt_to_unix_file_name( const UNICODE_STRING *nameW, ANSI_STRING *u
*
* Unmount the specified device.
*/
NTSTATUS CDECL unmount_device( HANDLE handle )
static NTSTATUS unmount_device( HANDLE handle )
{
NTSTATUS status;
int unix_fd, needs_close;
......@@ -4579,6 +4579,51 @@ static NTSTATUS server_write_file( HANDLE handle, HANDLE event, PIO_APC_ROUTINE
return status;
}
/* do an ioctl call through the server */
static NTSTATUS server_ioctl_file( HANDLE handle, HANDLE event,
PIO_APC_ROUTINE apc, PVOID apc_context,
IO_STATUS_BLOCK *io, ULONG code,
const void *in_buffer, ULONG in_size,
PVOID out_buffer, ULONG out_size )
{
struct async_irp *async;
NTSTATUS status;
HANDLE wait_handle;
ULONG options;
if (!(async = (struct async_irp *)alloc_fileio( sizeof(*async), irp_completion, handle )))
return STATUS_NO_MEMORY;
async->buffer = out_buffer;
async->size = out_size;
SERVER_START_REQ( ioctl )
{
req->code = code;
req->async = server_async( handle, &async->io, event, apc, apc_context, io );
wine_server_add_data( req, in_buffer, in_size );
if ((code & 3) != METHOD_BUFFERED) wine_server_add_data( req, out_buffer, out_size );
wine_server_set_reply( req, out_buffer, out_size );
status = virtual_locked_server_call( req );
wait_handle = wine_server_ptr_handle( reply->wait );
options = reply->options;
if (wait_handle && status != STATUS_PENDING)
{
io->u.Status = status;
io->Information = wine_server_reply_size( reply );
}
}
SERVER_END_REQ;
if (status == STATUS_NOT_SUPPORTED)
FIXME("Unsupported ioctl %x (device=%x access=%x func=%x method=%x)\n",
code, code >> 16, (code >> 14) & 3, (code >> 2) & 0xfff, code & 3);
if (status != STATUS_PENDING) RtlFreeHeap( GetProcessHeap(), 0, async );
if (wait_handle) status = wait_async( wait_handle, (options & FILE_SYNCHRONOUS_IO_ALERT), io );
return status;
}
struct io_timeouts
{
......@@ -5353,3 +5398,201 @@ NTSTATUS WINAPI NtWriteFileGather( HANDLE file, HANDLE event, PIO_APC_ROUTINE ap
if (send_completion) add_completion( file, cvalue, status, total, FALSE );
return status;
}
/******************************************************************************
* NtDeviceIoControlFile (NTDLL.@)
*/
NTSTATUS WINAPI NtDeviceIoControlFile( HANDLE handle, HANDLE event, PIO_APC_ROUTINE apc, void *apc_context,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer, ULONG in_size,
void *out_buffer, ULONG out_size )
{
ULONG device = (code >> 16);
NTSTATUS status = STATUS_NOT_SUPPORTED;
TRACE( "(%p,%p,%p,%p,%p,0x%08x,%p,0x%08x,%p,0x%08x)\n",
handle, event, apc, apc_context, io, code, in_buffer, in_size, out_buffer, out_size );
switch (device)
{
case FILE_DEVICE_DISK:
case FILE_DEVICE_CD_ROM:
case FILE_DEVICE_DVD:
case FILE_DEVICE_CONTROLLER:
case FILE_DEVICE_MASS_STORAGE:
status = cdrom_DeviceIoControl( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
break;
case FILE_DEVICE_SERIAL_PORT:
status = serial_DeviceIoControl( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
break;
case FILE_DEVICE_TAPE:
status = tape_DeviceIoControl( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
break;
}
if (status == STATUS_NOT_SUPPORTED || status == STATUS_BAD_DEVICE_TYPE)
return server_ioctl_file( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
if (status != STATUS_PENDING) io->u.Status = status;
return status;
}
/* Tell Valgrind to ignore any holes in structs we will be passing to the
* server */
static void ignore_server_ioctl_struct_holes( ULONG code, const void *in_buffer, ULONG in_size )
{
#ifdef VALGRIND_MAKE_MEM_DEFINED
# define IGNORE_STRUCT_HOLE(buf, size, t, f1, f2) \
do { \
if (FIELD_OFFSET(t, f1) + sizeof(((t *)0)->f1) < FIELD_OFFSET(t, f2)) \
if ((size) >= FIELD_OFFSET(t, f2)) \
VALGRIND_MAKE_MEM_DEFINED( \
(const char *)(buf) + FIELD_OFFSET(t, f1) + sizeof(((t *)0)->f1), \
FIELD_OFFSET(t, f2) - FIELD_OFFSET(t, f1) + sizeof(((t *)0)->f1)); \
} while (0)
switch (code)
{
case FSCTL_PIPE_WAIT:
IGNORE_STRUCT_HOLE(in_buffer, in_size, FILE_PIPE_WAIT_FOR_BUFFER, TimeoutSpecified, Name);
break;
}
#endif
}
/******************************************************************************
* NtFsControlFile (NTDLL.@)
*/
NTSTATUS WINAPI NtFsControlFile( HANDLE handle, HANDLE event, PIO_APC_ROUTINE apc, void *apc_context,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer, ULONG in_size,
void *out_buffer, ULONG out_size )
{
NTSTATUS status;
TRACE( "(%p,%p,%p,%p,%p,0x%08x,%p,0x%08x,%p,0x%08x)\n",
handle, event, apc, apc_context, io, code, in_buffer, in_size, out_buffer, out_size );
if (!io) return STATUS_INVALID_PARAMETER;
ignore_server_ioctl_struct_holes( code, in_buffer, in_size );
switch (code)
{
case FSCTL_DISMOUNT_VOLUME:
status = server_ioctl_file( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
if (!status) status = unmount_device( handle );
return status;
case FSCTL_PIPE_IMPERSONATE:
FIXME("FSCTL_PIPE_IMPERSONATE: impersonating self\n");
status = RtlImpersonateSelf( SecurityImpersonation );
break;
case FSCTL_IS_VOLUME_MOUNTED:
case FSCTL_LOCK_VOLUME:
case FSCTL_UNLOCK_VOLUME:
FIXME("stub! return success - Unsupported fsctl %x (device=%x access=%x func=%x method=%x)\n",
code, code >> 16, (code >> 14) & 3, (code >> 2) & 0xfff, code & 3);
status = STATUS_SUCCESS;
break;
case FSCTL_GET_RETRIEVAL_POINTERS:
{
RETRIEVAL_POINTERS_BUFFER *buffer = (RETRIEVAL_POINTERS_BUFFER *)out_buffer;
FIXME("stub: FSCTL_GET_RETRIEVAL_POINTERS\n");
if (out_size >= sizeof(RETRIEVAL_POINTERS_BUFFER))
{
buffer->ExtentCount = 1;
buffer->StartingVcn.QuadPart = 1;
buffer->Extents[0].NextVcn.QuadPart = 0;
buffer->Extents[0].Lcn.QuadPart = 0;
io->Information = sizeof(RETRIEVAL_POINTERS_BUFFER);
status = STATUS_SUCCESS;
}
else
{
io->Information = 0;
status = STATUS_BUFFER_TOO_SMALL;
}
break;
}
case FSCTL_SET_SPARSE:
TRACE("FSCTL_SET_SPARSE: Ignoring request\n");
io->Information = 0;
status = STATUS_SUCCESS;
break;
default:
return server_ioctl_file( handle, event, apc, apc_context, io, code,
in_buffer, in_size, out_buffer, out_size );
}
if (status != STATUS_PENDING) io->u.Status = status;
return status;
}
/******************************************************************************
* NtFlushBuffersFile (NTDLL.@)
*/
NTSTATUS WINAPI NtFlushBuffersFile( HANDLE handle, IO_STATUS_BLOCK *io )
{
NTSTATUS ret;
HANDLE wait_handle;
enum server_fd_type type;
int fd, needs_close;
if (!io || !virtual_check_buffer_for_write( io, sizeof(*io) )) return STATUS_ACCESS_VIOLATION;
ret = server_get_unix_fd( handle, FILE_WRITE_DATA, &fd, &needs_close, &type, NULL );
if (ret == STATUS_ACCESS_DENIED)
ret = server_get_unix_fd( handle, FILE_APPEND_DATA, &fd, &needs_close, &type, NULL );
if (!ret && (type == FD_TYPE_FILE || type == FD_TYPE_DIR))
{
if (fsync(fd)) ret = errno_to_status( errno );
io->u.Status = ret;
io->Information = 0;
}
else if (!ret && type == FD_TYPE_SERIAL)
{
ret = serial_FlushBuffersFile( fd );
}
else if (ret != STATUS_ACCESS_DENIED)
{
struct async_irp *async;
if (!(async = (struct async_irp *)alloc_fileio( sizeof(*async), irp_completion, handle )))
return STATUS_NO_MEMORY;
async->buffer = NULL;
async->size = 0;
SERVER_START_REQ( flush )
{
req->async = server_async( handle, &async->io, NULL, NULL, NULL, io );
ret = wine_server_call( req );
wait_handle = wine_server_ptr_handle( reply->event );
if (wait_handle && ret != STATUS_PENDING)
{
io->u.Status = ret;
io->Information = 0;
}
}
SERVER_END_REQ;
if (ret != STATUS_PENDING) RtlFreeHeap( GetProcessHeap(), 0, async );
if (wait_handle) ret = wait_async( wait_handle, FALSE, io );
}
if (needs_close) close( fd );
return ret;
}
......@@ -841,9 +841,12 @@ static struct unix_funcs unix_funcs =
NtCurrentTeb,
NtDelayExecution,
NtDeleteFile,
NtDeviceIoControlFile,
NtDuplicateObject,
NtFlushBuffersFile,
NtFlushVirtualMemory,
NtFreeVirtualMemory,
NtFsControlFile,
NtGetContextThread,
NtGetWriteWatch,
NtIsProcessInJob,
......@@ -942,9 +945,7 @@ static struct unix_funcs unix_funcs =
virtual_get_system_info,
virtual_create_builtin_view,
virtual_alloc_thread_stack,
virtual_locked_server_call,
virtual_locked_recvmsg,
virtual_check_buffer_for_write,
virtual_release_address_space,
virtual_set_large_address_space,
init_threading,
......@@ -960,7 +961,6 @@ static struct unix_funcs unix_funcs =
server_release_fd,
server_init_process_done,
nt_to_unix_file_name,
unmount_device,
set_show_dot_files,
__wine_dbg_get_channel_flags,
__wine_dbg_strdup,
......
/* Main file for COMM support
/*
* Serial device support
*
* DEC 93 Erik Bos <erik@xs4all.nl>
* Copyright 1993 Erik Bos
* Copyright 1996 Marcus Meissner
* Copyright 2005,2006 Eric Pouech
*
......@@ -19,6 +20,10 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#if 0
#pragma makedep unix
#endif
#include "config.h"
#include "wine/port.h"
......@@ -61,9 +66,8 @@
#include "winternl.h"
#include "winioctl.h"
#include "ddk/ntddser.h"
#include "ntdll_misc.h"
#include "wine/server.h"
#include "wine/library.h"
#include "unix_private.h"
#include "wine/debug.h"
#ifdef HAVE_LINUX_SERIAL_H
......@@ -130,11 +134,11 @@ static NTSTATUS get_baud_rate(int fd, SERIAL_BAUD_RATE* sbr)
{
struct termios port;
int speed;
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
speed = cfgetospeed(&port);
switch (speed)
......@@ -212,7 +216,7 @@ static NTSTATUS get_hand_flow(int fd, SERIAL_HANDFLOW* shf)
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
/* termios does not support DTR/DSR flow control */
shf->ControlHandShake = 0;
......@@ -260,13 +264,13 @@ static NTSTATUS get_hand_flow(int fd, SERIAL_HANDFLOW* shf)
static NTSTATUS get_line_control(int fd, SERIAL_LINE_CONTROL* slc)
{
struct termios port;
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
#ifdef CMSPAR
switch (port.c_cflag & (PARENB | PARODD | CMSPAR))
#else
......@@ -333,7 +337,7 @@ static NTSTATUS get_modem_status(int fd, DWORD* lpModemStat)
return STATUS_SUCCESS;
}
WARN("TIOCMGET err %s\n", strerror(errno));
status = FILE_GetNtStatus();
status = errno_to_status( errno );
#endif
return status;
}
......@@ -366,11 +370,11 @@ static NTSTATUS get_properties(int fd, SERIAL_COMMPROP *prop)
static NTSTATUS get_special_chars(int fd, SERIAL_CHARS* sc)
{
struct termios port;
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
sc->EofChar = port.c_cc[VEOF];
sc->ErrorChar = 0xFF;
......@@ -394,7 +398,7 @@ static NTSTATUS get_status(int fd, SERIAL_STATUS* ss)
if (ioctl(fd, TIOCOUTQ, &ss->AmountInOutQueue) == -1)
{
WARN("ioctl returned error\n");
status = FILE_GetNtStatus();
status = errno_to_status( errno );
}
#else
ss->AmountInOutQueue = 0; /* FIXME: find a different way to find out */
......@@ -404,7 +408,7 @@ static NTSTATUS get_status(int fd, SERIAL_STATUS* ss)
if (ioctl(fd, TIOCINQ, &ss->AmountInInQueue))
{
WARN("ioctl returned error\n");
status = FILE_GetNtStatus();
status = errno_to_status( errno );
}
#else
ss->AmountInInQueue = 0; /* FIXME: find a different way to find out */
......@@ -467,7 +471,7 @@ static NTSTATUS set_baud_rate(int fd, const SERIAL_BAUD_RATE* sbr)
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
switch (sbr->BaudRate)
......@@ -544,7 +548,7 @@ static NTSTATUS set_baud_rate(int fd, const SERIAL_BAUD_RATE* sbr)
{
struct serial_struct nuts;
int arby;
ioctl(fd, TIOCGSERIAL, &nuts);
nuts.custom_divisor = nuts.baud_base / sbr->BaudRate;
if (!(nuts.custom_divisor)) nuts.custom_divisor = 1;
......@@ -571,7 +575,7 @@ static NTSTATUS set_baud_rate(int fd, const SERIAL_BAUD_RATE* sbr)
if (tcsetattr(fd, TCSANOW, &port) == -1)
{
ERR("tcsetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
return STATUS_SUCCESS;
}
......@@ -594,16 +598,16 @@ static NTSTATUS set_handflow(int fd, const SERIAL_HANDFLOW* shf)
{
struct termios port;
if ((shf->FlowReplace & (SERIAL_RTS_CONTROL | SERIAL_RTS_HANDSHAKE)) ==
if ((shf->FlowReplace & (SERIAL_RTS_CONTROL | SERIAL_RTS_HANDSHAKE)) ==
(SERIAL_RTS_CONTROL | SERIAL_RTS_HANDSHAKE))
return STATUS_NOT_SUPPORTED;
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
#ifdef CRTSCTS
if ((shf->ControlHandShake & SERIAL_CTS_HANDSHAKE) ||
(shf->FlowReplace & SERIAL_RTS_HANDSHAKE))
......@@ -628,7 +632,7 @@ static NTSTATUS set_handflow(int fd, const SERIAL_HANDFLOW* shf)
{
if ((shf->FlowReplace & (SERIAL_RTS_CONTROL|SERIAL_RTS_HANDSHAKE)) == 0)
whack_modem(fd, ~TIOCM_RTS, 0);
else
else
whack_modem(fd, 0, TIOCM_RTS);
}
#endif
......@@ -644,7 +648,7 @@ static NTSTATUS set_handflow(int fd, const SERIAL_HANDFLOW* shf)
if (tcsetattr(fd, TCSANOW, &port) == -1)
{
ERR("tcsetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
return STATUS_SUCCESS;
......@@ -658,7 +662,7 @@ static NTSTATUS set_line_control(int fd, const SERIAL_LINE_CONTROL* slc)
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
#ifdef IMAXBEL
......@@ -757,7 +761,7 @@ static NTSTATUS set_line_control(int fd, const SERIAL_LINE_CONTROL* slc)
if (tcsetattr(fd, TCSANOW, &port) == -1)
{
ERR("tcsetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
return STATUS_SUCCESS;
}
......@@ -771,24 +775,24 @@ static NTSTATUS set_queue_size(int fd, const SERIAL_QUEUE_SIZE* sqs)
static NTSTATUS set_special_chars(int fd, const SERIAL_CHARS* sc)
{
struct termios port;
if (tcgetattr(fd, &port) == -1)
{
ERR("tcgetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
port.c_cc[VEOF ] = sc->EofChar;
/* FIXME: sc->ErrorChar is not supported */
/* FIXME: sc->BreakChar is not supported */
/* FIXME: sc->EventChar is not supported */
port.c_cc[VSTART] = sc->XonChar;
port.c_cc[VSTOP ] = sc->XoffChar;
if (tcsetattr(fd, TCSANOW, &port) == -1)
{
ERR("tcsetattr error '%s'\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
}
return STATUS_SUCCESS;
}
......@@ -800,7 +804,7 @@ static NTSTATUS set_XOff(int fd)
{
if (tcflow(fd, TCOOFF))
{
return FILE_GetNtStatus();
return errno_to_status( errno );
}
return STATUS_SUCCESS;
}
......@@ -812,7 +816,7 @@ static NTSTATUS set_XOn(int fd)
{
if (tcflow(fd, TCOON))
{
return FILE_GetNtStatus();
return errno_to_status( errno );
}
return STATUS_SUCCESS;
}
......@@ -892,7 +896,7 @@ static NTSTATUS get_irq_info(int fd, serial_irq_info *irq_info)
return STATUS_SUCCESS;
}
TRACE("TIOCOUTQ err %s\n", strerror(errno));
return FILE_GetNtStatus();
return errno_to_status( errno );
#endif
return STATUS_SUCCESS;
}
......@@ -951,13 +955,13 @@ static DWORD CALLBACK wait_for_event(LPVOID arg)
async_commio *commio = arg;
int fd, needs_close;
if (!unix_funcs->server_get_unix_fd( commio->hDevice, FILE_READ_DATA | FILE_WRITE_DATA, &fd, &needs_close, NULL, NULL ))
if (!server_get_unix_fd( commio->hDevice, FILE_READ_DATA | FILE_WRITE_DATA, &fd, &needs_close, NULL, NULL ))
{
serial_irq_info new_irq_info;
DWORD new_mstat, dummy, cookie;
LARGE_INTEGER time;
TRACE("device=%p fd=0x%08x mask=0x%08x buffer=%p event=%p irq_info=%p\n",
TRACE("device=%p fd=0x%08x mask=0x%08x buffer=%p event=%p irq_info=%p\n",
commio->hDevice, fd, commio->evtmask, commio->events, commio->hEvent, &commio->irq_info);
time.QuadPart = (ULONGLONG)10000;
......@@ -1103,33 +1107,23 @@ static NTSTATUS xmit_immediate(HANDLE hDevice, int fd, const char* ptr)
/* FIXME: not perfect as it should bypass the in-queue */
WARN("(%p,'%c') not perfect!\n", hDevice, *ptr);
if (write(fd, ptr, 1) != 1)
return FILE_GetNtStatus();
return errno_to_status( errno );
return STATUS_SUCCESS;
}
/******************************************************************
* COMM_DeviceIoControl
*
*
*/
static inline NTSTATUS io_control(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
ULONG dwIoControlCode,
LPVOID lpInBuffer, DWORD nInBufferSize,
LPVOID lpOutBuffer, DWORD nOutBufferSize)
static NTSTATUS io_control( HANDLE device, HANDLE event, PIO_APC_ROUTINE apc, void *apc_user,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer,
ULONG in_size, void *out_buffer, ULONG out_size )
{
DWORD sz = 0, access = FILE_READ_DATA;
NTSTATUS status = STATUS_SUCCESS;
int fd = -1, needs_close = 0;
DWORD sz = 0, access = FILE_READ_DATA;
NTSTATUS status = STATUS_SUCCESS;
int fd = -1, needs_close = 0;
enum server_fd_type type;
TRACE("%p %s %p %d %p %d %p\n",
hDevice, iocode2str(dwIoControlCode), lpInBuffer, nInBufferSize,
lpOutBuffer, nOutBufferSize, piosb);
device, iocode2str(code), in_buffer, in_size, out_buffer, out_size, io);
switch (dwIoControlCode)
switch (code)
{
case IOCTL_SERIAL_GET_TIMEOUTS:
case IOCTL_SERIAL_SET_TIMEOUTS:
......@@ -1139,10 +1133,9 @@ static inline NTSTATUS io_control(HANDLE hDevice,
return STATUS_NOT_SUPPORTED;
}
piosb->Information = 0;
io->Information = 0;
if ((status = unix_funcs->server_get_unix_fd( hDevice, access, &fd, &needs_close, &type, NULL )))
goto error;
if ((status = server_get_unix_fd( device, access, &fd, &needs_close, &type, NULL ))) goto error;
if (type != FD_TYPE_SERIAL)
{
if (needs_close) close( fd );
......@@ -1150,91 +1143,91 @@ static inline NTSTATUS io_control(HANDLE hDevice,
goto error;
}
switch (dwIoControlCode)
switch (code)
{
case IOCTL_SERIAL_CLR_DTR:
#ifdef TIOCM_DTR
if (whack_modem(fd, ~TIOCM_DTR, 0) == -1) status = FILE_GetNtStatus();
if (whack_modem(fd, ~TIOCM_DTR, 0) == -1) status = errno_to_status( errno );
#else
status = STATUS_NOT_SUPPORTED;
#endif
break;
case IOCTL_SERIAL_CLR_RTS:
#ifdef TIOCM_RTS
if (whack_modem(fd, ~TIOCM_RTS, 0) == -1) status = FILE_GetNtStatus();
if (whack_modem(fd, ~TIOCM_RTS, 0) == -1) status = errno_to_status( errno );
#else
status = STATUS_NOT_SUPPORTED;
#endif
break;
case IOCTL_SERIAL_GET_BAUD_RATE:
if (lpOutBuffer && nOutBufferSize == sizeof(SERIAL_BAUD_RATE))
if (out_buffer && out_size == sizeof(SERIAL_BAUD_RATE))
{
if (!(status = get_baud_rate(fd, lpOutBuffer)))
if (!(status = get_baud_rate(fd, out_buffer)))
sz = sizeof(SERIAL_BAUD_RATE);
}
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_GET_CHARS:
if (lpOutBuffer && nOutBufferSize == sizeof(SERIAL_CHARS))
if (out_buffer && out_size == sizeof(SERIAL_CHARS))
{
if (!(status = get_special_chars(fd, lpOutBuffer)))
if (!(status = get_special_chars(fd, out_buffer)))
sz = sizeof(SERIAL_CHARS);
}
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_GET_COMMSTATUS:
if (lpOutBuffer && nOutBufferSize == sizeof(SERIAL_STATUS))
if (out_buffer && out_size == sizeof(SERIAL_STATUS))
{
if (!(status = get_status(fd, lpOutBuffer)))
if (!(status = get_status(fd, out_buffer)))
sz = sizeof(SERIAL_STATUS);
}
else status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_GET_HANDFLOW:
if (lpOutBuffer && nOutBufferSize == sizeof(SERIAL_HANDFLOW))
if (out_buffer && out_size == sizeof(SERIAL_HANDFLOW))
{
if (!(status = get_hand_flow(fd, lpOutBuffer)))
if (!(status = get_hand_flow(fd, out_buffer)))
sz = sizeof(SERIAL_HANDFLOW);
}
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_GET_LINE_CONTROL:
if (lpOutBuffer && nOutBufferSize == sizeof(SERIAL_LINE_CONTROL))
if (out_buffer && out_size == sizeof(SERIAL_LINE_CONTROL))
{
if (!(status = get_line_control(fd, lpOutBuffer)))
if (!(status = get_line_control(fd, out_buffer)))
sz = sizeof(SERIAL_LINE_CONTROL);
}
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_GET_MODEMSTATUS:
if (lpOutBuffer && nOutBufferSize == sizeof(DWORD))
if (out_buffer && out_size == sizeof(DWORD))
{
if (!(status = get_modem_status(fd, lpOutBuffer)))
if (!(status = get_modem_status(fd, out_buffer)))
sz = sizeof(DWORD);
}
else status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_GET_PROPERTIES:
if (lpOutBuffer && nOutBufferSize == sizeof(SERIAL_COMMPROP))
if (out_buffer && out_size == sizeof(SERIAL_COMMPROP))
{
if (!(status = get_properties(fd, lpOutBuffer)))
if (!(status = get_properties(fd, out_buffer)))
sz = sizeof(SERIAL_COMMPROP);
}
else status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_IMMEDIATE_CHAR:
if (lpInBuffer && nInBufferSize == sizeof(CHAR))
status = xmit_immediate(hDevice, fd, lpInBuffer);
if (in_buffer && in_size == sizeof(CHAR))
status = xmit_immediate(device, fd, in_buffer);
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_PURGE:
if (lpInBuffer && nInBufferSize == sizeof(DWORD))
status = purge(fd, *(DWORD*)lpInBuffer);
if (in_buffer && in_size == sizeof(DWORD))
status = purge(fd, *(DWORD*)in_buffer);
else
status = STATUS_INVALID_PARAMETER;
break;
......@@ -1242,8 +1235,8 @@ static inline NTSTATUS io_control(HANDLE hDevice,
FIXME("Unsupported\n");
break;
case IOCTL_SERIAL_SET_BAUD_RATE:
if (lpInBuffer && nInBufferSize == sizeof(SERIAL_BAUD_RATE))
status = set_baud_rate(fd, lpInBuffer);
if (in_buffer && in_size == sizeof(SERIAL_BAUD_RATE))
status = set_baud_rate(fd, in_buffer);
else
status = STATUS_INVALID_PARAMETER;
break;
......@@ -1252,7 +1245,7 @@ static inline NTSTATUS io_control(HANDLE hDevice,
if (ioctl(fd, TIOCCBRK, 0) == -1)
{
TRACE("ioctl failed\n");
status = FILE_GetNtStatus();
status = errno_to_status( errno );
}
#else
FIXME("ioctl not available\n");
......@@ -1264,7 +1257,7 @@ static inline NTSTATUS io_control(HANDLE hDevice,
if (ioctl(fd, TIOCSBRK, 0) == -1)
{
TRACE("ioctl failed\n");
status = FILE_GetNtStatus();
status = errno_to_status( errno );
}
#else
FIXME("ioctl not available\n");
......@@ -1272,39 +1265,39 @@ static inline NTSTATUS io_control(HANDLE hDevice,
#endif
break;
case IOCTL_SERIAL_SET_CHARS:
if (lpInBuffer && nInBufferSize == sizeof(SERIAL_CHARS))
status = set_special_chars(fd, lpInBuffer);
if (in_buffer && in_size == sizeof(SERIAL_CHARS))
status = set_special_chars(fd, in_buffer);
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_SET_DTR:
#ifdef TIOCM_DTR
if (whack_modem(fd, 0, TIOCM_DTR) == -1) status = FILE_GetNtStatus();
if (whack_modem(fd, 0, TIOCM_DTR) == -1) status = errno_to_status( errno );
#else
status = STATUS_NOT_SUPPORTED;
#endif
break;
case IOCTL_SERIAL_SET_HANDFLOW:
if (lpInBuffer && nInBufferSize == sizeof(SERIAL_HANDFLOW))
status = set_handflow(fd, lpInBuffer);
if (in_buffer && in_size == sizeof(SERIAL_HANDFLOW))
status = set_handflow(fd, in_buffer);
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_SET_LINE_CONTROL:
if (lpInBuffer && nInBufferSize == sizeof(SERIAL_LINE_CONTROL))
status = set_line_control(fd, lpInBuffer);
if (in_buffer && in_size == sizeof(SERIAL_LINE_CONTROL))
status = set_line_control(fd, in_buffer);
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_SET_QUEUE_SIZE:
if (lpInBuffer && nInBufferSize == sizeof(SERIAL_QUEUE_SIZE))
status = set_queue_size(fd, lpInBuffer);
if (in_buffer && in_size == sizeof(SERIAL_QUEUE_SIZE))
status = set_queue_size(fd, in_buffer);
else
status = STATUS_INVALID_PARAMETER;
break;
case IOCTL_SERIAL_SET_RTS:
#ifdef TIOCM_RTS
if (whack_modem(fd, 0, TIOCM_RTS) == -1) status = FILE_GetNtStatus();
if (whack_modem(fd, 0, TIOCM_RTS) == -1) status = errno_to_status( errno );
#else
status = STATUS_NOT_SUPPORTED;
#endif
......@@ -1316,52 +1309,49 @@ static inline NTSTATUS io_control(HANDLE hDevice,
status = set_XOn(fd);
break;
case IOCTL_SERIAL_WAIT_ON_MASK:
if (lpOutBuffer && nOutBufferSize == sizeof(DWORD))
if (out_buffer && out_size == sizeof(DWORD))
{
if (!(status = wait_on(hDevice, fd, hEvent, piosb, lpOutBuffer)))
if (!(status = wait_on(device, fd, event, io, out_buffer)))
sz = sizeof(DWORD);
}
else
status = STATUS_INVALID_PARAMETER;
break;
default:
FIXME("Unsupported IOCTL %x (type=%x access=%x func=%x meth=%x)\n",
dwIoControlCode, dwIoControlCode >> 16, (dwIoControlCode >> 14) & 3,
(dwIoControlCode >> 2) & 0xFFF, dwIoControlCode & 3);
FIXME("Unsupported IOCTL %x (type=%x access=%x func=%x meth=%x)\n",
code, code >> 16, (code >> 14) & 3, (code >> 2) & 0xFFF, code & 3);
sz = 0;
status = STATUS_INVALID_PARAMETER;
break;
}
if (needs_close) close( fd );
error:
piosb->u.Status = status;
piosb->Information = sz;
if (hEvent && status != STATUS_PENDING) NtSetEvent(hEvent, NULL);
io->u.Status = status;
io->Information = sz;
if (event && status != STATUS_PENDING) NtSetEvent(event, NULL);
return status;
}
NTSTATUS COMM_DeviceIoControl(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
ULONG dwIoControlCode,
LPVOID lpInBuffer, DWORD nInBufferSize,
LPVOID lpOutBuffer, DWORD nOutBufferSize)
/******************************************************************
* serial_DeviceIoControl
*/
NTSTATUS serial_DeviceIoControl( HANDLE device, HANDLE event, PIO_APC_ROUTINE apc, void *apc_user,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer,
ULONG in_size, void *out_buffer, ULONG out_size )
{
NTSTATUS status;
if (dwIoControlCode == IOCTL_SERIAL_WAIT_ON_MASK)
if (code == IOCTL_SERIAL_WAIT_ON_MASK)
{
HANDLE hev = hEvent;
HANDLE hev = event;
/* this is an ioctl we implement in a non blocking way if hEvent is not
* null
* so we have to explicitly wait if no hEvent is provided
/* this is an ioctl we implement in a non blocking way if event is not null
* so we have to explicitly wait if no event is provided
*/
if (!hev)
{
OBJECT_ATTRIBUTES attr;
attr.Length = sizeof(attr);
attr.RootDirectory = 0;
attr.ObjectName = NULL;
......@@ -1372,10 +1362,9 @@ NTSTATUS COMM_DeviceIoControl(HANDLE hDevice,
if (status) return status;
}
status = io_control(hDevice, hev, UserApcRoutine, UserApcContext,
piosb, dwIoControlCode, lpInBuffer, nInBufferSize,
lpOutBuffer, nOutBufferSize);
if (hev != hEvent)
status = io_control( device, hev, apc, apc_user, io, code,
in_buffer, in_size, out_buffer, out_size );
if (hev != event)
{
if (status == STATUS_PENDING)
{
......@@ -1385,30 +1374,29 @@ NTSTATUS COMM_DeviceIoControl(HANDLE hDevice,
NtClose(hev);
}
}
else status = io_control(hDevice, hEvent, UserApcRoutine, UserApcContext,
piosb, dwIoControlCode, lpInBuffer, nInBufferSize,
lpOutBuffer, nOutBufferSize);
else status = io_control( device, event, apc, apc_user, io, code,
in_buffer, in_size, out_buffer, out_size );
return status;
}
NTSTATUS COMM_FlushBuffersFile( int fd )
NTSTATUS serial_FlushBuffersFile( int fd )
{
#ifdef HAVE_TCDRAIN
while (tcdrain( fd ) == -1)
{
if (errno != EINTR) return FILE_GetNtStatus();
if (errno != EINTR) return errno_to_status( errno );
}
return STATUS_SUCCESS;
#elif defined(TIOCDRAIN)
while (ioctl( fd, TIOCDRAIN ) == -1)
{
if (errno != EINTR) return FILE_GetNtStatus();
if (errno != EINTR) return errno_to_status( errno );
}
return STATUS_SUCCESS;
#elif defined(TCSBRK)
while (ioctl( fd, TCSBRK, 1 ) == -1)
{
if (errno != EINTR) return FILE_GetNtStatus();
if (errno != EINTR) return errno_to_status( errno );
}
return STATUS_SUCCESS;
#else
......
......@@ -18,11 +18,16 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#if 0
#pragma makedep unix
#endif
#include "config.h"
#include "wine/port.h"
#include <stdarg.h>
#include <stdio.h>
#include <errno.h>
#ifdef HAVE_SYS_IOCTL_H
#include <sys/ioctl.h>
#endif
......@@ -42,7 +47,6 @@
#ifndef MT_ST_BLKSIZE_MASK
#define MT_ST_BLKSIZE_MASK 0xffffff
#endif
/* Darwin 7.9.0 has MTSETBSIZ instead of MTSETBLK */
#if !defined(MTSETBLK) && defined(MTSETBSIZ)
#define MTSETBLK MTSETBSIZ
......@@ -55,8 +59,8 @@
#include "winternl.h"
#include "winioctl.h"
#include "ddk/ntddtape.h"
#include "ntdll_misc.h"
#include "wine/server.h"
#include "unix_private.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(tape);
......@@ -91,7 +95,7 @@ static const char *io2str( DWORD io )
static inline NTSTATUS TAPE_GetStatus( int error )
{
if (!error) return STATUS_SUCCESS;
return FILE_GetNtStatus();
return errno_to_status( errno );
}
#endif
......@@ -376,7 +380,7 @@ static NTSTATUS TAPE_SetDriveParams( int fd, const TAPE_SET_DRIVE_PARAMETERS *da
return STATUS_NOT_SUPPORTED;
#endif
}
/******************************************************************
* TAPE_SetMediaParams
*/
......@@ -386,7 +390,7 @@ static NTSTATUS TAPE_SetMediaParams( int fd, const TAPE_SET_MEDIA_PARAMETERS *da
struct mtop cmd;
TRACE( "fd: %d blocksize: 0x%08x\n", fd, data->BlockSize );
cmd.mt_op = MTSETBLK;
cmd.mt_count = data->BlockSize;
......@@ -396,7 +400,7 @@ static NTSTATUS TAPE_SetMediaParams( int fd, const TAPE_SET_MEDIA_PARAMETERS *da
return STATUS_NOT_SUPPORTED;
#endif
}
/******************************************************************
* TAPE_SetPosition
*/
......@@ -511,29 +515,24 @@ static NTSTATUS TAPE_WriteMarks( int fd, const TAPE_WRITE_MARKS *data )
}
/******************************************************************
* TAPE_DeviceIoControl
*
* SEE ALSO
* NtDeviceIoControl.
* tape_DeviceIoControl
*/
NTSTATUS TAPE_DeviceIoControl( HANDLE device, HANDLE event,
PIO_APC_ROUTINE apc, PVOID apc_user, PIO_STATUS_BLOCK io_status,
ULONG io_control, LPVOID in_buffer, DWORD in_size,
LPVOID out_buffer, DWORD out_size )
NTSTATUS tape_DeviceIoControl( HANDLE device, HANDLE event, PIO_APC_ROUTINE apc, void *apc_user,
IO_STATUS_BLOCK *io, ULONG code,
void *in_buffer, ULONG in_size, void *out_buffer, ULONG out_size )
{
DWORD sz = 0;
NTSTATUS status = STATUS_INVALID_PARAMETER;
int fd, needs_close;
TRACE( "%p %s %p %d %p %d %p\n", device, io2str(io_control),
in_buffer, in_size, out_buffer, out_size, io_status );
TRACE( "%p %s %p %d %p %d %p\n", device, io2str(code),
in_buffer, in_size, out_buffer, out_size, io );
io_status->Information = 0;
io->Information = 0;
if ((status = unix_funcs->server_get_unix_fd( device, 0, &fd, &needs_close, NULL, NULL )))
goto error;
if ((status = server_get_unix_fd( device, 0, &fd, &needs_close, NULL, NULL ))) goto error;
switch (io_control)
switch (code)
{
case IOCTL_TAPE_CREATE_PARTITION:
status = TAPE_CreatePartition( fd, in_buffer );
......@@ -552,7 +551,7 @@ NTSTATUS TAPE_DeviceIoControl( HANDLE device, HANDLE event,
out_buffer );
break;
case IOCTL_TAPE_GET_STATUS:
status = FILE_GetNtStatus();
status = errno_to_status( errno );
break;
case IOCTL_TAPE_PREPARE:
status = TAPE_Prepare( fd, in_buffer );
......@@ -575,16 +574,15 @@ NTSTATUS TAPE_DeviceIoControl( HANDLE device, HANDLE event,
break;
default:
FIXME( "Unsupported IOCTL %x (type=%x access=%x func=%x meth=%x)\n",
io_control, io_control >> 16, (io_control >> 14) & 3,
(io_control >> 2) & 0xfff, io_control & 3 );
code, code >> 16, (code >> 14) & 3, (code >> 2) & 0xfff, code & 3 );
break;
}
if (needs_close) close( fd );
error:
io_status->u.Status = status;
io_status->Information = sz;
io->u.Status = status;
io->Information = sz;
if (event) NtSetEvent( event, NULL );
return status;
}
......@@ -90,9 +90,7 @@ extern NTSTATUS CDECL virtual_map_section( HANDLE handle, PVOID *addr_ptr, unsig
extern void CDECL virtual_get_system_info( SYSTEM_BASIC_INFORMATION *info ) DECLSPEC_HIDDEN;
extern NTSTATUS CDECL virtual_create_builtin_view( void *module ) DECLSPEC_HIDDEN;
extern NTSTATUS CDECL virtual_alloc_thread_stack( INITIAL_TEB *stack, SIZE_T reserve_size, SIZE_T commit_size, SIZE_T *pthread_size ) DECLSPEC_HIDDEN;
extern unsigned int CDECL virtual_locked_server_call( void *req_ptr ) DECLSPEC_HIDDEN;
extern ssize_t CDECL virtual_locked_recvmsg( int fd, struct msghdr *hdr, int flags ) DECLSPEC_HIDDEN;
extern BOOL CDECL virtual_check_buffer_for_write( void *ptr, SIZE_T size ) DECLSPEC_HIDDEN;
extern void CDECL virtual_release_address_space(void) DECLSPEC_HIDDEN;
extern void CDECL virtual_set_large_address_space(void) DECLSPEC_HIDDEN;
......@@ -116,7 +114,6 @@ extern NTSTATUS CDECL exec_process( const UNICODE_STRING *cmdline, const pe_imag
extern NTSTATUS CDECL nt_to_unix_file_name( const UNICODE_STRING *nameW, ANSI_STRING *unix_name_ret,
UINT disposition, BOOLEAN check_case ) DECLSPEC_HIDDEN;
extern NTSTATUS CDECL unmount_device( HANDLE handle ) DECLSPEC_HIDDEN;
extern void CDECL set_show_dot_files( BOOL enable ) DECLSPEC_HIDDEN;
extern const char *data_dir DECLSPEC_HIDDEN;
......@@ -173,11 +170,13 @@ extern NTSTATUS virtual_alloc_teb( TEB **ret_teb ) DECLSPEC_HIDDEN;
extern void virtual_free_teb( TEB *teb ) DECLSPEC_HIDDEN;
extern void virtual_map_user_shared_data(void) DECLSPEC_HIDDEN;
extern NTSTATUS virtual_handle_fault( LPCVOID addr, DWORD err, BOOL on_signal_stack ) DECLSPEC_HIDDEN;
extern unsigned int virtual_locked_server_call( void *req_ptr ) DECLSPEC_HIDDEN;
extern ssize_t virtual_locked_read( int fd, void *addr, size_t size ) DECLSPEC_HIDDEN;
extern ssize_t virtual_locked_pread( int fd, void *addr, size_t size, off_t offset ) DECLSPEC_HIDDEN;
extern BOOL virtual_is_valid_code_address( const void *addr, SIZE_T size ) DECLSPEC_HIDDEN;
extern int virtual_handle_stack_fault( void *addr ) DECLSPEC_HIDDEN;
extern BOOL virtual_check_buffer_for_read( const void *ptr, SIZE_T size ) DECLSPEC_HIDDEN;
extern BOOL virtual_check_buffer_for_write( void *ptr, SIZE_T size ) DECLSPEC_HIDDEN;
extern SIZE_T virtual_uninterrupted_read_memory( const void *addr, void *buffer, SIZE_T size ) DECLSPEC_HIDDEN;
extern NTSTATUS virtual_uninterrupted_write_memory( void *addr, const void *buffer, SIZE_T size ) DECLSPEC_HIDDEN;
extern void virtual_set_force_exec( BOOL enable ) DECLSPEC_HIDDEN;
......@@ -193,6 +192,18 @@ extern void DECLSPEC_NORETURN signal_start_thread( PRTL_THREAD_START_ROUTINE ent
BOOL suspend, void *relay, TEB *teb ) DECLSPEC_HIDDEN;
extern void DECLSPEC_NORETURN signal_exit_thread( int status, void (*func)(int) ) DECLSPEC_HIDDEN;
extern NTSTATUS cdrom_DeviceIoControl( HANDLE device, HANDLE event, PIO_APC_ROUTINE apc, void *apc_user,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer,
ULONG in_size, void *out_buffer, ULONG out_size ) DECLSPEC_HIDDEN;
extern NTSTATUS serial_DeviceIoControl( HANDLE device, HANDLE event, PIO_APC_ROUTINE apc, void *apc_user,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer,
ULONG in_size, void *out_buffer, ULONG out_size ) DECLSPEC_HIDDEN;
extern NTSTATUS serial_FlushBuffersFile( int fd ) DECLSPEC_HIDDEN;
extern NTSTATUS tape_DeviceIoControl( HANDLE device, HANDLE event, PIO_APC_ROUTINE apc, void *apc_user,
IO_STATUS_BLOCK *io, ULONG code, void *in_buffer,
ULONG in_size, void *out_buffer, ULONG out_size ) DECLSPEC_HIDDEN;
extern NTSTATUS errno_to_status( int err ) DECLSPEC_HIDDEN;
extern void init_files(void) DECLSPEC_HIDDEN;
extern void dbg_init(void) DECLSPEC_HIDDEN;
......
......@@ -2840,7 +2840,7 @@ static NTSTATUS check_write_access( void *base, size_t size, BOOL *has_write_wat
/***********************************************************************
* virtual_locked_server_call
*/
unsigned int CDECL virtual_locked_server_call( void *req_ptr )
unsigned int virtual_locked_server_call( void *req_ptr )
{
struct __server_request_info * const req = req_ptr;
sigset_t sigset;
......@@ -3040,7 +3040,7 @@ BOOL virtual_check_buffer_for_read( const void *ptr, SIZE_T size )
*
* Check if a memory buffer can be written to, triggering page faults if needed for write watches.
*/
BOOL CDECL virtual_check_buffer_for_write( void *ptr, SIZE_T size )
BOOL virtual_check_buffer_for_write( void *ptr, SIZE_T size )
{
if (!size) return TRUE;
if (!ptr) return FALSE;
......
......@@ -28,7 +28,7 @@ struct ldt_copy;
struct msghdr;
/* increment this when you change the function table */
#define NTDLL_UNIXLIB_VERSION 49
#define NTDLL_UNIXLIB_VERSION 50
struct unix_funcs
{
......@@ -86,13 +86,22 @@ struct unix_funcs
TEB * (WINAPI *NtCurrentTeb)(void);
NTSTATUS (WINAPI *NtDelayExecution)( BOOLEAN alertable, const LARGE_INTEGER *timeout );
NTSTATUS (WINAPI *NtDeleteFile)( OBJECT_ATTRIBUTES *attr );
NTSTATUS (WINAPI *NtDeviceIoControlFile)( HANDLE handle, HANDLE event, PIO_APC_ROUTINE apc,
void *apc_context, IO_STATUS_BLOCK *io, ULONG code,
void *in_buffer, ULONG in_size,
void *out_buffer, ULONG out_size );
NTSTATUS (WINAPI *NtDuplicateObject)( HANDLE source_process, HANDLE source,
HANDLE dest_process, HANDLE *dest,
ACCESS_MASK access, ULONG attributes, ULONG options );
NTSTATUS (WINAPI *NtFlushBuffersFile)( HANDLE handle, IO_STATUS_BLOCK *io );
NTSTATUS (WINAPI *NtFlushVirtualMemory)( HANDLE process, LPCVOID *addr_ptr,
SIZE_T *size_ptr, ULONG unknown );
NTSTATUS (WINAPI *NtFreeVirtualMemory)( HANDLE process, PVOID *addr_ptr,
SIZE_T *size_ptr, ULONG type );
NTSTATUS (WINAPI *NtFsControlFile)( HANDLE handle, HANDLE event, PIO_APC_ROUTINE apc,
void *apc_context, IO_STATUS_BLOCK *io, ULONG code,
void *in_buffer, ULONG in_size,
void *out_buffer, ULONG out_size );
NTSTATUS (WINAPI *NtGetContextThread)( HANDLE handle, CONTEXT *context );
NTSTATUS (WINAPI *NtGetWriteWatch)( HANDLE process, ULONG flags, PVOID base, SIZE_T size,
PVOID *addresses, ULONG_PTR *count, ULONG *granularity );
......@@ -266,9 +275,7 @@ struct unix_funcs
void (CDECL *virtual_get_system_info)( SYSTEM_BASIC_INFORMATION *info );
NTSTATUS (CDECL *virtual_create_builtin_view)( void *module );
NTSTATUS (CDECL *virtual_alloc_thread_stack)( INITIAL_TEB *stack, SIZE_T reserve_size, SIZE_T commit_size, SIZE_T *pthread_size );
unsigned int (CDECL *virtual_locked_server_call)( void *req_ptr );
ssize_t (CDECL *virtual_locked_recvmsg)( int fd, struct msghdr *hdr, int flags );
BOOL (CDECL *virtual_check_buffer_for_write)( void *ptr, SIZE_T size );
void (CDECL *virtual_release_address_space)(void);
void (CDECL *virtual_set_large_address_space)(void);
......@@ -295,7 +302,6 @@ struct unix_funcs
/* file functions */
NTSTATUS (CDECL *nt_to_unix_file_name)( const UNICODE_STRING *nameW, ANSI_STRING *unix_name_ret,
UINT disposition, BOOLEAN check_case );
NTSTATUS (CDECL *unmount_device)( HANDLE handle );
void (CDECL *set_show_dot_files)( BOOL enable );
/* debugging functions */
......
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