diff --git a/src/dos/Makefile.am b/src/dos/Makefile.am index 4d206c7b..0beeb4aa 100644 --- a/src/dos/Makefile.am +++ b/src/dos/Makefile.am @@ -6,4 +6,5 @@ libdos_a_SOURCES = dos.cpp dos_devices.cpp dos_execute.cpp dos_files.cpp dos_ioc dos_misc.cpp dos_classes.cpp dos_programs.cpp dos_tables.cpp \ drives.cpp drives.h drive_virtual.cpp drive_local.cpp drive_cache.cpp drive_fat.cpp \ drive_iso.cpp dev_con.h dos_mscdex.cpp \ - cdrom.h cdrom.cpp cdrom_ioctl_win32.cpp cdrom_aspi_win32.cpp cdrom_ioctl_linux.cpp cdrom_image.cpp + cdrom.h cdrom.cpp cdrom_ioctl_win32.cpp cdrom_aspi_win32.cpp cdrom_ioctl_linux.cpp cdrom_image.cpp \ + cdrom_ioctl_os2.cpp diff --git a/src/dos/cdrom.h b/src/dos/cdrom.h index 173a9c24..705f8429 100644 --- a/src/dos/cdrom.h +++ b/src/dos/cdrom.h @@ -296,7 +296,7 @@ private: #endif /* WIN 32 */ -#if defined (LINUX) +#if defined (LINUX) || defined(OS2) class CDROM_Interface_Ioctl : public CDROM_Interface_SDL { diff --git a/src/dos/cdrom_ioctl_os2.cpp b/src/dos/cdrom_ioctl_os2.cpp new file mode 100644 index 00000000..7374d8f0 --- /dev/null +++ b/src/dos/cdrom_ioctl_os2.cpp @@ -0,0 +1,153 @@ +/* + * Copyright (C) 2002-2005 The DOSBox Team + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + */ + +/* $Id: cdrom_ioctl_os2.cpp,v 1.1 2005-11-25 19:15:12 qbix79 Exp $ */ + +#include +#include "dosbox.h" +#include "cdrom.h" + +#if defined (OS2) +#define INCL_DOSFILEMGR +#define INCL_DOSERRORS +#define INCL_DOSDEVICES +#define INCL_DOSDEVIOCTL +#include "os2.h" + +// Ripped from linux/cdrom.h +#define CD_FRAMESIZE_RAW 2352 +#define CD_FRAMESIZE 2048 + +CDROM_Interface_Ioctl::CDROM_Interface_Ioctl(void) : CDROM_Interface_SDL(){ + strcpy(device_name, ""); +} + +bool CDROM_Interface_Ioctl::GetUPC(unsigned char& attr, char* upc){ + HFILE cdrom_fd = 0; + ULONG ulAction = 0; + APIRET rc = DosOpen((unsigned char*)device_name, &cdrom_fd, &ulAction, 0L, FILE_NORMAL, OPEN_ACTION_OPEN_IF_EXISTS, + OPEN_FLAGS_DASD | OPEN_SHARE_DENYNONE | OPEN_ACCESS_READONLY, 0L); + if (rc != NO_ERROR) { + return false; + } + char data[50]; + ULONG len = sizeof(data); + char sig[] = {'C', 'D', '0', '1'}; + ULONG sigsize = 4; + rc = DosDevIOCtl(cdrom_fd, IOCTL_CDROMDISK, CDROMDISK_GETUPC, sig, sigsize, &sigsize, + data, len, &len); + if (rc != NO_ERROR) { + return false; + } + rc = DosClose(cdrom_fd); + return rc == NO_ERROR; +} + +bool CDROM_Interface_Ioctl::ReadSectors(PhysPt buffer, bool raw, unsigned long sector, unsigned long num){ + HFILE cdrom_fd = 0; + ULONG ulAction = 0; + APIRET rc = DosOpen((unsigned char*)device_name, &cdrom_fd, &ulAction, 0L, FILE_NORMAL, OPEN_ACTION_OPEN_IF_EXISTS, + OPEN_FLAGS_DASD | OPEN_SHARE_DENYNONE | OPEN_ACCESS_READONLY, 0L); + if (rc != NO_ERROR) { + return false; + } + + Bitu buflen = raw ? num * CD_FRAMESIZE_RAW : num * CD_FRAMESIZE; + Bit8u* buf = new Bit8u[buflen]; + int ret = NO_ERROR; + + if (raw) { + struct paramseek { + UCHAR sig[4]; + UCHAR mode; + ULONG sec; + + paramseek(ULONG sector) + { + sig[0] = 'C'; sig[1] = 'D'; sig[2] = '0'; sig[3] = '1'; + sec = sector; + } + } param_seek(sector); + ULONG paramsize = sizeof (paramseek); + rc = DosDevIOCtl(cdrom_fd, IOCTL_CDROMDISK, CDROMDISK_SEEK, ¶m_seek, paramsize, ¶msize, + 0, 0, 0); + if (rc != NO_ERROR) { + return false; + } + + struct paramread { + UCHAR sig[4]; + UCHAR mode; + USHORT number; + BYTE sec; + BYTE reserved; + BYTE interleave; + + paramread(USHORT num) + { + sig[0] = 'C'; sig[1] = 'D'; sig[2] = '0'; sig[3] = '1'; + mode = 0; number = num; + sec = interleave = 0; + } + } param_read(num); + paramsize = sizeof (paramread); + ULONG len = buflen; + rc = DosDevIOCtl(cdrom_fd, IOCTL_CDROMDISK, CDROMDISK_READLONG, ¶m_read, paramsize, ¶msize, + buf, len, &len); + if (rc != NO_ERROR) { + return false; + } + } else { + ULONG pos = 0; + rc = DosSetFilePtr(cdrom_fd, sector * CD_FRAMESIZE, FILE_BEGIN, &pos); + if (rc != NO_ERROR) { + return false; + } + ULONG read = 0; + rc = DosRead(cdrom_fd, buf, buflen, &read); + if (rc != NO_ERROR || read != buflen) { + return false; + } + } + rc = DosClose(cdrom_fd); + MEM_BlockWrite(buffer, buf, buflen); + delete[] buf; + + return (ret == NO_ERROR); +} + +bool CDROM_Interface_Ioctl::SetDevice(char* path, int forceCD) { + bool success = CDROM_Interface_SDL::SetDevice(path, forceCD); + + if (success) { + char temp[3] = {0, 0, 0}; + if (path[1] == ':') { + temp[0] = path[0]; + temp[1] = path[1]; + temp[2] = 0; + } + strncpy(device_name, temp, 512); + } else { + strcpy(device_name, ""); + success = false; + } + + return success; +} + +#endif diff --git a/src/dos/dos_mscdex.cpp b/src/dos/dos_mscdex.cpp index c0871f96..088cc5a1 100644 --- a/src/dos/dos_mscdex.cpp +++ b/src/dos/dos_mscdex.cpp @@ -16,7 +16,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ -/* $Id: dos_mscdex.cpp,v 1.32 2005-09-28 11:21:50 qbix79 Exp $ */ +/* $Id: dos_mscdex.cpp,v 1.33 2005-11-25 19:15:12 qbix79 Exp $ */ #include #include @@ -264,8 +264,8 @@ int CMscdex::AddDrive(Bit16u _drive, char* physicalPath, Bit8u& subUnit) break; } #endif - #if defined (LINUX) - // Always use IOCTL in Linux + #if defined (LINUX) || defined(OS2) + // Always use IOCTL in Linux or OS/2 // if (useCdromInterface==CDROM_USE_IOCTL) { cdrom[numDrives] = new CDROM_Interface_Ioctl(); LOG(LOG_MISC,LOG_NORMAL)("MSCDEX: IOCTL Interface.");