winedos / Migrate most ioctl routines to winedos
Jukka Heinonen
jhei at iki.fi
Sun May 25 09:23:52 CDT 2003
Changelog:
Migrate most int21 ioctl routines to winedos.
Migrate int21 set drive routine to winedos.
Index: include/drive.h
===================================================================
RCS file: /home/wine/wine/include/drive.h,v
retrieving revision 1.10
diff -u -r1.10 drive.h
--- include/drive.h 27 Aug 2002 01:13:59 -0000 1.10
+++ include/drive.h 25 May 2003 14:14:57 -0000
@@ -54,8 +54,6 @@
extern int DRIVE_Enable( int drive );
extern int DRIVE_SetLogicalMapping ( int existing_drive, int new_drive );
extern int DRIVE_OpenDevice( int drive, int flags );
-extern int DRIVE_RawRead(BYTE drive, DWORD begin, DWORD length, BYTE *dataptr, BOOL fake_success );
-extern int DRIVE_RawWrite(BYTE drive, DWORD begin, DWORD length, BYTE *dataptr, BOOL fake_success );
extern char *DRIVE_BuildEnv(void);
#endif /* __WINE_DRIVE_H */
Index: files/drive.c
===================================================================
RCS file: /home/wine/wine/files/drive.c,v
retrieving revision 1.89
diff -u -r1.89 drive.c
--- files/drive.c 19 Apr 2003 02:48:34 -0000 1.89
+++ files/drive.c 25 May 2003 14:15:02 -0000
@@ -1295,61 +1295,6 @@
/***********************************************************************
- * DRIVE_RawRead
- *
- * Read raw sectors from a device
- */
-int DRIVE_RawRead(BYTE drive, DWORD begin, DWORD nr_sect, BYTE *dataptr, BOOL fake_success)
-{
- int fd;
-
- if ((fd = DRIVE_OpenDevice( drive, O_RDONLY )) != -1)
- {
- lseek( fd, begin * 512, SEEK_SET );
- /* FIXME: check errors */
- read( fd, dataptr, nr_sect * 512 );
- close( fd );
- }
- else
- {
- memset(dataptr, 0, nr_sect * 512);
- if (fake_success)
- {
- if (begin == 0 && nr_sect > 1) *(dataptr + 512) = 0xf8;
- if (begin == 1) *dataptr = 0xf8;
- }
- else
- return 0;
- }
- return 1;
-}
-
-
-/***********************************************************************
- * DRIVE_RawWrite
- *
- * Write raw sectors to a device
- */
-int DRIVE_RawWrite(BYTE drive, DWORD begin, DWORD nr_sect, BYTE *dataptr, BOOL fake_success)
-{
- int fd;
-
- if ((fd = DRIVE_OpenDevice( drive, O_RDONLY )) != -1)
- {
- lseek( fd, begin * 512, SEEK_SET );
- /* FIXME: check errors */
- write( fd, dataptr, nr_sect * 512 );
- close( fd );
- }
- else
- if (!(fake_success))
- return 0;
-
- return 1;
-}
-
-
-/***********************************************************************
* DRIVE_GetFreeSpace
*/
static int DRIVE_GetFreeSpace( int drive, PULARGE_INTEGER size,
Index: msdos/int21.c
===================================================================
RCS file: /home/wine/wine/msdos/int21.c,v
retrieving revision 1.93
diff -u -r1.93 int21.c
--- msdos/int21.c 19 May 2003 21:40:05 -0000 1.93
+++ msdos/int21.c 25 May 2003 14:15:11 -0000
@@ -275,35 +275,6 @@
}
-static void ioctlGetDeviceInfo( CONTEXT86 *context )
-{
- int curr_drive;
- const DOS_DEVICE *dev;
-
- TRACE("(%d)\n", BX_reg(context));
-
- RESET_CFLAG(context);
-
- /* DOS device ? */
- if ((dev = DOSFS_GetDeviceByHandle( DosFileHandleToWin32Handle(BX_reg(context)) )))
- {
- SET_DX( context, dev->flags );
- return;
- }
-
- /* it seems to be a file */
- curr_drive = DRIVE_GetCurrentDrive();
- SET_DX( context, 0x0140 + curr_drive + ((curr_drive > 1) ? 0x0800 : 0) );
- /* no floppy */
- /* bits 0-5 are current drive
- * bit 6 - file has NOT been written..FIXME: correct?
- * bit 8 - generate int24 if no diskspace on write/ read past end of file
- * bit 11 - media not removable
- * bit 14 - don't set file date/time on closing
- * bit 15 - file is remote
- */
-}
-
static BOOL ioctlGenericBlkDevReq( CONTEXT86 *context )
{
BYTE *dataptr = CTX_SEG_OFF_TO_LIN(context, context->SegDs, context->Edx);
@@ -323,10 +294,6 @@
switch (CL_reg(context))
{
- case 0x4a: /* lock logical volume */
- TRACE("lock logical volume (%d) level %d mode %d\n",drive,BH_reg(context),DX_reg(context));
- break;
-
case 0x60: /* get device parameters */
/* used by w4wgrp's winfile */
memset(dataptr, 0, 0x20); /* DOS 6.22 uses 0x20 bytes */
@@ -348,30 +315,6 @@
RESET_CFLAG(context);
break;
- case 0x41: /* write logical device track */
- case 0x61: /* read logical device track */
- {
- BYTE drive = BL_reg(context) ?
- BL_reg(context) : DRIVE_GetCurrentDrive();
- WORD head = *(WORD *)dataptr+1;
- WORD cyl = *(WORD *)dataptr+3;
- WORD sect = *(WORD *)dataptr+5;
- WORD nrsect = *(WORD *)dataptr+7;
- BYTE *data = (BYTE *)dataptr+9;
- int (*raw_func)(BYTE, DWORD, DWORD, BYTE *, BOOL);
-
- raw_func = (CL_reg(context) == 0x41) ?
- DRIVE_RawWrite : DRIVE_RawRead;
-
- if (raw_func(drive, head*cyl*sect, nrsect, data, FALSE))
- RESET_CFLAG(context);
- else
- {
- SET_AX( context, 0x1e ); /* read fault */
- SET_CFLAG(context);
- }
- }
- break;
case 0x66:/* get disk serial number */
{
char label[12],fsname[9],path[4];
@@ -388,10 +331,6 @@
}
break;
- case 0x6a:
- TRACE("logical volume %d unlocked.\n",drive);
- break;
-
case 0x6f:
memset(dataptr+1, '\0', dataptr[0]-1);
dataptr[1] = dataptr[0];
@@ -911,12 +850,6 @@
switch(AH_reg(context))
{
- case 0x0e: /* SELECT DEFAULT DRIVE */
- TRACE("SELECT DEFAULT DRIVE %d\n", DL_reg(context));
- DRIVE_SetCurrentDrive( DL_reg(context) );
- SET_AL( context, MAX_DOS_DRIVES );
- break;
-
case 0x11: /* FIND FIRST MATCHING FILE USING FCB */
TRACE("FIND FIRST MATCHING FILE USING FCB %p\n",
CTX_SEG_OFF_TO_LIN(context, context->SegDs, context->Edx));
@@ -981,82 +914,12 @@
case 0x44: /* IOCTL */
switch (AL_reg(context))
{
- case 0x00:
- ioctlGetDeviceInfo(context);
- break;
-
- case 0x01:
- break;
-
- case 0x05:{ /* IOCTL - WRITE TO BLOCK DEVICE CONTROL CHANNEL */
- /*BYTE *dataptr = CTX_SEG_OFF_TO_LIN(context, context->SegDs,context->Edx);*/
- int drive = DOS_GET_DRIVE(BL_reg(context));
-
- FIXME("program tried to write to block device control channel of drive %d:\n",drive);
- /* for (i=0;i<CX_reg(context);i++)
- fprintf(stdnimp,"%02x ",dataptr[i]);
- fprintf(stdnimp,"\n");*/
- SET_AX( context, context->Ecx );
- break;
- }
- case 0x08: /* Check if drive is removable. */
- TRACE("IOCTL - CHECK IF BLOCK DEVICE REMOVABLE for drive %s\n",
- INT21_DriveName( BL_reg(context)));
- switch(GetDriveType16( DOS_GET_DRIVE( BL_reg(context) )))
- {
- case DRIVE_UNKNOWN:
- SetLastError( ERROR_INVALID_DRIVE );
- SET_AX( context, ERROR_INVALID_DRIVE );
- SET_CFLAG(context);
- break;
- case DRIVE_REMOVABLE:
- SET_AX( context, 0 ); /* removable */
- break;
- default:
- SET_AX( context, 1 ); /* not removable */
- break;
- }
- break;
-
- case 0x09: /* CHECK IF BLOCK DEVICE REMOTE */
- TRACE("IOCTL - CHECK IF BLOCK DEVICE REMOTE for drive %s\n",
- INT21_DriveName( BL_reg(context)));
- switch(GetDriveType16( DOS_GET_DRIVE( BL_reg(context) )))
- {
- case DRIVE_UNKNOWN:
- SetLastError( ERROR_INVALID_DRIVE );
- SET_AX( context, ERROR_INVALID_DRIVE );
- SET_CFLAG(context);
- break;
- case DRIVE_REMOTE:
- SET_DX( context, (1<<9) | (1<<12) ); /* remote */
- break;
- default:
- SET_DX( context, 0 ); /* FIXME: use driver attr here */
- break;
- }
- break;
-
- case 0x0a: /* check if handle (BX) is remote */
- TRACE("IOCTL - CHECK IF HANDLE %d IS REMOTE\n",BX_reg(context));
- /* returns DX, bit 15 set if remote, bit 14 set if date/time
- * not set on close
- */
- SET_DX( context, 0 );
- break;
-
case 0x0d:
TRACE("IOCTL - GENERIC BLOCK DEVICE REQUEST %s\n",
INT21_DriveName( BL_reg(context)));
bSetDOSExtendedError = ioctlGenericBlkDevReq(context);
break;
- case 0x0e: /* get logical drive mapping */
- TRACE("IOCTL - GET LOGICAL DRIVE MAP for drive %s\n",
- INT21_DriveName( BL_reg(context)));
- SET_AL( context, 0 ); /* drive has no mapping - FIXME: may be wrong*/
- break;
-
case 0x0F: /* Set logical drive mapping */
{
int drive;
@@ -1070,10 +933,6 @@
}
break;
}
-
- default:
- INT_BARF( context, 0x21 );
- break;
}
break;
Index: dlls/winedos/int21.c
===================================================================
RCS file: /home/wine/wine/dlls/winedos/int21.c,v
retrieving revision 1.35
diff -u -r1.35 int21.c
--- dlls/winedos/int21.c 20 May 2003 17:49:04 -0000 1.35
+++ dlls/winedos/int21.c 25 May 2003 14:15:16 -0000
@@ -154,6 +154,22 @@
/***********************************************************************
+ * INT21_SetCurrentDrive
+ *
+ * Set current drive. Uses scheme (0=A:, 1=B:, 2=C:, ...).
+ */
+static void INT21_SetCurrentDrive( BYTE drive )
+{
+ WCHAR drivespec[3] = {'A', ':', 0};
+
+ drivespec[0] += drive;
+
+ if (!SetCurrentDirectoryW( drivespec ))
+ TRACE( "Failed to set current drive.\n" );
+}
+
+
+/***********************************************************************
* INT21_ReadChar
*
* Reads a character from the standard input.
@@ -1584,7 +1600,139 @@
*/
static void INT21_Ioctl_Block( CONTEXT86 *context )
{
- INT_Int21Handler( context );
+ BYTE *dataptr;
+ BYTE drive = INT21_MapDrive( BL_reg(context) );
+ WCHAR drivespec[4] = {'A', ':', '\\', 0};
+ UINT drivetype;
+
+ drivespec[0] += drive;
+ drivetype = GetDriveTypeW( drivespec );
+
+ if (drivetype == DRIVE_UNKNOWN || drivetype == DRIVE_NO_ROOT_DIR)
+ {
+ TRACE( "IOCTL - SUBFUNCTION %d - INVALID DRIVE %c:\n",
+ AL_reg(context), 'A' + drive );
+ SetLastError( ERROR_INVALID_DRIVE );
+ SET_AX( context, ERROR_INVALID_DRIVE );
+ SET_CFLAG( context );
+ return;
+ }
+
+ switch (AL_reg(context))
+ {
+ case 0x04: /* READ FROM BLOCK DEVICE CONTROL CHANNEL */
+ case 0x05: /* WRITE TO BLOCK DEVICE CONTROL CHANNEL */
+ INT_BARF( context, 0x21 );
+ break;
+
+ case 0x08: /* CHECK IF BLOCK DEVICE REMOVABLE */
+ TRACE( "IOCTL - CHECK IF BLOCK DEVICE REMOVABLE - %c:\n",
+ 'A' + drive );
+
+ if (drivetype == DRIVE_REMOVABLE)
+ SET_AX( context, 0 ); /* removable */
+ else
+ SET_AX( context, 1 ); /* not removable */
+ break;
+
+ case 0x09: /* CHECK IF BLOCK DEVICE REMOTE */
+ TRACE( "IOCTL - CHECK IF BLOCK DEVICE REMOTE - %c:\n",
+ 'A' + drive );
+
+ if (drivetype == DRIVE_REMOTE)
+ SET_DX( context, (1<<9) | (1<<12) ); /* remote + no direct IO */
+ else
+ SET_DX( context, 0 ); /* FIXME: use driver attr here */
+ break;
+
+ case 0x0d: /* GENERIC BLOCK DEVICE REQUEST */
+ /* Get pointer to IOCTL parameter block. */
+ dataptr = CTX_SEG_OFF_TO_LIN(context, context->SegDs, context->Edx);
+
+ switch (CX_reg(context))
+ {
+ case 0x0841: /* write logical device track */
+ TRACE( "GENERIC IOCTL - Write logical device track - %c:\n",
+ 'A' + drive);
+ {
+ WORD head = *(WORD *)dataptr+1;
+ WORD cyl = *(WORD *)dataptr+3;
+ WORD sect = *(WORD *)dataptr+5;
+ WORD nrsect = *(WORD *)dataptr+7;
+ BYTE *data = (BYTE *)dataptr+9; /* FIXME: is this correct? */
+
+ if (!DOSVM_RawWrite(drive, head*cyl*sect, nrsect, data, FALSE))
+ {
+ SET_AX( context, ERROR_WRITE_FAULT );
+ SET_CFLAG(context);
+ }
+ }
+ break;
+
+ case 0x084a: /* lock logical volume */
+ TRACE( "GENERIC IOCTL - Lock logical volume, level %d mode %d - %c:\n",
+ BH_reg(context), DX_reg(context), 'A' + drive );
+ break;
+
+ case 0x0860: /* get device parameters */
+ INT_Int21Handler( context );
+ break;
+
+ case 0x0861: /* read logical device track */
+ TRACE( "GENERIC IOCTL - Read logical device track - %c:\n",
+ 'A' + drive);
+ {
+ WORD head = *(WORD *)dataptr+1;
+ WORD cyl = *(WORD *)dataptr+3;
+ WORD sect = *(WORD *)dataptr+5;
+ WORD nrsect = *(WORD *)dataptr+7;
+ BYTE *data = (BYTE *)dataptr+9; /* FIXME: is this correct? */
+
+ if (!DOSVM_RawRead(drive, head*cyl*sect, nrsect, data, FALSE))
+ {
+ SET_AX( context, ERROR_READ_FAULT );
+ SET_CFLAG(context);
+ }
+ }
+ break;
+
+ case 0x0866: /* get volume serial number */
+ INT_Int21Handler( context );
+ break;
+
+ case 0x086a: /* unlock logical volume */
+ TRACE( "GENERIC IOCTL - Logical volume unlocked - %c:\n",
+ 'A' + drive );
+ break;
+
+ case 0x086f: /* get drive map information */
+ INT_Int21Handler( context );
+ break;
+
+ case 0x0872:
+ INT_Int21Handler( context );
+ break;
+
+ default:
+ INT_BARF( context, 0x21 );
+ }
+ break;
+
+ case 0x0e: /* GET LOGICAL DRIVE MAP */
+ TRACE( "IOCTL - GET LOGICAL DRIVE MAP - %c:\n",
+ 'A' + drive );
+ /* FIXME: this is not correct if drive has mappings */
+ SET_AL( context, 0 ); /* drive has no mapping */
+ break;
+
+ case 0x0f: /* SET LOGICAL DRIVE MAP */
+ INT_Int21Handler( context );
+ break;
+
+ case 0x11: /* QUERY GENERIC IOCTL CAPABILITY */
+ default:
+ INT_BARF( context, 0x21 );
+ }
}
@@ -1613,7 +1761,74 @@
return;
}
- INT_Int21Handler( context );
+ switch (AL_reg(context))
+ {
+ case 0x00: /* GET DEVICE INFORMATION */
+ TRACE( "IOCTL - GET DEVICE INFORMATION - %d\n", BX_reg(context) );
+ if (dev)
+ {
+ /*
+ * Returns attribute word in DX:
+ * Bit 14 - Device driver can process IOCTL requests.
+ * Bit 13 - Output until busy supported.
+ * Bit 11 - Driver supports OPEN/CLOSE calls.
+ * Bit 8 - Unknown.
+ * Bit 7 - Set (indicates device).
+ * Bit 6 - EOF on input.
+ * Bit 5 - Raw (binary) mode.
+ * Bit 4 - Device is special (uses int29).
+ * Bit 3 - Clock device.
+ * Bit 2 - NUL device.
+ * Bit 1 - Standard output.
+ * Bit 0 - Standard input.
+ */
+ SET_DX( context, dev->flags );
+ }
+ else
+ {
+ /*
+ * Returns attribute word in DX:
+ * Bit 15 - File is remote.
+ * Bit 14 - Don't set file date/time on closing.
+ * Bit 11 - Media not removable.
+ * Bit 8 - Generate int24 if no disk space on write
+ * or read past end of file
+ * Bit 7 - Clear (indicates file).
+ * Bit 6 - File has not been written.
+ * Bit 5..0 - Drive number (0=A:,...)
+ *
+ * FIXME: Should check if file is on remote or removable drive.
+ * FIXME: Should use drive file is located on (and not current).
+ */
+ SET_DX( context, 0x0140 + INT21_GetCurrentDrive() );
+ }
+ break;
+
+ case 0x01: /* SET DEVICE INFORMATION */
+ case 0x02: /* READ FROM CHARACTER DEVICE CONTROL CHANNEL */
+ case 0x03: /* WRITE TO CHARACTER DEVICE CONTROL CHANNEL */
+ case 0x06: /* GET INPUT STATUS */
+ case 0x07: /* GET OUTPUT STATUS */
+ INT_BARF( context, 0x21 );
+ break;
+
+ case 0x0a: /* CHECK IF HANDLE IS REMOTE */
+ TRACE( "IOCTL - CHECK IF HANDLE IS REMOTE - %d\n", BX_reg(context) );
+ /*
+ * Returns attribute word in DX:
+ * Bit 15 - Set if remote.
+ * Bit 14 - Set if date/time not set on close.
+ *
+ * FIXME: Should check if file is on remote drive.
+ */
+ SET_DX( context, 0 );
+ break;
+
+ case 0x0c: /* GENERIC CHARACTER DEVICE REQUEST */
+ case 0x10: /* QUERY GENERIC IOCTL CAPABILITY */
+ default:
+ INT_BARF( context, 0x21 );
+ }
}
@@ -2211,7 +2426,9 @@
break;
case 0x0e: /* SELECT DEFAULT DRIVE */
- INT_Int21Handler( context );
+ TRACE( "SELECT DEFAULT DRIVE - %c:\n", 'A' + DL_reg(context) );
+ INT21_SetCurrentDrive( DL_reg(context) );
+ SET_AL( context, MAX_DOS_DRIVES );
break;
case 0x0f: /* OPEN FILE USING FCB */
--
Jukka Heinonen <http://www.iki.fi/jhei/>
More information about the wine-patches
mailing list