home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 10 Tools
/
10-Tools.zip
/
cdrom.zip
/
DDK
/
BASE
/
SRC
/
VDEV
/
VCDROM
/
vcdrom.c
< prev
next >
Wrap
C/C++ Source or Header
|
1996-06-18
|
19KB
|
568 lines
/***************************************************************************
*
* SOURCE FILE NAME = VCDROM.C
*
* DESCRIPTIVE NAME = VCDROM Initializations
*
* DESCRIPTION This module contains all the VCDROM's initialization
* procedures, event handler procedures, and global
* as well as VDM instance data declarations.
*
* Copyright : COPYRIGHT IBM CORPORATION, 1991, 1992
* Copyright Microsoft Corporation, 1990
* LICENSED MATERIAL - PROGRAM PROPERTY OF IBM
* REFER TO COPYRIGHT INSTRUCTION FORM#G120-2083
* RESTRICTED MATERIALS OF IBM
* IBM CONFIDENTIAL
*
* ENTRY POINTS:
* VDDInit
* VCDROMCreateVDM
* InstallStub
* VCDROMTerminateVDM
* VCDROMPDBDestroy
* CloseHandles
*
* EXTERNAL REFERENCES:
*
* CHANGE ACTIVITY =
* DATE FLAG APAR CHANGE DESCRIPTION
* -------- ---------- ----- --------------------------------------
* mm/dd/yy @Vr.mpppxx xxxxx xxxxxxx
* 08/16/91 @V2.0DTF Created.
*
* 09/25/92 @V2.0FJS00 Changed installstub to installinthook on int
* 0x2f instead of int 0x66. Also patch dos stub
* device driver with VCDROMDosLink address for
* ARPL. Define and initialize current HVDM
* instance storage.
*
* 10/21/92 @V2.0FJS01 Changed VCDROMCreateVDM to obtain VPIC slave
* routine address and to query the INT_DURING_IO
* DOS property. MSCDEX absolute sector read
* (used by Sherlock Holmes) blocks in the device
* driver preventing simulated hardware interrupts
* (like sound) in a DOS session.
*
* 12/05/92 @V2.0FJS02 Changed installstub to copy the number of
* units to the stub DOS device driver header.
* Some DOS applications look for the number of
* units there.
*
* 03/24/93 @V2.0FJS03 Added VCDROMPDBDestroy routine to close drive
* handles when the application terminates. This
* usually indicates the CD-ROM disc is being
* changed.
*
****************************************************************************/
#include <mvdm.h>
#include <propname.h>
#include "vcdromp.h"
#include "reqhdr.h"
#include "ctrlblk.h"
#include "cdstub.h"
#ifdef VDDSTRICT
MODNAME = __FILE__;
#endif
/*
** VCDROM Global Data
*/
#pragma BEGIN_GLOBAL_DATA
#ifdef VDDSTRICT
CHAR szAssertMsg[] = "VCDROM assertion failure in %s, line %d\n";
#endif
#ifdef VDDDEBUG
CHAR szModule[] = "VCDROM: ";
#endif
BOOL flSLAVE;
SZ szRealTime = PROP_NAME_INT_DURING_IO;
SZ szVPICName = "VPIC";
HVDD hvddVPIC=NULL;
PFN pfnSlaveRequest=NULL;
#pragma END_GLOBAL_DATA
#pragma BEGIN_SWAP_DATA
#pragma END_SWAP_DATA
/*
** VCDROM Instance Data
*/
#pragma BEGIN_SWAP_INSTANCE
HVDM hvdmCurrent=0; /* instance copy of HVDM */
ULONG slaveparms [10]; /* VDHFSCtl parms to pass to slave thread */
struct /* OS/2 generic ioctl code and category */
CategoryCode
IoctlOutputCodes [] = {
0x44, 0x80, /* eject disk */
0x46, 0x80, /* lock/unlock */
0x40, 0x80, /* reset */
0x40, 0x81, /* audio channel control */
0x4F, 0x80, /* write drive bytes */
0x45, 0x80 /* close tray */
};
struct /* OS/2 generic ioctl code and category */
CategoryCode
IoctlInputCodes [] = {
0xFF, 0x80, /* undefined */
0x70, 0x80, /* location of head */
0xFF, 0x80, /* undefined */
0xFF, 0x80, /* undefined */
0x60, 0x81, /* audio channel info */
0x6F, 0x80, /* read drive bytes */
0x60, 0x80, /* device status */
0x63, 0x80, /* return sector size */
0x78, 0x80, /* return volume size */
0x00, 0x80, /* ** MEDIA CHANGED exception ** */
0x61, 0x81, /* audio disk info */
0x62, 0x81, /* audio track info */
0x63, 0x81, /* q channel info */
0x64, 0x81, /* sub channel info */
0x79, 0x80, /* UPC code */
0x65, 0x81 /* audio status info */
};
USHORT NumberOfDrives = 0;
USHORT FirstDriveNumber = 0;
VPDOSDDTYPE DosDDHeader; /* V86FAR address of dos driver */
HFILE
DriveHandle [MAX_NUMBER_OF_DRIVES]; /* DASD open drive handles */
UCHAR
CdromCharDriverName[] = CDROM_CHAR_DRIVER_NAME;
UCHAR
DriveString [] = "A:\0B:\0C:\0D:\0E:\0F:\0G:\0H:\0I:\0J:\0K:\0L:\0M:\0"
"N:\0O:\0P:\0Q:\0R:\0S:\0T:\0U:\0V:\0W:\0X:\0Y:\0Z:\0";
ULONG DataArea[4]; /* for the VDHDevIOCtl call */
ULONG ParmList[20]; /* for VDHDevIOCtl/VDHFSCtl calls*/
ULONG DataLengthInOut; /* these are just dummies for */
ULONG ParmLengthInOut; /* the VDHDevIOCtl call */
ULONG ActionTaken; /* for VDHOpen */
HFILE FileHandle; /* for VDHOpen */
#pragma END_SWAP_INSTANCE
/*
** VCDROM Initialization Data
*/
#pragma BEGIN_INIT_DATA
#pragma END_INIT_DATA
#pragma BEGIN_GLOBAL_CODE
#pragma END_GLOBAL_CODE
/*
** VCDROM Initialization Code
*/
#pragma BEGIN_INIT_CODE
/****************************************************************************
*
* FUNCTION NAME = VDDInit
*
* DESCRIPTION = Virtual CDROM Initialization Entry Point
*
* VCDROM initialization routine
* See VDD Manager for complete semantics.
*
* This dynamically exported subroutine is called during
* system initialization.
*
* CONTEXT:
* Init-time
*
* PSEUDOCODE:
* define user event hook (VCDROMCreateVDM)
* define user event hook (VCDROMTerminateVDM)
* define user event hook (VCDROMPDBDestroy)
*
* INPUT = psz - pointer to configuration strings (not used) NONE
*
* OUTPUT =
*
* RETURN-NORMAL = return TRUE
*
* RETURN-ERROR = return FALSE
*
****************************************************************************/
BOOL EXPENTRY VDDInit ( PSZ psz )
{
/*---------------------------------------------------------------*/
/*- Register a VDM Creation handler entry point. -*/
/*---------------------------------------------------------------*/
if ((VDHInstallUserHook((ULONG)VDM_CREATE,
(PUSERHOOK)VCDROMCreateVDM)) == 0)
return FALSE; /* return FALSE if VDH call failed */
/*---------------------------------------------------------------*/
/*- Register a VDM Termination handler entry point. -*/
/*---------------------------------------------------------------*/
if ((VDHInstallUserHook((ULONG)VDM_TERMINATE,
(PUSERHOOK)VCDROMTerminateVDM)) == 0)
return FALSE; /* return FALSE if VDH call failed */
/*---------------------------------------------------------------*/
/*- Register a VDM PDB destruction handler entry point. -*/
/*---------------------------------------------------------------*/
if ((VDHInstallUserHook((ULONG)VDM_PDB_DESTROY,
(PUSERHOOK)VCDROMPDBDestroy)) == 0)
return FALSE; /* return FALSE if VDH call failed */
return TRUE; /* successful installation */
}
#pragma END_INIT_CODE
#pragma BEGIN_SWAP_CODE
/****************************************************************************
*
* FUNCTION NAME = VCDROMCreateVDM
*
* DESCRIPTION = VDM creation notification
* See VDHInstallUserHook for complete semantics.
*
* This registered subroutine is called each time a new VDM
* is created. Note that not a lot of initialization should be
* needed (ie, static initialization for most of the instance
* data suffices).
*
* CONTEXT:
* VDM Task-time
*
* PSEUDOCODE:
* Get the drive letter information from the physical driver.
* Install the DOS stub driver.
* request VPIC slave thread routine for MSCDEX absolute disc
* reads. Set flSLAVE flag if INT_DURING_IO property set.
*
* INPUT = hvdm - handle of VDM
*
* OUTPUT =
*
* RETURN-NORMAL = return TRUE
*
* RETURN-ERROR = return FALSE
*
****************************************************************************/
BOOL HOOKENTRY VCDROMCreateVDM (HVDM hvdm)
{
register
ULONG rc;
hvdmCurrent = hvdm;
/* INT_3; */
rc = VDHOpen ( CdromCharDriverName,
&FileHandle,
&ActionTaken,
FILESIZE,
FILEATTRIBUTE,
OPENFLAG,
CHAROPENMODE,
EABUF );
if ( rc == VDH_FAILURE )
{
rc = VDHGetError (); /* For debugging and to clear it. */
return TRUE; /* Do not fail install because */
} /* the VDM will crash, but do */
/* not register anything. */
ParmLengthInOut = PARM_LENGTH_MAX; /* these are just dummies for */
DataLengthInOut = DATA_LENGTH_MAX; /* the VDHDevIOCtl call */
rc = VDHDevIOCtl ( FileHandle,
0x0082,
0x0060, /* return drive letter information*/
ParmList,
PARM_LENGTH_MAX,
&ParmLengthInOut,
DataArea,
DATA_LENGTH_MAX,
&DataLengthInOut );
if ( rc == VDH_FAILURE )
{
rc = VDHGetError ();
}
else
{
rc = FALSE;
}
if ( rc )
{
VDHClose ( FileHandle );
return FALSE; /* do not install */
}
VDHClose ( FileHandle );
NumberOfDrives = (USHORT) *DataArea;
FirstDriveNumber = * ( (PUSHORT) DataArea + 1 );
if ( ! InstallStub () )
return FALSE;
/*
** if INT_DURING_IO DOS property set, and have VPIC slave routine
** then set the flSLAVE flag for dual thread operations.
*/
if(VDHQueryProperty(szRealTime))
{
if(hvddVPIC==NULL)
hvddVPIC = VDHOpenVDD(szVPICName);
if((hvddVPIC!=NULL)&&(pfnSlaveRequest==NULL))
VDHRequestVDD(hvddVPIC,
0,
VPIC_SLAVE_ADDRESS,
NULL,
(PVOID)&pfnSlaveRequest);
if(pfnSlaveRequest!=NULL)
flSLAVE = TRUE;
}
return TRUE;
}
/****************************************************************************
*
* FUNCTION NAME = InstallStub
*
* DESCRIPTION = install our DOS Device Driver
*
* The DOS Device Driver stub serves three purposes:
*
* To let DOS applications know that CDROM and MSCDEX are
* installed. Most apps call int 2f to determine this, some
* will search for the device driver name.
*
* To trap int 2fh (ah=15h) calls and relay them to this
* driver.
*
* To route cdrom device driver requests to this code.
*
* GLOBAL EFFECTS:
* Memory is allocated from DOS to hold our device driver
*
* PSEUDOCODE:
* Get some VDM memory for our device driver.
* Copy the driver into VDM space.
* Copy the number of units into the device driver header.
* Install the driver as a DOS device driver.
* Save the DOS drivers address.
* If the installation failed, erase the driver name
* (so that applications that try to identify the
* existence of the CDROM driver by hunting through
* the device driver list will not find a
* half-installed CDROM driver).
*
* INPUT = NONE
*
* OUTPUT =
*
* RETURN-NORMAL = returns TRUE
*
* RETURN-ERROR = returns FALSE
*
****************************************************************************/
BOOL PRIVENTRY InstallStub (VOID)
{
register
PBYTE dosDDstart; /* where the Dos Device Driver will go */
VPVOID vpBP; /* breakpoint address for ARPL */
HHOOK hBPHook; /* hook handle */
if ( ! ( dosDDstart = VDHAllocDosMem (CDROMStubLength) ) )
return FALSE;
memcpy ( dosDDstart, CDROMStubStart, CDROMStubLength );
*(dosDDstart + CDROMNumUnits) = (UCHAR) NumberOfDrives; /* patch dd header*/
/* set arpl to VCDROMDosLink */
hBPHook = VDHAllocHook (VDH_BP_HOOK,(PFNARM) VCDROMDosLink, 0);
if (hBPHook == NULL)
return FALSE;
vpBP = VDHArmBPHook (hBPHook); /* get arpl address */
*(PDWORD)(dosDDstart + CDROMPatch0) = (DWORD) vpBP; /* patch device driver*/
DosDDHeader = (VPDOSDDTYPE) VPFROMP(dosDDstart);
if ( ! VDHSetDosDevice ( (VPDOSDDTYPE) VPFROMP(dosDDstart) ))
{
*(PDWORD) (dosDDstart + CDROMDevName) = 0; /* kill the device name */
return FALSE;
}
return TRUE;
}
/****************************************************************************
*
* FUNCTION NAME = VCDROMTerminateVDM
*
* DESCRIPTION = VDM Destruction
*
* VDM destruction notification
* See VDHInstallUserHook for complete semantics.
*
* This registered subroutine is called each time a VDM
* is destroyed. This handler deallocates the per VDM
* resources used by the VDM being destroyed.
*
* CONTEXT:
* VDM Task-time
*
* PSEUDOCODE:
* Close any open drive handles
*
* INPUT = hvdm - handle of VDM
*
* OUTPUT = return TRUE
*
* RETURN-NORMAL =
* RETURN-ERROR =
*
****************************************************************************/
BOOL HOOKENTRY VCDROMTerminateVDM (HVDM hvdm)
{
CloseHandles();
return TRUE;
}
/****************************************************************************
*
* FUNCTION NAME = VCDROMPDBDestroy
*
* DESCRIPTION = VDM PDB destruction notification
* See VDHInstallUserHook for complete semantics.
*
* This registered subroutine is called each time a VDM PDB
* is destroyed. This handler causes the per VDM drive handles
* to be closed.
*
* When an application terminates, the PDB is destroyed. This
* also means (probably) that the CD-ROM disc is being changed.
* The open drive handles need to be closed. When a new drive
* request occurs, vcdrom will open the drive and mount the new
* disc (or remount the old disc if no disc change occurred).
*
* CONTEXT:
* VDM Task-time
*
* PSEUDOCODE:
* Close any open drive handles
*
* INPUT = hvdm - handle of VDM
* vpdb - V86 segment of terminating DOS Program Data Block
*
* OUTPUT = TRUE
*
* RETURN-NORMAL =
* RETURN-ERROR =
*
****************************************************************************/
BOOL HOOKENTRY VCDROMPDBDestroy(HVDM hvdm, USHORT vPDB)
{
CloseHandles();
return TRUE;
}
/****************************************************************************
*
* FUNCTION NAME = CloseHandles
*
* DESCRIPTION = Close any open per-VDM drive handles
*
* This routine is called to close any open per-VDM drive
* handles. This routine searches through the DriveHandle array
* for any non NULL drive handles. If one is found, VDHClose
* is called to close the handle and NULL is stored in the
* DriveHandle array.
*
* CONTEXT:
* VDM Task-time
*
* PSEUDOCODE:
* Close any open drive handles
*
* INPUT = None
*
* OUTPUT = None
*
* RETURN-NORMAL =
* RETURN-ERROR =
*
****************************************************************************/
VOID PRIVENTRY CloseHandles (VOID)
{
register
ULONG n;
register
ULONG last_drive;
register
HFILE handle;
last_drive = FirstDriveNumber + NumberOfDrives;
for ( n = FirstDriveNumber; n < last_drive; ++n ) {
handle = DriveHandle [n];
if ( handle != NULL ) {
VDHClose ( handle );
DriveHandle [n] = NULL;
}
}
return;
}
#pragma END_SWAP_CODE