ntdll / kernel32: #43
Eric Pouech
pouech-eric at wanadoo.fr
Wed Feb 4 14:55:16 CST 2004
Changes for device & VxD management (kernel)
- remove server/device.c and all the associated hacks
- opening a device is now implemented as opening a unix file
(either a real unix device, or an empty file for VxDs & TSRs)
Notes: server/device.c has to be removed
-------------- next part --------------
diff -u -N -r -x '*~' -x '.#*' -x CVS dlls/kernel42/device.c dlls/kernel/device.c
--- dlls/kernel42/device.c 2004-01-16 19:58:25.000000000 +0100
+++ dlls/kernel/device.c 2004-01-18 21:11:05.000000000 +0100
@@ -24,6 +24,7 @@
#include "wine/port.h"
#include <stdlib.h>
+#include <stdio.h>
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
@@ -40,19 +41,23 @@
#include <string.h>
#include <stdarg.h>
#include <time.h>
+#include <dirent.h>
+#define NONAMELESSUNION
+#define NONAMELESSSTRUCT
#include "ntstatus.h"
#include "windef.h"
#include "winbase.h"
#include "winreg.h"
#include "winerror.h"
#include "winnls.h"
-#include "file.h"
#include "winioctl.h"
#include "winnt.h"
#include "iphlpapi.h"
+#include "wine/winbase16.h"
#include "kernel_private.h"
#include "wine/server.h"
+#include "wine/library.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(file);
@@ -132,190 +137,182 @@
struct VxDInfo
{
LPCSTR name;
- WORD id;
BOOL (*deviceio)(DWORD, LPVOID, DWORD,
- LPVOID, DWORD, LPDWORD, LPOVERLAPPED);
+ LPVOID, DWORD, LPDWORD, LPOVERLAPPED);
};
static const struct VxDInfo VxDList[] =
{
/* Standard VxD IDs */
- { "VMM", 0x0001, NULL },
- { "DEBUG", 0x0002, NULL },
- { "VPICD", 0x0003, NULL },
- { "VDMAD", 0x0004, NULL },
- { "VTD", 0x0005, NULL },
- { "V86MMGR", 0x0006, NULL },
- { "PAGESWAP", 0x0007, NULL },
- { "PARITY", 0x0008, NULL },
- { "REBOOT", 0x0009, NULL },
- { "VDD", 0x000A, NULL },
- { "VSD", 0x000B, NULL },
- { "VMD", 0x000C, NULL },
- { "VKD", 0x000D, NULL },
- { "VCD", 0x000E, DeviceIo_VCD },
- { "VPD", 0x000F, NULL },
- { "BLOCKDEV", 0x0010, NULL },
- { "VMCPD", 0x0011, NULL },
- { "EBIOS", 0x0012, NULL },
- { "BIOSXLAT", 0x0013, NULL },
- { "VNETBIOS", 0x0014, DeviceIo_NetBIOS },
- { "DOSMGR", 0x0015, NULL },
- { "WINLOAD", 0x0016, NULL },
- { "SHELL", 0x0017, NULL },
- { "VMPOLL", 0x0018, NULL },
- { "VPROD", 0x0019, NULL },
- { "DOSNET", 0x001A, NULL },
- { "VFD", 0x001B, NULL },
- { "VDD2", 0x001C, NULL },
- { "WINDEBUG", 0x001D, NULL },
- { "TSRLOAD", 0x001E, NULL },
- { "BIOSHOOK", 0x001F, NULL },
- { "INT13", 0x0020, NULL },
- { "PAGEFILE", 0x0021, NULL },
- { "SCSI", 0x0022, NULL },
- { "MCA_POS", 0x0023, NULL },
- { "SCSIFD", 0x0024, NULL },
- { "VPEND", 0x0025, NULL },
- { "VPOWERD", 0x0026, NULL },
- { "VXDLDR", 0x0027, NULL },
- { "NDIS", 0x0028, NULL },
- { "BIOS_EXT", 0x0029, NULL },
- { "VWIN32", 0x002A, DeviceIo_VWin32 },
- { "VCOMM", 0x002B, NULL },
- { "SPOOLER", 0x002C, NULL },
- { "WIN32S", 0x002D, NULL },
- { "DEBUGCMD", 0x002E, NULL },
-
- { "VNB", 0x0031, DeviceIo_VNB },
- { "SERVER", 0x0032, NULL },
- { "CONFIGMG", 0x0033, NULL },
- { "DWCFGMG", 0x0034, NULL },
- { "SCSIPORT", 0x0035, NULL },
- { "VFBACKUP", 0x0036, NULL },
- { "ENABLE", 0x0037, NULL },
- { "VCOND", 0x0038, NULL },
-
- { "EFAX", 0x003A, NULL },
- { "DSVXD", 0x003B, NULL },
- { "ISAPNP", 0x003C, NULL },
- { "BIOS", 0x003D, NULL },
- { "WINSOCK", 0x003E, NULL },
- { "WSOCK", 0x003E, NULL },
- { "WSIPX", 0x003F, NULL },
- { "IFSMgr", 0x0040, DeviceIo_IFSMgr },
- { "VCDFSD", 0x0041, NULL },
- { "MRCI2", 0x0042, NULL },
- { "PCI", 0x0043, NULL },
- { "PELOADER", 0x0044, NULL },
- { "EISA", 0x0045, NULL },
- { "DRAGCLI", 0x0046, NULL },
- { "DRAGSRV", 0x0047, NULL },
- { "PERF", 0x0048, NULL },
- { "AWREDIR", 0x0049, NULL },
-
+ { "VMM", NULL },
+ { "DEBUG", NULL },
+ { "VPICD", NULL },
+ { "VDMAD", NULL },
+ { "VTD", NULL },
+ { "V86MMGR", NULL },
+ { "PAGESWAP", NULL },
+ { "PARITY", NULL },
+ { "REBOOT", NULL },
+ { "VDD", NULL },
+ { "VSD", NULL },
+ { "VMD", NULL },
+ { "VKD", NULL },
+ { "VCD", DeviceIo_VCD },
+ { "VPD", NULL },
+ { "BLOCKDEV", NULL },
+ { "VMCPD", NULL },
+ { "EBIOS", NULL },
+ { "BIOSXLAT", NULL },
+ { "VNETBIOS", DeviceIo_NetBIOS },
+ { "DOSMGR", NULL },
+ { "WINLOAD", NULL },
+ { "SHELL", NULL },
+ { "VMPOLL", NULL },
+ { "VPROD", NULL },
+ { "DOSNET", NULL },
+ { "VFD", NULL },
+ { "VDD2", NULL },
+ { "WINDEBUG", NULL },
+ { "TSRLOAD", NULL },
+ { "BIOSHOOK", NULL },
+ { "INT13", NULL },
+ { "PAGEFILE", NULL },
+ { "SCSI", NULL },
+ { "MCA_POS", NULL },
+ { "SCSIFD", NULL },
+ { "VPEND", NULL },
+ { "VPOWERD", NULL },
+ { "VXDLDR", NULL },
+ { "NDIS", NULL },
+ { "BIOS_EXT", NULL },
+ { "VWIN32", DeviceIo_VWin32 },
+ { "VCOMM", NULL },
+ { "SPOOLER", NULL },
+ { "WIN32S", NULL },
+ { "DEBUGCMD", NULL },
+
+ { "VNB", DeviceIo_VNB },
+ { "SERVER", NULL },
+ { "CONFIGMG", NULL },
+ { "DWCFGMG", NULL },
+ { "SCSIPORT", NULL },
+ { "VFBACKUP", NULL },
+ { "ENABLE", NULL },
+ { "VCOND", NULL },
+
+ { "EFAX", NULL },
+ { "DSVXD", NULL },
+ { "ISAPNP", NULL },
+ { "BIOS", NULL },
+ { "WINSOCK", NULL },
+ { "WSOCK", NULL },
+ { "WSIPX", NULL },
+ { "IFSMgr", DeviceIo_IFSMgr },
+ { "VCDFSD", NULL },
+ { "MRCI2", NULL },
+ { "PCI", NULL },
+ { "PELOADER", NULL },
+ { "EISA", NULL },
+ { "DRAGCLI", NULL },
+ { "DRAGSRV", NULL },
+ { "PERF", NULL },
+ { "AWREDIR", NULL },
+
/* Far East support */
- { "ETEN", 0x0060, NULL },
- { "CHBIOS", 0x0061, NULL },
- { "VMSGD", 0x0062, NULL },
- { "VPPID", 0x0063, NULL },
- { "VIME", 0x0064, NULL },
- { "VHBIOSD", 0x0065, NULL },
+ { "ETEN", NULL },
+ { "CHBIOS", NULL },
+ { "VMSGD", NULL },
+ { "VPPID", NULL },
+ { "VIME", NULL },
+ { "VHBIOSD", NULL },
/* Multimedia OEM IDs */
- { "VTDAPI", 0x0442, DeviceIo_VTDAPI },
- { "MMDEVLDR", 0x044A, DeviceIo_MMDEVLDR },
+ { "VTDAPI", DeviceIo_VTDAPI },
+ { "MMDEVLDR", DeviceIo_MMDEVLDR },
/* Network Device IDs */
- { "VNetSup", 0x0480, NULL },
- { "VRedir", 0x0481, NULL },
- { "VBrowse", 0x0482, NULL },
- { "VSHARE", 0x0483, NULL },
- { "IFSMgr", 0x0484, NULL },
- { "MEMPROBE", 0x0485, NULL },
- { "VFAT", 0x0486, NULL },
- { "NWLINK", 0x0487, NULL },
- { "VNWLINK", 0x0487, NULL },
- { "NWSUP", 0x0487, NULL },
- { "VTDI", 0x0488, NULL },
- { "VIP", 0x0489, NULL },
- { "VTCP", 0x048A, NULL },
- { "VCache", 0x048B, NULL },
- { "VUDP", 0x048C, NULL },
- { "VAsync", 0x048D, NULL },
- { "NWREDIR", 0x048E, NULL },
- { "STAT80", 0x048F, NULL },
- { "SCSIPORT", 0x0490, NULL },
- { "FILESEC", 0x0491, NULL },
- { "NWSERVER", 0x0492, NULL },
- { "SECPROV", 0x0493, NULL },
- { "NSCL", 0x0494, NULL },
- { "WSTCP", 0x0495, NULL },
- { "NDIS2SUP", 0x0496, NULL },
- { "MSODISUP", 0x0497, NULL },
- { "Splitter", 0x0498, NULL },
- { "PPP", 0x0499, NULL },
- { "VDHCP", 0x049A, DeviceIo_DHCP },
- { "VNBT", 0x049B, NULL },
- { "LOGGER", 0x049D, NULL },
- { "EFILTER", 0x049E, NULL },
- { "FFILTER", 0x049F, NULL },
- { "TFILTER", 0x04A0, NULL },
- { "AFILTER", 0x04A1, NULL },
- { "IRLAMP", 0x04A2, NULL },
-
- { "PCCARD", 0x097C, DeviceIo_PCCARD },
- { "HASP95", 0x3721, DeviceIo_HASP },
+ { "VNetSup", NULL },
+ { "VRedir", NULL },
+ { "VBrowse", NULL },
+ { "VSHARE", NULL },
+ { "IFSMgr", NULL },
+ { "MEMPROBE", NULL },
+ { "VFAT", NULL },
+ { "NWLINK", NULL },
+ { "VNWLINK", NULL },
+ { "NWSUP", NULL },
+ { "VTDI", NULL },
+ { "VIP", NULL },
+ { "VTCP", NULL },
+ { "VCache", NULL },
+ { "VUDP", NULL },
+ { "VAsync", NULL },
+ { "NWREDIR", NULL },
+ { "STAT80", NULL },
+ { "SCSIPORT", NULL },
+ { "FILESEC", NULL },
+ { "NWSERVER", NULL },
+ { "SECPROV", NULL },
+ { "NSCL", NULL },
+ { "WSTCP", NULL },
+ { "NDIS2SUP", NULL },
+ { "MSODISUP", NULL },
+ { "Splitter", NULL },
+ { "PPP", NULL },
+ { "VDHCP", DeviceIo_DHCP },
+ { "VNBT", NULL },
+ { "LOGGER", NULL },
+ { "EFILTER", NULL },
+ { "FFILTER", NULL },
+ { "TFILTER", NULL },
+ { "AFILTER", NULL },
+ { "IRLAMP", NULL },
+
+
+ { "PCCARD", DeviceIo_PCCARD },
+ { "HASP95", DeviceIo_HASP },
/* WINE additions, ids unknown */
- { "MONODEBG.VXD", 0x4242, DeviceIo_MONODEBG },
+ { "MONODEBG.VXD", DeviceIo_MONODEBG },
- { NULL, 0, NULL }
+ { NULL, NULL }
};
-HANDLE DEVICE_Open( LPCWSTR filenameW, DWORD access, LPSECURITY_ATTRIBUTES sa )
+static const struct VxDInfo* lookup_vxd(HANDLE hDevice)
{
- const struct VxDInfo *info;
- char filename[MAX_PATH];
-
- if (!WideCharToMultiByte(CP_ACP, 0, filenameW, -1, filename, MAX_PATH, NULL, NULL))
- {
- SetLastError( ERROR_FILE_NOT_FOUND );
- return 0;
- }
-
- for (info = VxDList; info->name; info++)
- if (!strncasecmp( info->name, filename, strlen(info->name) ))
- return FILE_CreateDevice( info->id | 0x10000, access, sa );
-
- FIXME( "Unknown/unsupported VxD %s. Try setting Windows version to 'nt40' or 'win31'.\n",
- filename);
-
- SetLastError( ERROR_FILE_NOT_FOUND );
- return 0;
-}
-
-static DWORD DEVICE_GetClientID( HANDLE handle )
-{
- DWORD ret = 0;
- SERVER_START_REQ( get_device_id )
- {
- req->handle = handle;
- if (!wine_server_call( req )) ret = reply->id;
- }
- SERVER_END_REQ;
- return ret;
-}
-
-static const struct VxDInfo *DEVICE_GetInfo( DWORD clientID )
-{
- const struct VxDInfo *info = NULL;
-
- if (clientID & 0x10000)
- {
- for (info = VxDList; info->name; info++)
- if (info->id == LOWORD(clientID)) break;
+ struct stat st_ref, st;
+ int fd;
+ char p[MAX_PATH], *l;
+ DIR* dir;
+ struct dirent* de;
+ const struct VxDInfo*info = NULL;
+
+ wine_server_handle_to_fd( hDevice, GENERIC_READ, &fd, NULL, NULL );
+ if (fd == -1) return NULL;
+
+ if (fstat(fd, &st_ref) != -1)
+ {
+ sprintf(p, "%s/DosDevices/", wine_get_config_dir());
+ l = p + strlen(p);
+ dir = opendir(p);
+ if (dir)
+ {
+ while ((de = readdir(dir)))
+ {
+ strcpy(l, de->d_name);
+ if (stat(p, &st) != -1 && st.st_dev == st_ref.st_dev &&
+ st.st_ino == st_ref.st_ino)
+ {
+ for (info = VxDList; info->name; info++)
+ if (!strcmp(info->name, de->d_name))
+ break;
+ break;
+ }
+ }
+ closedir(dir);
+ }
}
+ close(fd);
return info;
}
@@ -329,78 +326,65 @@
* GetLastError can decipher.
*/
BOOL WINAPI DeviceIoControl(HANDLE hDevice, DWORD dwIoControlCode,
- LPVOID lpvInBuffer, DWORD cbInBuffer,
- LPVOID lpvOutBuffer, DWORD cbOutBuffer,
- LPDWORD lpcbBytesReturned,
- LPOVERLAPPED lpOverlapped)
-{
- DWORD clientID;
+ LPVOID lpvInBuffer, DWORD cbInBuffer,
+ LPVOID lpvOutBuffer, DWORD cbOutBuffer,
+ LPDWORD lpcbBytesReturned, LPOVERLAPPED lpOverlapped)
+{
+ TRACE( "(%p,%ld,%p,%ld,%p,%ld,%p,%p)\n",
+ hDevice,dwIoControlCode,lpvInBuffer,cbInBuffer,
+ lpvOutBuffer,cbOutBuffer,lpcbBytesReturned,lpOverlapped );
- TRACE( "(%p,%ld,%p,%ld,%p,%ld,%p,%p)\n",
- hDevice,dwIoControlCode,lpvInBuffer,cbInBuffer,
- lpvOutBuffer,cbOutBuffer,lpcbBytesReturned,lpOverlapped );
-
- if (!(clientID = DEVICE_GetClientID( hDevice )))
- {
- SetLastError( ERROR_INVALID_PARAMETER );
- return FALSE;
- }
-
- /* Check if this is a user defined control code for a VxD */
- if( HIWORD( dwIoControlCode ) == 0 )
- {
- const struct VxDInfo *info;
- if (!(info = DEVICE_GetInfo( clientID )))
- {
- FIXME( "No device found for id %lx\n", clientID);
- }
- else if ( info->deviceio )
- {
- return info->deviceio( dwIoControlCode,
- lpvInBuffer, cbInBuffer,
- lpvOutBuffer, cbOutBuffer,
- lpcbBytesReturned, lpOverlapped );
- }
- else
- {
- FIXME( "Unimplemented control %ld for VxD device %s\n",
- dwIoControlCode, info->name ? info->name : "???" );
- /* FIXME: this is for invalid calls on W98SE,
- * but maybe we should use ERROR_CALL_NOT_IMPLEMENTED
- * instead ? */
- SetLastError( ERROR_INVALID_FUNCTION );
- }
- }
- else
- {
- NTSTATUS status;
-
- if (lpOverlapped)
- {
- status = NtDeviceIoControlFile(hDevice, lpOverlapped->hEvent,
- NULL, NULL,
- (PIO_STATUS_BLOCK)lpOverlapped,
- dwIoControlCode,
- lpvInBuffer, cbInBuffer,
- lpvOutBuffer, cbOutBuffer);
- if (status) SetLastError(RtlNtStatusToDosError(status));
- if (lpcbBytesReturned) *lpcbBytesReturned = lpOverlapped->InternalHigh;
- return !status;
- }
- else
- {
- IO_STATUS_BLOCK iosb;
+ /* Check if this is a user defined control code for a VxD */
+ if ( HIWORD( dwIoControlCode ) == 0 )
+ {
+ const struct VxDInfo *info;
+ if (!(info = lookup_vxd(hDevice)))
+ {
+ FIXME( "No device found for hDevice %p\n", hDevice);
+ SetLastError( ERROR_FILE_NOT_FOUND );
+ return FALSE;
+ }
+ else if ( !info->deviceio )
+ {
+ FIXME( "Unimplemented ioproc for VxD device %s, control=%lx\n",
+ info->name ? info->name : "???", dwIoControlCode );
+ /* FIXME: this is for invalid calls on W98SE,
+ * but maybe we should use ERROR_CALL_NOT_IMPLEMENTED
+ * instead ? */
+ SetLastError( ERROR_INVALID_FUNCTION );
+ return FALSE;
+ }
+ return info->deviceio( dwIoControlCode,
+ lpvInBuffer, cbInBuffer,
+ lpvOutBuffer, cbOutBuffer,
+ lpcbBytesReturned, lpOverlapped );
+ }
+ if (lpOverlapped)
+ {
+ NTSTATUS status;
+
+ status = NtDeviceIoControlFile(hDevice, lpOverlapped->hEvent,
+ NULL, NULL,
+ (PIO_STATUS_BLOCK)lpOverlapped,
+ dwIoControlCode,
+ lpvInBuffer, cbInBuffer,
+ lpvOutBuffer, cbOutBuffer);
+ if (status) SetLastError(RtlNtStatusToDosError(status));
+ if (lpcbBytesReturned) *lpcbBytesReturned = lpOverlapped->InternalHigh;
+ return !status;
+ }
+ else
+ {
+ IO_STATUS_BLOCK iosb;
- status = NtDeviceIoControlFile(hDevice, NULL, NULL, NULL, &iosb,
- dwIoControlCode,
- lpvInBuffer, cbInBuffer,
- lpvOutBuffer, cbOutBuffer);
- if (status) SetLastError(RtlNtStatusToDosError(status));
- if (lpcbBytesReturned) *lpcbBytesReturned = iosb.Information;
- return !status;
- }
- }
- return FALSE;
+ NtDeviceIoControlFile(hDevice, NULL, NULL, NULL, &iosb,
+ dwIoControlCode,
+ lpvInBuffer, cbInBuffer,
+ lpvOutBuffer, cbOutBuffer);
+ if (iosb.u.Status) SetLastError(RtlNtStatusToDosError(iosb.u.Status));
+ if (lpcbBytesReturned) *lpcbBytesReturned = iosb.Information;
+ return !iosb.u.Status;
+ }
}
/***********************************************************************
diff -u -N -r -x '*~' -x '.#*' -x CVS dlls/kernel42/kernel32.spec dlls/kernel/kernel32.spec
--- dlls/kernel42/kernel32.spec 2004-02-01 14:10:48.000000000 +0100
+++ dlls/kernel/kernel32.spec 2004-02-01 14:27:38.000000000 +0100
@@ -1154,7 +1154,6 @@
################################################################
# Wine dll separation hacks, these will go away, don't use them
#
-@ cdecl DOSFS_GetDeviceByHandle(long)
@ cdecl DOSMEM_AllocSelector(long)
@ cdecl DOSMEM_Available()
@ cdecl DOSMEM_FreeBlock(ptr)
diff -u -N -r -x '*~' -x '.#*' -x CVS dlls/ntdll42/cdrom.c dlls/ntdll/cdrom.c
--- dlls/ntdll42/cdrom.c 2004-01-23 22:21:08.000000000 +0100
+++ dlls/ntdll/cdrom.c 2004-02-02 22:01:27.000000000 +0100
@@ -2,7 +2,7 @@
/* Main file for CD-ROM support
*
* Copyright 1994 Martin Ayotte
- * Copyright 1999, 2001,2003 Eric Pouech
+ * Copyright 1999, 2001, 2003 Eric Pouech
* Copyright 2000 Andreas Mohr
*
* This library is free software; you can redistribute it and/or
@@ -83,6 +83,9 @@
#include "ntddstor.h"
#include "ntddcdrm.h"
#include "ntddscsi.h"
+#include "ntdll_misc.h"
+#include "wine/server.h"
+#include "wine/library.h"
#include "wine/debug.h"
/* Non-Linux systems do not have linux/cdrom.h and the like, and thus
@@ -182,13 +185,20 @@
* for toc inquiries.
*/
struct cdrom_cache {
- int fd;
- int count;
- char toc_good; /* if false, will reread TOC from disk */
- CDROM_TOC toc;
+ int fd;
+ HANDLE hDevice;
+ dev_t device;
+ ino_t inode;
+ int count;
+ char toc_good; /* if false, will reread TOC from disk */
+ CDROM_TOC toc;
SUB_Q_CURRENT_POSITION CurrentPosition;
- const char *device;
};
+/* who has more than 5 cdroms on his/her machine ?? */
+/* FIXME: this should grow depending on the number of cdroms we install/configure
+ * at startup
+ */
+#define MAX_CACHE_ENTRIES 5
static struct cdrom_cache cdrom_cache[26];
/* Proposed media change function: not really needed at this time */
@@ -201,7 +211,7 @@
struct cdrom_tochdr hdr;
struct cdrom_tocentry entry;
- if (dev < 0 || dev >= 26)
+ if (dev < 0 || dev >= MAX_CACHE_ENTRIES)
return 0;
if ( ioctl(cdrom_cache[dev].fd, CDROMREADTOCHDR, &hdr) == -1 )
return 0;
@@ -365,71 +375,70 @@
static int CDROM_GetInterfaceInfo(int fd, int* port, int* iface, int* device,int* lun)
{
#if defined(linux)
+ struct stat st;
+ if ( fstat(fd, &st) == -1 || ! S_ISBLK(st.st_mode))
{
- struct stat st;
- if ( fstat(fd, &st) == -1 || ! S_ISBLK(st.st_mode)) {
- FIXME("cdrom not a block device!!!\n");
- return 0;
- }
- *port = 0;
- *iface = 0;
- *device = 0;
- *lun = 0;
- switch (major(st.st_rdev)) {
- case IDE0_MAJOR: *iface = 0; break;
- case IDE1_MAJOR: *iface = 1; break;
- case IDE2_MAJOR: *iface = 2; break;
- case IDE3_MAJOR: *iface = 3; break;
- case IDE4_MAJOR: *iface = 4; break;
- case IDE5_MAJOR: *iface = 5; break;
- case IDE6_MAJOR: *iface = 6; break;
- case IDE7_MAJOR: *iface = 7; break;
- default: *port = 1; break;
- }
+ FIXME("cdrom not a block device!!!\n");
+ return 0;
+ }
+ *port = 0;
+ *iface = 0;
+ *device = 0;
+ *lun = 0;
+ switch (major(st.st_rdev)) {
+ case IDE0_MAJOR: *iface = 0; break;
+ case IDE1_MAJOR: *iface = 1; break;
+ case IDE2_MAJOR: *iface = 2; break;
+ case IDE3_MAJOR: *iface = 3; break;
+ case IDE4_MAJOR: *iface = 4; break;
+ case IDE5_MAJOR: *iface = 5; break;
+ case IDE6_MAJOR: *iface = 6; break;
+ case IDE7_MAJOR: *iface = 7; break;
+ default: *port = 1; break;
+ }
- if (*port == 0)
- *device = (minor(st.st_rdev) >> 6);
+ if (*port == 0)
+ *device = (minor(st.st_rdev) >> 6);
+ else
+ {
+#ifdef SCSI_IOCTL_GET_IDLUN
+ UINT32 idlun[2];
+ if (ioctl(fd, SCSI_IOCTL_GET_IDLUN, &idlun) != -1)
+ {
+ *port = ((idlun[0] >> 24) & 0xff) + 1;
+ *iface = (idlun[0] >> 16) & 0xff;
+ *device = idlun[0] & 0xff;
+ *lun = (idlun[0] >> 8) & 0xff;
+ }
else
+#endif
{
-#ifdef SCSI_IOCTL_GET_IDLUN
- UINT32 idlun[2];
- if (ioctl(fd, SCSI_IOCTL_GET_IDLUN, &idlun) != -1)
- {
- *port = ((idlun[0] >> 24) & 0xff) + 1;
- *iface = (idlun[0] >> 16) & 0xff;
- *device = idlun[0] & 0xff;
- *lun = (idlun[0] >> 8) & 0xff;
- }
- else
-#endif
- {
- FIXME("CD-ROM device (%d, %d) not supported\n",
- major(st.st_rdev), minor(st.st_rdev));
- return 0;
- }
+ FIXME("CD-ROM device (%d, %d) not supported\n",
+ major(st.st_rdev), minor(st.st_rdev));
+ return 0;
}
- return 1;
}
+ return 1;
#elif defined(__NetBSD__)
+ struct scsi_addr addr;
+ if (ioctl(fd, SCIOCIDENTIFY, &addr) != -1)
{
- struct scsi_addr addr;
- if (ioctl(fd, SCIOCIDENTIFY, &addr) != -1) {
- switch (addr.type) {
- case TYPE_SCSI: *port = 1;
- *iface = addr.addr.scsi.scbus;
- *device = addr.addr.scsi.target;
- *lun = addr.addr.scsi.lun;
- break;
- case TYPE_ATAPI: *port = 0;
- *iface = addr.addr.atapi.atbus;
- *device = addr.addr.atapi.drive;
- *lun = 0;
- break;
- }
- return 1;
- }
- return 0;
+ switch (addr.type)
+ {
+ case TYPE_SCSI: *port = 1;
+ *iface = addr.addr.scsi.scbus;
+ *device = addr.addr.scsi.target;
+ *lun = addr.addr.scsi.lun;
+ break;
+ case TYPE_ATAPI: *port = 0;
+ *iface = addr.addr.atapi.atbus;
+ *device = addr.addr.atapi.drive;
+ *lun = 0;
+ break;
+ }
+ return 1;
}
+ return 0;
#elif defined(__FreeBSD__)
FIXME("not implemented for BSD\n");
return 0;
@@ -449,7 +458,7 @@
* NOTE: programs usually read these registry entries after sending the
* IOCTL_SCSI_GET_ADDRESS ioctl to the cdrom
*/
-void CDROM_InitRegistry(int fd, int device_id, const char *device )
+void CDROM_InitRegistry(int fd)
{
int portnum, busid, targetid, lun;
OBJECT_ATTRIBUTES attr;
@@ -465,8 +474,6 @@
HKEY targetKey;
DWORD disp;
- cdrom_cache[device_id].device = device;
-
attr.Length = sizeof(attr);
attr.RootDirectory = 0;
attr.ObjectName = &nameW;
@@ -474,7 +481,7 @@
attr.SecurityDescriptor = NULL;
attr.SecurityQualityOfService = NULL;
- if ( ! CDROM_GetInterfaceInfo(fd, &portnum, &busid, &targetid, &lun))
+ if (!CDROM_GetInterfaceInfo(fd, &portnum, &busid, &targetid, &lun))
return;
/* Ensure there is Scsi key */
@@ -583,25 +590,39 @@
* CDROM_Open
*
*/
-static NTSTATUS CDROM_Open(HANDLE hDevice, DWORD clientID, int* dev)
+static NTSTATUS CDROM_Open(HANDLE hDevice, int* dev)
{
- *dev = LOWORD(clientID);
-
- if (*dev >= 26) return STATUS_NO_SUCH_DEVICE;
-
+ int fd;
+ struct stat st;
+ int empty = -1;
+
+ wine_server_handle_to_fd(hDevice, GENERIC_READ, &fd, NULL, NULL);
+ if (fd == -1 || fstat(fd, &st) == -1) return STATUS_NO_SUCH_DEVICE;
+
+ for (*dev = 0; *dev < MAX_CACHE_ENTRIES; (*dev)++)
+ {
+ if (empty == -1 &&
+ cdrom_cache[*dev].device == 0 &&
+ cdrom_cache[*dev].inode == 0)
+ empty = *dev;
+ else if (cdrom_cache[*dev].device == st.st_dev &&
+ cdrom_cache[*dev].inode == st.st_ino)
+ break;
+ }
+ if (*dev == MAX_CACHE_ENTRIES)
+ {
+ if (empty == -1) return STATUS_NOT_IMPLEMENTED;
+ *dev = empty;
+ }
if (!cdrom_cache[*dev].count)
{
- const char *device;
-
- if (!(device = cdrom_cache[*dev].device)) return STATUS_NO_SUCH_DEVICE;
- cdrom_cache[*dev].fd = open(device, O_RDONLY|O_NONBLOCK);
- if (cdrom_cache[*dev].fd == -1)
- {
- FIXME("Can't open configured CD-ROM drive %c: (device %s): %s\n",
- 'A' + *dev, device, strerror(errno));
- return STATUS_NO_SUCH_DEVICE;
- }
+ cdrom_cache[*dev].fd = fd;
+ cdrom_cache[*dev].hDevice = hDevice;
+ cdrom_cache[*dev].device = st.st_dev;
+ cdrom_cache[*dev].inode = st.st_ino;
}
+ else
+ wine_server_release_fd(hDevice, fd);
cdrom_cache[*dev].count++;
TRACE("%d, %d, %d\n", *dev, cdrom_cache[*dev].fd, cdrom_cache[*dev].count);
return STATUS_SUCCESS;
@@ -612,15 +633,15 @@
*
*
*/
-static void CDROM_Close(DWORD clientID)
+static void CDROM_Close(int dev)
{
- int dev = LOWORD(clientID);
-
- if (dev >= 26 /*|| fd != cdrom_cache[dev].fd*/) FIXME("how come\n");
if (--cdrom_cache[dev].count == 0)
{
- close(cdrom_cache[dev].fd);
- cdrom_cache[dev].fd = -1;
+ wine_server_release_fd(cdrom_cache[dev].hDevice, cdrom_cache[dev].fd);
+ cdrom_cache[dev].fd = -1;
+ cdrom_cache[dev].hDevice = 0;
+ cdrom_cache[dev].device = 0;
+ cdrom_cache[dev].inode = 0;
}
}
@@ -752,13 +773,11 @@
{
NTSTATUS ret = STATUS_NOT_SUPPORTED;
- if (dev < 0 || dev >= 26)
- return STATUS_INVALID_PARAMETER;
- if ( !cdrom_cache[dev].toc_good ) {
- ret = CDROM_SyncCache(dev);
- if ( ret )
- return ret;
- }
+ if (dev < 0 || dev >= MAX_CACHE_ENTRIES)
+ return STATUS_INVALID_PARAMETER;
+ if ( !cdrom_cache[dev].toc_good && (ret = CDROM_SyncCache(dev)))
+ return ret;
+
*toc = cdrom_cache[dev].toc;
return STATUS_SUCCESS;
}
@@ -1686,7 +1705,7 @@
*
*
*/
-NTSTATUS CDROM_DeviceIoControl(DWORD clientID, HANDLE hDevice,
+NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
@@ -1698,13 +1717,13 @@
NTSTATUS status = STATUS_SUCCESS;
int dev;
- TRACE("%lx[%c] %s %lx %ld %lx %ld %p\n",
- (DWORD)hDevice, 'A' + LOWORD(clientID), iocodex(dwIoControlCode), (DWORD)lpInBuffer, nInBufferSize,
+ TRACE("%lx %s %lx %ld %lx %ld %p\n",
+ (DWORD)hDevice, iocodex(dwIoControlCode), (DWORD)lpInBuffer, nInBufferSize,
(DWORD)lpOutBuffer, nOutBufferSize, piosb);
piosb->Information = 0;
- if ((status = CDROM_Open(hDevice, clientID, &dev))) goto error;
+ if ((status = CDROM_Open(hDevice, &dev))) goto error;
switch (dwIoControlCode)
{
@@ -1893,7 +1912,7 @@
status = STATUS_INVALID_PARAMETER;
break;
}
- CDROM_Close(clientID);
+ CDROM_Close(dev);
error:
piosb->u.Status = status;
piosb->Information = sz;
diff -u -N -r -x '*~' -x '.#*' -x CVS dlls/ntdll42/file.c dlls/ntdll/file.c
--- dlls/ntdll42/file.c 2004-01-23 22:21:08.000000000 +0100
+++ dlls/ntdll/file.c 2004-01-23 22:24:09.000000000 +0100
@@ -665,24 +665,12 @@
PVOID OutputBuffer,
ULONG OutputBufferSize)
{
- DWORD clientID = 0;
-
TRACE("(%p,%p,%p,%p,%p,0x%08lx,%p,0x%08lx,%p,0x%08lx)\n",
DeviceHandle, hEvent, UserApcRoutine, UserApcContext,
IoStatusBlock, IoControlCode,
InputBuffer, InputBufferSize, OutputBuffer, OutputBufferSize);
- /* FIXME: clientID hack should disappear */
- SERVER_START_REQ( get_device_id )
- {
- req->handle = DeviceHandle;
- if (!wine_server_call( req )) clientID = reply->id;
- }
- SERVER_END_REQ;
-
- if (!clientID) return STATUS_INVALID_PARAMETER;
-
- if (CDROM_DeviceIoControl(clientID, DeviceHandle, hEvent,
+ if (CDROM_DeviceIoControl(DeviceHandle, hEvent,
UserApcRoutine, UserApcContext,
IoStatusBlock, IoControlCode,
InputBuffer, InputBufferSize,
diff -u -N -r -x '*~' -x '.#*' -x CVS dlls/ntdll42/ntdll_misc.h dlls/ntdll/ntdll_misc.h
--- dlls/ntdll42/ntdll_misc.h 2004-01-23 22:21:08.000000000 +0100
+++ dlls/ntdll/ntdll_misc.h 2004-01-23 22:24:09.000000000 +0100
@@ -89,7 +89,7 @@
/* Device IO */
/* ntdll/cdrom.c.c */
-extern NTSTATUS CDROM_DeviceIoControl(DWORD clientID, HANDLE hDevice,
+extern NTSTATUS CDROM_DeviceIoControl(HANDLE hDevice,
HANDLE hEvent, PIO_APC_ROUTINE UserApcRoutine,
PVOID UserApcContext,
PIO_STATUS_BLOCK piosb,
diff -u -N -r -x '*~' -x '.#*' -x CVS dlls/ntdll42/ntdll.spec dlls/ntdll/ntdll.spec
--- dlls/ntdll42/ntdll.spec 2004-01-23 22:21:08.000000000 +0100
+++ dlls/ntdll/ntdll.spec 2004-01-23 22:24:09.000000000 +0100
@@ -1084,7 +1084,7 @@
################################################################
# Wine dll separation hacks, these will go away, don't use them
#
-@ cdecl CDROM_InitRegistry(long long str)
+@ cdecl CDROM_InitRegistry(long)
@ cdecl MODULE_DllThreadAttach(ptr)
@ cdecl MODULE_GetLoadOrderW(ptr wstr wstr)
@ cdecl VERSION_Init(wstr)
diff -u -N -r -x '*~' -x '.#*' -x CVS files42/directory.c files/directory.c
--- files42/directory.c 2004-01-01 09:53:52.000000000 +0100
+++ files/directory.c 2004-01-18 21:20:00.000000000 +0100
@@ -531,7 +531,7 @@
TRACE_(file)("(%s,%p)\n", debugstr_w(path), lpsecattribs );
- if (DOSFS_GetDevice( path ))
+ if (RtlIsDosDeviceName_U( path ))
{
TRACE_(file)("cannot use device %s!\n", debugstr_w(path));
SetLastError( ERROR_ACCESS_DENIED );
@@ -630,7 +630,7 @@
TRACE_(file)("%s\n", debugstr_w(path));
- if (DOSFS_GetDevice( path ))
+ if (RtlIsDosDeviceName_U( path ))
{
TRACE_(file)("cannot remove device %s!\n", debugstr_w(path));
SetLastError( ERROR_FILE_NOT_FOUND );
diff -u -N -r -x '*~' -x '.#*' -x CVS files42/dos_fs.c files/dos_fs.c
--- files42/dos_fs.c 2004-01-23 22:21:09.000000000 +0100
+++ files/dos_fs.c 2004-01-23 22:24:19.000000000 +0100
@@ -94,39 +94,6 @@
/* Chars we don't want to see in DOS file names */
#define INVALID_DOS_CHARS "*?<>|\"+=,;[] \345"
-static const DOS_DEVICE DOSFS_Devices[] =
-/* name, device flags (see Int 21/AX=0x4400) */
-{
- { {'C','O','N',0}, 0xc0d3 },
- { {'P','R','N',0}, 0xa0c0 },
- { {'N','U','L',0}, 0x80c4 },
- { {'A','U','X',0}, 0x80c0 },
- { {'L','P','T','1',0}, 0xa0c0 },
- { {'L','P','T','2',0}, 0xa0c0 },
- { {'L','P','T','3',0}, 0xa0c0 },
- { {'L','P','T','4',0}, 0xc0d3 },
- { {'C','O','M','1',0}, 0x80c0 },
- { {'C','O','M','2',0}, 0x80c0 },
- { {'C','O','M','3',0}, 0x80c0 },
- { {'C','O','M','4',0}, 0x80c0 },
- { {'S','C','S','I','M','G','R','$',0}, 0xc0c0 },
- { {'H','P','S','C','A','N',0}, 0xc0c0 },
- { {'E','M','M','X','X','X','X','0',0}, 0x0000 }
-};
-
-static const WCHAR devW[] = {'\\','D','e','v','i','c','e','\\',0};
-static const WCHAR dosW[] = {'\\','D','o','s','D','e','v','i','c','e','s','\\',0};
-
-static const WCHAR auxW[] = {'A','U','X',0};
-static const WCHAR comW[] = {'C','O','M',0};
-static const WCHAR lptW[] = {'L','P','T',0};
-static const WCHAR nulW[] = {'N','U','L',0};
-
-static const WCHAR nullW[] = {'N','u','l','l',0};
-static const WCHAR parW[] = {'P','a','r','a','l','l','e','l',0};
-static const WCHAR serW[] = {'S','e','r','i','a','l',0};
-static const WCHAR oneW[] = {'1',0};
-
/*
* Directory info for DOSFS_ReadDir
* contains the names of *all* the files in the directory
@@ -805,189 +772,6 @@
/***********************************************************************
- * DOSFS_GetDevice
- *
- * Check if a DOS file name represents a DOS device and return the device.
- */
-const DOS_DEVICE *DOSFS_GetDevice( LPCWSTR name )
-{
- unsigned int i;
- const WCHAR *p;
-
- if (!name) return NULL; /* if wine_server_handle_to_fd was used */
- if (name[0] && (name[1] == ':')) name += 2;
- if ((p = strrchrW( name, '/' ))) name = p + 1;
- if ((p = strrchrW( name, '\\' ))) name = p + 1;
- for (i = 0; i < sizeof(DOSFS_Devices)/sizeof(DOSFS_Devices[0]); i++)
- {
- const WCHAR *dev = DOSFS_Devices[i].name;
- if (!strncmpiW( dev, name, strlenW(dev) ))
- {
- p = name + strlenW( dev );
- if (!*p || (*p == '.') || (*p == ':')) return &DOSFS_Devices[i];
- }
- }
- return NULL;
-}
-
-
-/***********************************************************************
- * DOSFS_GetDeviceByHandle
- */
-const DOS_DEVICE *DOSFS_GetDeviceByHandle( HANDLE hFile )
-{
- const DOS_DEVICE *ret = NULL;
- SERVER_START_REQ( get_device_id )
- {
- req->handle = hFile;
- if (!wine_server_call( req ))
- {
- if ((reply->id >= 0) &&
- (reply->id < sizeof(DOSFS_Devices)/sizeof(DOSFS_Devices[0])))
- ret = &DOSFS_Devices[reply->id];
- }
- }
- SERVER_END_REQ;
- return ret;
-}
-
-
-/**************************************************************************
- * DOSFS_CreateCommPort
- */
-static HANDLE DOSFS_CreateCommPort(LPCWSTR name, DWORD access, DWORD attributes, LPSECURITY_ATTRIBUTES sa)
-{
- HANDLE ret;
- HKEY hkey;
- DWORD dummy;
- OBJECT_ATTRIBUTES attr;
- UNICODE_STRING nameW;
- WCHAR *devnameW;
- char tmp[128];
- char devname[40];
-
- static const WCHAR serialportsW[] = {'M','a','c','h','i','n','e','\\',
- 'S','o','f','t','w','a','r','e','\\',
- 'W','i','n','e','\\','W','i','n','e','\\',
- 'C','o','n','f','i','g','\\',
- 'S','e','r','i','a','l','P','o','r','t','s',0};
-
- TRACE_(file)("%s %lx %lx\n", debugstr_w(name), access, attributes);
-
- attr.Length = sizeof(attr);
- attr.RootDirectory = 0;
- attr.ObjectName = &nameW;
- attr.Attributes = 0;
- attr.SecurityDescriptor = NULL;
- attr.SecurityQualityOfService = NULL;
- RtlInitUnicodeString( &nameW, serialportsW );
-
- if (NtOpenKey( &hkey, KEY_ALL_ACCESS, &attr )) return 0;
-
- RtlInitUnicodeString( &nameW, name );
- if (!NtQueryValueKey( hkey, &nameW, KeyValuePartialInformation, tmp, sizeof(tmp), &dummy ))
- devnameW = (WCHAR *)((KEY_VALUE_PARTIAL_INFORMATION *)tmp)->Data;
- else
- devnameW = NULL;
-
- NtClose( hkey );
-
- if (!devnameW) return 0;
- WideCharToMultiByte(CP_ACP, 0, devnameW, -1, devname, sizeof(devname), NULL, NULL);
-
- TRACE("opening %s as %s\n", devname, debugstr_w(name));
-
- SERVER_START_REQ( create_serial )
- {
- req->access = access;
- req->inherit = (sa && (sa->nLength>=sizeof(*sa)) && sa->bInheritHandle);
- req->attributes = attributes;
- req->sharing = FILE_SHARE_READ|FILE_SHARE_WRITE;
- wine_server_add_data( req, devname, strlen(devname) );
- SetLastError(0);
- wine_server_call_err( req );
- ret = reply->handle;
- }
- SERVER_END_REQ;
-
- if(!ret)
- ERR("Couldn't open device '%s' ! (check permissions)\n",devname);
- else
- TRACE("return %p\n", ret );
- return ret;
-}
-
-/***********************************************************************
- * DOSFS_OpenDevice
- *
- * Open a DOS device. This might not map 1:1 into the UNIX device concept.
- * Returns 0 on failure.
- */
-HANDLE DOSFS_OpenDevice( LPCWSTR name, DWORD access, DWORD attributes, LPSECURITY_ATTRIBUTES sa )
-{
- unsigned int i;
- const WCHAR *p;
- HANDLE handle;
-
- if (name[0] && (name[1] == ':')) name += 2;
- if ((p = strrchrW( name, '/' ))) name = p + 1;
- if ((p = strrchrW( name, '\\' ))) name = p + 1;
- for (i = 0; i < sizeof(DOSFS_Devices)/sizeof(DOSFS_Devices[0]); i++)
- {
- const WCHAR *dev = DOSFS_Devices[i].name;
- if (!strncmpiW( dev, name, strlenW(dev) ))
- {
- p = name + strlenW( dev );
- if (!*p || (*p == '.') || (*p == ':')) {
- static const WCHAR nulW[] = {'N','U','L',0};
- static const WCHAR conW[] = {'C','O','N',0};
- static const WCHAR scsimgrW[] = {'S','C','S','I','M','G','R','$',0};
- static const WCHAR hpscanW[] = {'H','P','S','C','A','N',0};
- static const WCHAR emmxxxx0W[] = {'E','M','M','X','X','X','X','0',0};
- /* got it */
- if (!strcmpiW(DOSFS_Devices[i].name, nulW))
- return FILE_CreateFile( "/dev/null", access,
- FILE_SHARE_READ|FILE_SHARE_WRITE, sa,
- OPEN_EXISTING, 0, 0, TRUE, DRIVE_UNKNOWN );
- if (!strcmpiW(DOSFS_Devices[i].name, conW)) {
- HANDLE to_dup;
- switch (access & (GENERIC_READ|GENERIC_WRITE)) {
- case GENERIC_READ:
- to_dup = GetStdHandle( STD_INPUT_HANDLE );
- break;
- case GENERIC_WRITE:
- to_dup = GetStdHandle( STD_OUTPUT_HANDLE );
- break;
- default:
- FIXME("can't open CON read/write\n");
- return 0;
- }
- if (!DuplicateHandle( GetCurrentProcess(), to_dup, GetCurrentProcess(),
- &handle, 0,
- sa && (sa->nLength>=sizeof(*sa)) && sa->bInheritHandle,
- DUPLICATE_SAME_ACCESS ))
- handle = 0;
- return handle;
- }
- if (!strcmpiW(DOSFS_Devices[i].name, scsimgrW) ||
- !strcmpiW(DOSFS_Devices[i].name, hpscanW) ||
- !strcmpiW(DOSFS_Devices[i].name, emmxxxx0W))
- {
- return FILE_CreateDevice( i, access, sa );
- }
-
- if( (handle=DOSFS_CreateCommPort(DOSFS_Devices[i].name,access,attributes,sa)) )
- return handle;
- FIXME("device open %s not supported (yet)\n", debugstr_w(DOSFS_Devices[i].name));
- return 0;
- }
- }
- }
- return 0;
-}
-
-
-/***********************************************************************
* DOSFS_GetPathDrive
*
* Get the drive specified by a given path name (DOS or Unix format).
diff -u -N -r -x '*~' -x '.#*' -x CVS files42/drive.c files/drive.c
--- files42/drive.c 2004-01-23 22:21:09.000000000 +0100
+++ files/drive.c 2004-01-23 22:24:19.000000000 +0100
@@ -141,7 +141,7 @@
#define IS_OPTION_TRUE(ch) ((ch) == 'y' || (ch) == 'Y' || (ch) == 't' || (ch) == 'T' || (ch) == '1')
-extern void CDROM_InitRegistry(int dev, int id, const char *device);
+extern void CDROM_InitRegistry(int dev);
/***********************************************************************
* DRIVE_GetDriveType
@@ -334,7 +334,7 @@
int cd_fd;
if ((cd_fd = open(drive->device, O_RDONLY|O_NONBLOCK)) != -1)
{
- CDROM_InitRegistry(cd_fd, i, drive->device);
+ CDROM_InitRegistry(cd_fd);
close(cd_fd);
}
}
@@ -1210,7 +1210,6 @@
return 1;
}
-
/***********************************************************************
* DRIVE_GetType
*/
diff -u -N -r -x '*~' -x '.#*' -x CVS files42/file.c files/file.c
--- files42/file.c 2004-01-23 22:21:09.000000000 +0100
+++ files/file.c 2004-01-23 22:24:19.000000000 +0100
@@ -264,28 +264,6 @@
}
-/***********************************************************************
- * FILE_CreateDevice
- *
- * Same as FILE_CreateFile but for a device
- * Returns 0 on failure.
- */
-HANDLE FILE_CreateDevice( int client_id, DWORD access, LPSECURITY_ATTRIBUTES sa )
-{
- HANDLE ret;
- SERVER_START_REQ( create_device )
- {
- req->access = access;
- req->inherit = (sa && (sa->nLength>=sizeof(*sa)) && sa->bInheritHandle);
- req->id = client_id;
- SetLastError(0);
- wine_server_call_err( req );
- ret = reply->handle;
- }
- SERVER_END_REQ;
- return ret;
-}
-
static HANDLE FILE_OpenPipe(LPCWSTR name, DWORD access, LPSECURITY_ATTRIBUTES sa )
{
HANDLE ret;
@@ -390,18 +368,7 @@
ret = FILE_OpenPipe( filename, access, sa );
goto done;
}
- else if (isalphaW(filename[4]) && filename[5] == ':' && filename[6] == '\0')
- {
- ret = FILE_CreateDevice( (toupperW(filename[4]) - 'A') | 0x20000, access, sa );
- goto done;
- }
- else if (!DOSFS_GetDevice( filename ))
- {
- ret = DEVICE_Open( filename+4, access, sa );
- goto done;
- }
- else
- filename+=4; /* fall into DOSFS_Device case below */
+ filename += 4;
}
/* If the name still starts with '\\', it's a UNC name. */
@@ -425,15 +392,48 @@
goto done;
}
- if (DOSFS_GetDevice( filename ))
+ if ((isalphaW(filename[0]) && filename[1] == ':' && !filename[2]) ||
+ RtlIsDosDeviceName_U( filename ))
{
+ char buffer[MAX_PATH];
+ char tmp[MAX_PATH], *ptr;
+ LPWSTR p;
TRACE("opening device %s\n", debugstr_w(filename) );
- if (!(ret = DOSFS_OpenDevice( filename, access, attributes, sa )))
+ if (isalphaW(filename[0]) && (filename[1] == ':') && filename[2]) filename += 2;
+ if ((p = strrchrW( filename, '/' ))) filename = p + 1;
+ if ((p = strrchrW( filename, '\\' ))) filename = p + 1;
+
+ WideCharToMultiByte(CP_UNIXCP, 0, filename, -1, tmp, sizeof(tmp), NULL, NULL);
+ for (ptr = tmp; *ptr; ptr++) *ptr = tolower(*ptr);
+
+ sprintf(buffer, "%s/device/%s/device", wine_get_config_dir(), tmp);
+ if (tmp[0] == 'c' && tmp[1] == 'o' && tmp[2] == 'm' && isdigit(tmp[3]) &&
+ !tmp[4])
{
- /* Do not silence this please. It is a critical error. -MM */
- ERR("Couldn't open device %s!\n", debugstr_w(filename));
- SetLastError( ERROR_FILE_NOT_FOUND );
+ SERVER_START_REQ( create_serial )
+ {
+ req->access = access;
+ req->inherit = (sa && (sa->nLength>=sizeof(*sa)) && sa->bInheritHandle);
+ req->attributes = attributes;
+ req->sharing = FILE_SHARE_READ|FILE_SHARE_WRITE;
+ wine_server_add_data( req, buffer, strlen(buffer) );
+ SetLastError(0);
+ wine_server_call_err( req );
+ ret = reply->handle;
+ }
+ SERVER_END_REQ;
+
+ if (!ret)
+ ERR("Couldn't open device '%s' ! (check permissions)\n", buffer);
+ else
+ TRACE("return %p\n", ret );
+ }
+ else
+ {
+ ret = FILE_CreateFile( buffer, access, sharing,
+ sa, creation, attributes, template,
+ FALSE, DRIVE_UNKNOWN );
}
goto done;
}
@@ -1407,7 +1407,7 @@
SetLastError(ERROR_PATH_NOT_FOUND);
return FALSE;
}
- if (DOSFS_GetDevice( path ))
+ if (RtlIsDosDeviceName_U( path ))
{
WARN("cannot remove DOS device %s!\n", debugstr_w(path));
SetLastError( ERROR_FILE_NOT_FOUND );
diff -u -N -r -x '*~' -x '.#*' -x CVS include42/file.h include/file.h
--- include42/file.h 2004-01-01 09:54:11.000000000 +0100
+++ include/file.h 2004-01-18 22:29:49.000000000 +0100
@@ -45,14 +45,6 @@
#define IS_END_OF_NAME(ch) (!(ch) || ((ch) == '/') || ((ch) == '\\'))
-/* DOS device descriptor */
-typedef struct
-{
- const WCHAR name[9];
- int flags;
- UINT codepage;
-} DOS_DEVICE;
-
/* locale-independent case conversion */
inline static char FILE_tolower( char c )
{
@@ -71,12 +63,10 @@
extern int FILE_strncasecmp( const char *str1, const char *str2, int len );
extern void FILE_SetDosError(void);
extern BOOL FILE_Stat( LPCSTR unixName, BY_HANDLE_FILE_INFORMATION *info, BOOL *is_symlink );
-extern HFILE16 FILE_Dup2( HFILE16 hFile1, HFILE16 hFile2 );
extern HANDLE FILE_CreateFile( LPCSTR filename, DWORD access, DWORD sharing,
LPSECURITY_ATTRIBUTES sa, DWORD creation,
DWORD attributes, HANDLE template, BOOL fail_read_only,
UINT drive_type );
-extern HANDLE FILE_CreateDevice( int client_id, DWORD access, LPSECURITY_ATTRIBUTES sa );
extern LONG WINAPI WIN16_hread(HFILE16,SEGPTR,LONG);
@@ -89,15 +79,9 @@
/* files/dos_fs.c */
extern BOOL DOSFS_ToDosFCBFormat( LPCWSTR name, LPWSTR buffer );
-extern const DOS_DEVICE *DOSFS_GetDevice( LPCWSTR name );
-extern const DOS_DEVICE *DOSFS_GetDeviceByHandle( HANDLE hFile );
-extern HANDLE DOSFS_OpenDevice( LPCWSTR name, DWORD access, DWORD attributes, LPSECURITY_ATTRIBUTES sa);
extern BOOL DOSFS_FindUnixName( const DOS_FULL_NAME *path, LPCWSTR name, char *long_buf,
INT long_len, LPWSTR short_buf, BOOL ignore_case );
extern BOOL DOSFS_GetFullName( LPCWSTR name, BOOL check_last,
DOS_FULL_NAME *full );
-/* win32/device.c */
-extern HANDLE DEVICE_Open( LPCWSTR filename, DWORD access, LPSECURITY_ATTRIBUTES sa );
-
#endif /* __WINE_FILE_H */
diff -u -N -r -x '*~' -x '.#*' -x CVS server42/Makefile.in server/Makefile.in
--- server42/Makefile.in 2004-01-01 09:54:22.000000000 +0100
+++ server/Makefile.in 2004-01-18 21:13:52.000000000 +0100
@@ -16,7 +16,6 @@
context_powerpc.c \
context_sparc.c \
debugger.c \
- device.c \
event.c \
fd.c \
file.c \
diff -u -N -r -x '*~' -x '.#*' -x CVS server42/protocol.def server/protocol.def
--- server42/protocol.def 2004-01-14 22:29:59.000000000 +0100
+++ server/protocol.def 2004-01-18 21:11:59.000000000 +0100
@@ -1106,24 +1106,6 @@
@END
-/* Create a device */
- at REQ(create_device)
- unsigned int access; /* wanted access rights */
- int inherit; /* inherit flag */
- int id; /* client private id */
- at REPLY
- obj_handle_t handle; /* handle to the device */
- at END
-
-
-/* Retrieve the client private id for a device */
- at REQ(get_device_id)
- obj_handle_t handle; /* handle to the device */
- at REPLY
- int id; /* client private id */
- at END
-
-
#define SNAP_HEAPLIST 0x00000001
#define SNAP_PROCESS 0x00000002
#define SNAP_THREAD 0x00000004
Index: dlls/winedos/int21.c
===================================================================
RCS file: /home/cvs/cvsroot/wine/wine/dlls/winedos/int21.c,v
retrieving revision 1.52
diff -u -r1.52 int21.c
--- dlls/winedos/int21.c 14 Jan 2004 04:34:22 -0000 1.52
+++ dlls/winedos/int21.c 18 Jan 2004 21:24:47 -0000
@@ -31,6 +31,7 @@
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
+#include <dirent.h>
#include "windef.h"
#include "winbase.h"
@@ -38,12 +39,12 @@
#include "winternl.h"
#include "wine/winbase16.h"
#include "dosexe.h"
-#include "file.h"
#include "winerror.h"
#include "winuser.h"
#include "wine/unicode.h"
#include "wine/debug.h"
#include "wine/exception.h"
+#include "wine/server.h"
/*
* Note:
@@ -245,7 +246,6 @@
#define EL_Serial 0x04
#define EL_Memory 0x05
-
/* Many calls translate a drive argument like this:
drive number (00h = default, 01h = A:, etc)
*/
@@ -2444,19 +2444,45 @@
*/
static void INT21_Ioctl_Char( CONTEXT86 *context )
{
- static const WCHAR emmxxxx0W[] = {'E','M','M','X','X','X','X','0',0};
- static const WCHAR scsimgrW[] = {'S','C','S','I','M','G','R','$',0};
-
- HANDLE handle = DosFileHandleToWin32Handle(BX_reg(context));
- const DOS_DEVICE *dev = DOSFS_GetDeviceByHandle(handle);
-
- if (dev && !strcmpiW( dev->name, emmxxxx0W ))
+ HANDLE handle;
+ struct stat st_ref, st;
+ int fd;
+ char p[MAX_PATH], *l;
+ DIR* dir;
+ struct dirent* de = NULL;
+
+ handle = DosFileHandleToWin32Handle(BX_reg(context));
+ if (wine_server_handle_to_fd(handle, GENERIC_READ, &fd, NULL, NULL))
+
+ if (fstat(fd, &st_ref) != -1)
+ {
+ sprintf(p, "%s/dosdevices/", wine_get_config_dir());
+ l = p + strlen(p);
+ dir = opendir(p);
+ if (dir)
+ {
+ while ((de = readdir(dir)))
+ {
+ strcpy(l, de->d_name);
+ if (stat(p, &st) != -1 && st.st_dev == st_ref.st_dev &&
+ st.st_ino == st_ref.st_ino)
+ {
+ strcpy(p, de->d_name);
+ break;
+ }
+ }
+ closedir(dir);
+ }
+ }
+ close(fd);
+
+ if (de && !strcasecmp( p, "EMMXXXX0"))
{
EMS_Ioctl_Handler(context);
return;
}
- if (dev && !strcmpiW( dev->name, scsimgrW ) && AL_reg(context) == 2)
+ if (de && !strcasecmp( p, "SCSIMGR$" ) && AL_reg(context) == 2)
{
DOSVM_ASPIHandler(context);
return;
@@ -2466,8 +2492,26 @@
{
case 0x00: /* GET DEVICE INFORMATION */
TRACE( "IOCTL - GET DEVICE INFORMATION - %d\n", BX_reg(context) );
- if (dev)
+ if (de)
{
+ static struct {const char* name; unsigned flags;} dos_dev[] = {
+ { "CON", 0xc0d3 },
+ { "PRN", 0xa0c0 },
+ { "NUL", 0x80c4 },
+ { "AUX", 0x80c0 },
+ { "LPT1", 0xa0c0 },
+ { "LPT2", 0xa0c0 },
+ { "LPT3", 0xa0c0 },
+ { "LPT4", 0xc0d3 },
+ { "COM1", 0x80c0 },
+ { "COM2", 0x80c0 },
+ { "COM3", 0x80c0 },
+ { "COM4", 0x80c0 },
+ { "SCSIMGR$", 0xc0c0 },
+ { "HPSCAN", 0xc0c0 },
+ { "EMMXXXX0", 0x0000 }
+ };
+ int i;
/*
* Returns attribute word in DX:
* Bit 14 - Device driver can process IOCTL requests.
@@ -2483,7 +2527,10 @@
* Bit 1 - Standard output.
* Bit 0 - Standard input.
*/
- SET_DX( context, dev->flags );
+ for (i = sizeof(dos_dev) / sizeof(dos_dev[0]) - 1; i >= 0; i--)
+ if (!strcmp(p, dos_dev[i].name))
+ SET_DX( context, dos_dev[i].flags );
+ if (i < 0) SET_DX( context, 0 );
}
else
{
@@ -3439,7 +3486,7 @@
* is something behind this ?
*/
while (*p == '*' || *p == ' ') p++; /* skip wildcards and spaces */
- return IS_END_OF_NAME(*p);
+ return *p == '\0' || *p == '/' || *p == '\\';
}
static HANDLE INT21_FindHandle;
More information about the wine-patches
mailing list