]> Shamusworld >> Repos - virtualjaguar/commitdiff
New OS dependent CDROM code
authorShamus Hammons <jlhamm@acm.org>
Thu, 25 Mar 2004 21:02:40 +0000 (21:02 +0000)
committerShamus Hammons <jlhamm@acm.org>
Thu, 25 Mar 2004 21:02:40 +0000 (21:02 +0000)
src/cdintf.cpp [new file with mode: 0644]
src/cdintf_linux.cpp [new file with mode: 0644]
src/cdintf_osx.cpp [new file with mode: 0644]
src/cdintf_win32.cpp [new file with mode: 0644]
src/include/cdintf.h [new file with mode: 0644]
src/include/scsidefs.h [new file with mode: 0644]
src/include/wnaspi32.h [new file with mode: 0644]

diff --git a/src/cdintf.cpp b/src/cdintf.cpp
new file mode 100644 (file)
index 0000000..4f8924f
--- /dev/null
@@ -0,0 +1,41 @@
+//
+// OS agnostic CDROM interface functions
+//
+// by James L. Hammons
+//
+// This file is basically a shell to keep the front-end clean and also pull in the
+// appropriate back-end code depending on which target is being compiled for.
+//
+
+#include "cdintf.h"                                                                    // Every OS has to implement these
+
+/*#ifdef __GCCWIN32__
+#include "cdintf_win32.cpp"
+#endif
+
+#ifdef __GCCUNIX__
+#ifdef _OSX_
+
+#include "cdintf_osx.cpp"
+
+#else
+#include "cdintf_linux.cpp"
+
+#endif
+#endif//*/
+
+#if defined(__GCCWIN32__)
+
+#include "cdintf_win32.cpp"
+
+#elif defined(__GCCUNIX__)
+#if defined(_OSX_)
+
+#include "cdintf_osx.cpp"
+
+#else
+
+#include "cdintf_linux.cpp"
+
+#endif
+#endif
diff --git a/src/cdintf_linux.cpp b/src/cdintf_linux.cpp
new file mode 100644 (file)
index 0000000..c418df5
--- /dev/null
@@ -0,0 +1,5 @@
+//
+// OS specific CDROM interface (linux)
+//
+// by James L. Hammons
+//
diff --git a/src/cdintf_osx.cpp b/src/cdintf_osx.cpp
new file mode 100644 (file)
index 0000000..1ca290e
--- /dev/null
@@ -0,0 +1,5 @@
+//
+// OS specific CDROM interface (Mac OS X)
+//
+// by ?
+//
diff --git a/src/cdintf_win32.cpp b/src/cdintf_win32.cpp
new file mode 100644 (file)
index 0000000..b075af5
--- /dev/null
@@ -0,0 +1,412 @@
+//
+// OS specific CDROM interface (Win32)
+//
+// by James L. Hammons
+//
+
+// OS dependent CDROM stuffola
+#include <windows.h>
+#include <stdio.h>
+#include "wnaspi32.h"
+#include "scsidefs.h"
+// End OS dependent
+
+#include "log.h"
+
+using namespace std;
+
+// Local variables
+
+DWORD remain = 0, sector = 0;
+BYTE cdBuf[2532 * 10];
+
+// Private function prototypes
+
+
+HINSTANCE WNASPI32_handle = NULL;  //Handle to ASPI for Win32 (WNASPI.DLL)
+//WNASPI.DLL functions
+DWORD (*ASPI_GetASPI32SupportInfo)(VOID);
+DWORD (*ASPI_SendASPI32Command)(LPSRB);
+//BOOL  (*ASPI_GetASPI32Buffer)(PASPI32BUFF);
+//BOOL  (*ASPI_FreeASPI32Buffer)(PASPI32BUFF);
+//BOOL  (*ASPI_TranslateASPI32Address)(PDWORD, PDWORD);
+
+byte DataBuf[2352];  //Buffer for holding data to/from drive
+//************************************************************
+//End of globals
+
+//
+// Load the WNASPI32.DLL and import the required functions, then initialise
+// Win ASPI 32.
+//
+BOOL InitASPI()
+{
+       DWORD dwSupportInfo;
+       SRB_GetSetTimeouts srbTimeouts;
+
+       WNASPI32_handle = LoadLibrary("WNASPI32"); //WNASPI32.DLL
+
+       if (!WNASPI32_handle)
+       {
+               WriteLog("CDINTF: Could not load WNASPI32.DLL\n");
+               return FALSE;
+       };
+
+    /*
+    ** Get the ASPI entry points.  Note that only two functions are mandatory:
+    ** GetASPI32SupportInfo and SendASPI32Command.  The code will run if the
+    ** others are not present.
+    */
+    ASPI_GetASPI32SupportInfo = (DWORD (*)(void))GetProcAddress(WNASPI32_handle, "GetASPI32SupportInfo");
+    ASPI_SendASPI32Command = (DWORD (*)(LPSRB))GetProcAddress(WNASPI32_handle, "SendASPI32Command");
+    //ASPI_GetASPI32Buffer = (BOOL (*)(PASPI32BUFF))GetProcAddress(WNASPI32_handle, "GetASPI32Buffer");
+    //ASPI_FreeASPI32Buffer = (BOOL (*)(PASPI32BUFF))GetProcAddress(WNASPI32_handle, "FreeASPI32Buffer");
+    //ASPI_TranslateASPI32Address = (BOOL (*)(PDWORD, PDWORD))GetProcAddress(WNASPI32_handle, "TranslateASPI32Address");
+
+    //Check if the 2 functions were imported.
+    if(!ASPI_GetASPI32SupportInfo || !ASPI_SendASPI32Command)
+    {
+        WriteLog("Could not import GetASPI32SupportInfo & SendASPI32Command functions from WNASPI32.DLL\n");
+        return FALSE;
+    };
+
+    //Initialise Win ASPI 32 by calling ASPI_GetASPI32SupportInfo().
+    dwSupportInfo = ASPI_GetASPI32SupportInfo();
+    if (HIBYTE(LOWORD(dwSupportInfo)) != SS_COMP && HIBYTE(LOWORD(dwSupportInfo)) != SS_NO_ADAPTERS)
+    {
+        WriteLog("Could not initialise using GetASPI32SupportInfo function or no adapters\n");
+        return FALSE;
+    };
+
+    /*
+    ** Set timeouts for ALL devices to 15 seconds.  Nothing we deal with should
+    ** take that long to do ANYTHING.  We are just doing inquiries to most
+    ** devices, and then simple reads to CDs, disks, etc. so 10 seconds (even
+    ** if they have to spin up) should be plenty. 
+    */
+    memset(&srbTimeouts, 0, sizeof(SRB_GetSetTimeouts));
+    srbTimeouts.SRB_Cmd = SC_GETSET_TIMEOUTS;
+    srbTimeouts.SRB_HaId = 0xFF;
+    srbTimeouts.SRB_Flags = SRB_DIR_OUT;
+    srbTimeouts.SRB_Target = 0xFF;
+    srbTimeouts.SRB_Lun = 0xFF;
+    srbTimeouts.SRB_Timeout = 15 * 2;
+    ASPI_SendASPI32Command(&srbTimeouts);
+
+    return TRUE;
+};
+
+/*
+    Sends a SRB (SCSI Request Block) to Win ASPI32 driver for processing and
+    waits for completion.
+
+    The SRB contains the CDB (Command Descriptor Block) which has the
+    raw SCSI command/info you want to send to the drive.  So effectively
+    this is actually sending the SCSI command to the drive.
+
+    Note that this uses a Windows event to wait for the drive to reply back
+    which is efficient.  If an event is not available (which should never
+    happen really) a loop is used to poll for reply back.
+
+    Both methods will wait infinitely - so the drive must reply back otherwise
+    this software will appear to hang.  There seems to be no mechanism for
+    cancelling the SRB process - the Win ASPI 32 'SC_ABORT_SRB' command doesn't
+    seem to work.
+*/
+BOOL SendASPICMD_and_wait(BYTE HA_ID, BYTE Target_ID, BYTE SRB_flags, DWORD Buffer_len,
+       PBYTE Buffer, BYTE CDB_len, PBYTE CDB)
+{
+    DWORD           dwASPIStatus;
+    HANDLE          hevent_SRB;  //A handle for a new Windows event
+    SRB_ExecSCSICmd SRB;  //The SRB variable with CDB included
+    BOOL b_retry = TRUE;
+
+    //Clear & setup the SRB for this command..
+    memset(&SRB, 0, sizeof(SRB_ExecSCSICmd));  //Set it to zeroes
+    memcpy(SRB.CDBByte, CDB, CDB_len);  //Copy CDB into SRB
+
+    SRB.SRB_Cmd = SC_EXEC_SCSI_CMD;
+    SRB.SRB_HaId = HA_ID;
+    SRB.SRB_Target = Target_ID;
+    //SRB.SRB_Lun = 0;  //It's already zero
+    SRB.SRB_Flags = SRB_flags;
+    SRB.SRB_BufLen = Buffer_len;
+    SRB.SRB_BufPointer = Buffer;
+    SRB.SRB_SenseLen = SENSE_LEN;
+    SRB.SRB_CDBLen = CDB_len;
+
+    do
+    {
+        /*
+        ** Create an event (if possible) and issue the command.  After sending
+        ** the command, wait for completion.
+        */
+        hevent_SRB = CreateEvent(NULL, TRUE, FALSE, NULL);
+        if (hevent_SRB)
+        {
+            //Windows event method for waiting - efficient.
+
+            SRB.SRB_Flags |= SRB_EVENT_NOTIFY;
+            SRB.SRB_PostProc = (LPVOID)hevent_SRB;
+        
+            //Send the SRB for processing.
+            dwASPIStatus = ASPI_SendASPI32Command((LPSRB)&SRB);
+            if (dwASPIStatus == SS_PENDING)
+            {
+                //Wait for reply back.
+                WaitForSingleObject(hevent_SRB, INFINITE);
+            }
+            CloseHandle(hevent_SRB);
+        }
+        else
+        {
+            //Polling method for waiting - not very efficient.
+
+            //Send the SRB for processing.
+            ASPI_SendASPI32Command((LPSRB)&SRB);
+            //Wait for reply back.
+            while(SRB.SRB_Status == SS_PENDING);
+        };
+
+        /*
+        ** Check for errors.  We'll retry on unit attention condition.  Anything
+        ** else will generate an error msg.
+        */
+        if (SRB.SRB_Status != SS_COMP)
+        {
+                       if (b_retry && (SRB.SRB_TargStat != STATUS_CHKCOND
+                               || (SRB.SenseArea[2] & 0x0F) != KEY_UNITATT))
+                b_retry = FALSE;
+            else
+            {
+                WriteLog("SCSI command failed.\n");
+                return FALSE;
+            }
+        }
+    }
+    while (b_retry == FALSE);
+
+    return TRUE;
+};
+
+/*
+    Lists all available CDROM type drives.  This includes:
+        - CDROM drives
+        - CD rewriters/Combo
+        - DVD drives
+        - DVD rewriters
+        etc
+
+    It can only list the SCSI IDs not drive letters.  Win ASPI 32 does
+    not provide a mechanism for this.  You will have to use windows API
+    for this.
+*/
+VOID ListDevices()
+{
+    BYTE          HaId;
+    BYTE          Target;
+    BYTE          MaxHaId;
+    BYTE          MaxTarget;
+    BYTE          InquiryBuf[36];
+    BYTE          InquiryCDB[6];
+    CHAR          szVendor[9];
+    CHAR          szProduct[17];
+    CHAR          szRev[5];
+    BOOL          bSRB_exec;
+    DWORD         dwASPIStatus;
+    DWORD         dwMaxTransferBytes;    
+    SRB_HAInquiry srbHAInquiry;
+    SRB_GDEVBlock srbGDEVBlock;
+    DWORD         n_CDROM_drives=0;  //No of CDROM type drives found.
+
+    //Use support info for host adapter count and loop over all of them.
+    dwASPIStatus = ASPI_GetASPI32SupportInfo();
+    if(HIBYTE(LOWORD(dwASPIStatus)) == SS_COMP)
+    {
+        MaxHaId = LOBYTE(LOWORD(dwASPIStatus));
+        for(HaId = 0; HaId < MaxHaId; HaId++)
+        {
+            /*
+            ** Do a host adapter inquiry to get max target count.  If the 
+            ** target count isn't 8 or 16 then go with a default of 8.
+            */
+            memset(&srbHAInquiry, 0, sizeof(SRB_HAInquiry));
+            srbHAInquiry.SRB_Cmd = SC_HA_INQUIRY;
+            srbHAInquiry.SRB_HaId = HaId;
+
+            ASPI_SendASPI32Command((LPSRB)&srbHAInquiry);
+            if(srbHAInquiry.SRB_Status != SS_COMP)
+            {
+                continue;
+            };
+
+            MaxTarget = srbHAInquiry.HA_Unique[3];
+            if(MaxTarget != 8 && MaxTarget != 16)
+            {
+                MaxTarget = 8;
+            };
+
+            /*
+            ** Loop over all the targets on this host adapter.
+            */
+            for(Target = 0; Target < MaxTarget; Target++ )
+            {
+                /*
+                ** Issue get device type call to see if there is a device we're
+                ** interested in at this address.  We're interested in CDROMs.
+                */
+                memset(&srbGDEVBlock, 0, sizeof(SRB_GDEVBlock));
+                srbGDEVBlock.SRB_Cmd = SC_GET_DEV_TYPE;
+                srbGDEVBlock.SRB_HaId = HaId;
+                srbGDEVBlock.SRB_Target = Target;
+
+                ASPI_SendASPI32Command((LPSRB)&srbGDEVBlock);
+                if(srbGDEVBlock.SRB_Status != SS_COMP ||
+                  (srbGDEVBlock.SRB_DeviceType != DTYPE_CDROM))
+                {                    
+                    continue;
+                };
+
+                /*
+                ** Determine the max transfer count of this target.  It will
+                ** be the min of the host adapters min count and the size
+                ** of our global transfer buffer.
+                */
+                dwMaxTransferBytes = (DWORD)&srbHAInquiry.HA_Unique[4];
+
+                /*
+                ** Issue an INQUIRY.
+                */
+                memset(InquiryCDB, 0, 6);
+                InquiryCDB[0] = SCSI_INQUIRY;
+                InquiryCDB[4] = 36;  //Size in bytes of inquiry buffer.
+
+                //Send SCSI device inquiry command and wait for completion.
+                bSRB_exec = SendASPICMD_and_wait
+                (
+                    HaId,
+                    Target,
+                    SRB_DIR_IN,
+                    36,
+                    InquiryBuf,
+                    6,
+                    InquiryCDB
+                );
+
+                /*
+                ** Make sure the inquiry worked.  If it failed, or if the
+                ** inquiry data returns a different device type than we got
+                ** before (guards against certain device drivers and against
+                ** vendor unique devices).
+                */
+                if(!bSRB_exec || (InquiryBuf[0] != DTYPE_CDROM))
+                    continue;
+
+                /*
+                ** Add this target to the screen.
+                */
+                WriteLog("Host adapter ID: %ld\n", HaId);
+                WriteLog("Target ID      : %ld\n", Target);
+                WriteLog("LUN ID         : 0\n");
+                WriteLog("Max buffer size: %ld bytes\n", dwMaxTransferBytes);
+
+                memcpy(szVendor, InquiryBuf + 8, 8);                
+                szVendor[8] = '\0';  //Terminate the string
+
+                memcpy(szProduct, InquiryBuf + 16, 16);
+                szProduct[16] = '\0';  //Terminate the string
+
+                memcpy(szRev, InquiryBuf + 32, 4);
+                szRev[4] = '\0';  //Terminate the string
+
+                WriteLog("Vendor         : %s\n", szVendor);
+                WriteLog("Product        : %s\n", szProduct);
+                WriteLog("Revision       : %s\n\n", szRev);
+
+                n_CDROM_drives++;
+            }
+        }
+
+        if (n_CDROM_drives == 0)
+            WriteLog("No CDROM type drives found.\n");
+    }
+}
+
+//
+// 1. Sets up the CDB for MMC readcd (CDB12) command.
+// 2. Send the request to the drive.
+// 3. If success displays the sector data as hex on the screen.
+//
+BOOL ReadCD(BYTE HA_ID, BYTE Target_ID, long int MMC_LBA_sector)
+{
+    BYTE read_CDB12[12];
+    long int MMC_LBA_sector2;    
+
+    //CDB with values for ReadCD CDB12 command.  The values were taken from MMC1 draft paper.
+    read_CDB12[0] = 0xBE;  //Code for ReadCD CDB12 command
+    read_CDB12[1] = 0;        
+
+    read_CDB12[5] = byte(MMC_LBA_sector);   //Least sig byte of LBA sector no. to read from CD
+    MMC_LBA_sector2 = MMC_LBA_sector >> 8;
+    read_CDB12[4] = byte(MMC_LBA_sector2);  //2nd byte of:
+    MMC_LBA_sector2 = MMC_LBA_sector2 >> 8;
+    read_CDB12[3] = byte(MMC_LBA_sector2);  //3rd byte of:
+    MMC_LBA_sector2 = MMC_LBA_sector2 >> 8;
+    read_CDB12[2] = byte(MMC_LBA_sector2);  //Most significant byte        
+
+    read_CDB12[6] = 0;  //No. of sectors to read from CD byte 2 (MSB)
+    read_CDB12[7] = 0;  //No. of sectors to read from CD byte 1
+    read_CDB12[8] = 1;  //No. of sectors to read from CD byte 0 (LSB)
+    read_CDB12[9] = 0xF8;  //Raw read, 2352 bytes per sector
+    read_CDB12[10] = 0;  //Sub-channel selection bits.
+    read_CDB12[11] = 0;
+
+       return SendASPICMD_and_wait(HA_ID, Target_ID, SRB_DIR_IN, 2352, DataBuf, 12, read_CDB12);
+}
+
+//
+// Initialize the SDL sound system
+//
+void __CDInit(void)
+{
+       if (!InitASPI())
+       {
+               WriteLog("Sound: Failed to init ASPI layer!\n");
+               exit(1);//bad!
+       }
+}
+
+//
+// Close down the SDL sound subsystem
+//
+void __CDDone(void)
+{
+    //Unload ASPI if it has been loaded.
+       if (WNASPI32_handle)
+               FreeLibrary(WNASPI32_handle);
+}
+
+/*//
+// Sound card callback handler
+//
+void SDLSoundCallback(void * userdata, Uint8 * buffer, int length)
+{
+       if (remain > 0)
+       {
+               memcpy(buffer, DataBuf + 2352 - remain, remain);
+               length -= remain;
+               buffer += remain;
+               remain = 0;
+       }
+
+       while (length > 0)
+       {
+               ReadCD(0, 1, sector++);
+               memcpy(buffer, DataBuf, (length >= 2352 ? 2352 : length));
+               length -= 2352;
+               buffer += 2352;
+       }
+
+       if (length < 0)
+               remain = -length;
+}*/
diff --git a/src/include/cdintf.h b/src/include/cdintf.h
new file mode 100644 (file)
index 0000000..e69de29
diff --git a/src/include/scsidefs.h b/src/include/scsidefs.h
new file mode 100644 (file)
index 0000000..0d782b7
--- /dev/null
@@ -0,0 +1,275 @@
+//***************************************************************************
+//
+// Name:            SCSIDEFS.H
+//
+// Description: SCSI definitions ('C' Language)
+//
+//***************************************************************************
+
+//***************************************************************************
+//                          %%% TARGET STATUS VALUES %%%
+//***************************************************************************
+#define STATUS_GOOD     0x00    // Status Good
+#define STATUS_CHKCOND  0x02    // Check Condition
+#define STATUS_CONDMET  0x04    // Condition Met
+#define STATUS_BUSY     0x08    // Busy
+#define STATUS_INTERM   0x10    // Intermediate
+#define STATUS_INTCDMET 0x14    // Intermediate-condition met
+#define STATUS_RESCONF  0x18    // Reservation conflict
+#define STATUS_COMTERM  0x22    // Command Terminated
+#define STATUS_QFULL    0x28    // Queue full
+
+//***************************************************************************
+//                      %%% SCSI MISCELLANEOUS EQUATES %%%
+//***************************************************************************
+#define MAXLUN          7       // Maximum Logical Unit Id
+#define MAXTARG         7       // Maximum Target Id
+#define MAX_SCSI_LUNS   64      // Maximum Number of SCSI LUNs
+#define MAX_NUM_HA      8       // Maximum Number of SCSI HA's
+
+//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/
+//
+//                          %%% SCSI COMMAND OPCODES %%%
+//
+///\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/
+
+//***************************************************************************
+//               %%% Commands for all Device Types %%%
+//***************************************************************************
+#define SCSI_CHANGE_DEF 0x40    // Change Definition (Optional)
+#define SCSI_COMPARE    0x39    // Compare (O)
+#define SCSI_COPY       0x18    // Copy (O)
+#define SCSI_COP_VERIFY 0x3A    // Copy and Verify (O)
+#define SCSI_INQUIRY    0x12    // Inquiry (MANDATORY)
+#define SCSI_LOG_SELECT 0x4C    // Log Select (O)
+#define SCSI_LOG_SENSE  0x4D    // Log Sense (O)
+#define SCSI_MODE_SEL6  0x15    // Mode Select 6-byte (Device Specific)
+#define SCSI_MODE_SEL10 0x55    // Mode Select 10-byte (Device Specific)
+#define SCSI_MODE_SEN6  0x1A    // Mode Sense 6-byte (Device Specific)
+#define SCSI_MODE_SEN10 0x5A    // Mode Sense 10-byte (Device Specific)
+#define SCSI_READ_BUFF  0x3C    // Read Buffer (O)
+#define SCSI_REQ_SENSE  0x03    // Request Sense (MANDATORY)
+#define SCSI_SEND_DIAG  0x1D    // Send Diagnostic (O)
+#define SCSI_TST_U_RDY  0x00    // Test Unit Ready (MANDATORY)
+#define SCSI_WRITE_BUFF 0x3B    // Write Buffer (O)
+
+//***************************************************************************
+//            %%% Commands Unique to Direct Access Devices %%%
+//***************************************************************************
+#define SCSI_COMPARE    0x39    // Compare (O)
+#define SCSI_FORMAT     0x04    // Format Unit (MANDATORY)
+#define SCSI_LCK_UN_CAC 0x36    // Lock Unlock Cache (O)
+#define SCSI_PREFETCH   0x34    // Prefetch (O)
+#define SCSI_MED_REMOVL 0x1E    // Prevent/Allow medium Removal (O)
+#define SCSI_READ6      0x08    // Read 6-byte (MANDATORY)
+#define SCSI_READ10     0x28    // Read 10-byte (MANDATORY)
+#define SCSI_RD_CAPAC   0x25    // Read Capacity (MANDATORY)
+#define SCSI_RD_DEFECT  0x37    // Read Defect Data (O)
+#define SCSI_READ_LONG  0x3E    // Read Long (O)
+#define SCSI_REASS_BLK  0x07    // Reassign Blocks (O)
+#define SCSI_RCV_DIAG   0x1C    // Receive Diagnostic Results (O)
+#define SCSI_RELEASE    0x17    // Release Unit (MANDATORY)
+#define SCSI_REZERO     0x01    // Rezero Unit (O)
+#define SCSI_SRCH_DAT_E 0x31    // Search Data Equal (O)
+#define SCSI_SRCH_DAT_H 0x30    // Search Data High (O)
+#define SCSI_SRCH_DAT_L 0x32    // Search Data Low (O)
+#define SCSI_SEEK6      0x0B    // Seek 6-Byte (O)
+#define SCSI_SEEK10     0x2B    // Seek 10-Byte (O)
+#define SCSI_SEND_DIAG  0x1D    // Send Diagnostics (MANDATORY)
+#define SCSI_SET_LIMIT  0x33    // Set Limits (O)
+#define SCSI_START_STP  0x1B    // Start/Stop Unit (O)
+#define SCSI_SYNC_CACHE 0x35    // Synchronize Cache (O)
+#define SCSI_VERIFY     0x2F    // Verify (O)
+#define SCSI_WRITE6     0x0A    // Write 6-Byte (MANDATORY)
+#define SCSI_WRITE10    0x2A    // Write 10-Byte (MANDATORY)
+#define SCSI_WRT_VERIFY 0x2E    // Write and Verify (O)
+#define SCSI_WRITE_LONG 0x3F    // Write Long (O)
+#define SCSI_WRITE_SAME 0x41    // Write Same (O)
+
+//***************************************************************************
+//          %%% Commands Unique to Sequential Access Devices %%%
+//***************************************************************************
+#define SCSI_ERASE      0x19    // Erase (MANDATORY)
+#define SCSI_LOAD_UN    0x1B    // Load/Unload (O)
+#define SCSI_LOCATE     0x2B    // Locate (O)
+#define SCSI_RD_BLK_LIM 0x05    // Read Block Limits (MANDATORY)
+#define SCSI_READ_POS   0x34    // Read Position (O)
+#define SCSI_READ_REV   0x0F    // Read Reverse (O)
+#define SCSI_REC_BF_DAT 0x14    // Recover Buffer Data (O)
+#define SCSI_RESERVE    0x16    // Reserve Unit (MANDATORY)
+#define SCSI_REWIND     0x01    // Rewind (MANDATORY)
+#define SCSI_SPACE      0x11    // Space (MANDATORY)
+#define SCSI_VERIFY_T   0x13    // Verify (Tape) (O)
+#define SCSI_WRT_FILE   0x10    // Write Filemarks (MANDATORY)
+
+//***************************************************************************
+//                %%% Commands Unique to Printer Devices %%%
+//***************************************************************************
+#define SCSI_PRINT      0x0A    // Print (MANDATORY)
+#define SCSI_SLEW_PNT   0x0B    // Slew and Print (O)
+#define SCSI_STOP_PNT   0x1B    // Stop Print (O)
+#define SCSI_SYNC_BUFF  0x10    // Synchronize Buffer (O)
+
+//***************************************************************************
+//               %%% Commands Unique to Processor Devices %%%
+//***************************************************************************
+#define SCSI_RECEIVE    0x08        // Receive (O)
+#define SCSI_SEND       0x0A        // Send (O)
+
+//***************************************************************************
+//              %%% Commands Unique to Write-Once Devices %%%
+//***************************************************************************
+#define SCSI_MEDIUM_SCN 0x38    // Medium Scan (O)
+#define SCSI_SRCHDATE10 0x31    // Search Data Equal 10-Byte (O)
+#define SCSI_SRCHDATE12 0xB1    // Search Data Equal 12-Byte (O)
+#define SCSI_SRCHDATH10 0x30    // Search Data High 10-Byte (O)
+#define SCSI_SRCHDATH12 0xB0    // Search Data High 12-Byte (O)
+#define SCSI_SRCHDATL10 0x32    // Search Data Low 10-Byte (O)
+#define SCSI_SRCHDATL12 0xB2    // Search Data Low 12-Byte (O)
+#define SCSI_SET_LIM_10 0x33    // Set Limits 10-Byte (O)
+#define SCSI_SET_LIM_12 0xB3    // Set Limits 10-Byte (O)
+#define SCSI_VERIFY10   0x2F    // Verify 10-Byte (O)
+#define SCSI_VERIFY12   0xAF    // Verify 12-Byte (O)
+#define SCSI_WRITE12    0xAA    // Write 12-Byte (O)
+#define SCSI_WRT_VER10  0x2E    // Write and Verify 10-Byte (O)
+#define SCSI_WRT_VER12  0xAE    // Write and Verify 12-Byte (O)
+
+//***************************************************************************
+//                %%% Commands Unique to CD-ROM Devices %%%
+//***************************************************************************
+#define SCSI_PLAYAUD_10 0x45    // Play Audio 10-Byte (O)
+#define SCSI_PLAYAUD_12 0xA5    // Play Audio 12-Byte 12-Byte (O)
+#define SCSI_PLAYAUDMSF 0x47    // Play Audio MSF (O)
+#define SCSI_PLAYA_TKIN 0x48    // Play Audio Track/Index (O)
+#define SCSI_PLYTKREL10 0x49    // Play Track Relative 10-Byte (O)
+#define SCSI_PLYTKREL12 0xA9    // Play Track Relative 12-Byte (O)
+#define SCSI_READCDCAP  0x25    // Read CD-ROM Capacity (MANDATORY)
+#define SCSI_READHEADER 0x44    // Read Header (O)
+#define SCSI_SUBCHANNEL 0x42    // Read Subchannel (O)
+#define SCSI_READ_TOC   0x43    // Read TOC (O)
+
+//***************************************************************************
+//                %%% Commands Unique to Scanner Devices %%%
+//***************************************************************************
+#define SCSI_GETDBSTAT  0x34    // Get Data Buffer Status (O)
+#define SCSI_GETWINDOW  0x25    // Get Window (O)
+#define SCSI_OBJECTPOS  0x31    // Object Postion (O)
+#define SCSI_SCAN       0x1B    // Scan (O)
+#define SCSI_SETWINDOW  0x24    // Set Window (MANDATORY)
+
+//***************************************************************************
+//           %%% Commands Unique to Optical Memory Devices %%%
+//***************************************************************************
+#define SCSI_UpdateBlk  0x3D    // Update Block (O)
+
+//***************************************************************************
+//           %%% Commands Unique to Medium Changer Devices %%%
+//***************************************************************************
+#define SCSI_EXCHMEDIUM 0xA6    // Exchange Medium (O)
+#define SCSI_INITELSTAT 0x07    // Initialize Element Status (O)
+#define SCSI_POSTOELEM  0x2B    // Position to Element (O)
+#define SCSI_REQ_VE_ADD 0xB5    // Request Volume Element Address (O)
+#define SCSI_SENDVOLTAG 0xB6    // Send Volume Tag (O)
+
+//***************************************************************************
+//            %%% Commands Unique to Communication Devices %%%
+//***************************************************************************
+#define SCSI_GET_MSG_6  0x08    // Get Message 6-Byte (MANDATORY)
+#define SCSI_GET_MSG_10 0x28    // Get Message 10-Byte (O)
+#define SCSI_GET_MSG_12 0xA8    // Get Message 12-Byte (O)
+#define SCSI_SND_MSG_6  0x0A    // Send Message 6-Byte (MANDATORY)
+#define SCSI_SND_MSG_10 0x2A    // Send Message 10-Byte (O)
+#define SCSI_SND_MSG_12 0xAA    // Send Message 12-Byte (O)
+
+//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/
+//
+//                    %%% END OF SCSI COMMAND OPCODES %%%
+//
+///\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/
+
+//***************************************************************************
+//                      %%% Request Sense Data Format %%%
+//***************************************************************************
+typedef struct {
+
+    BYTE    ErrorCode;          // Error Code (70H or 71H)
+    BYTE    SegmentNum;         // Number of current segment descriptor
+    BYTE    SenseKey;           // Sense Key(See bit definitions too)
+    BYTE    InfoByte0;          // Information MSB
+    BYTE    InfoByte1;          // Information MID
+    BYTE    InfoByte2;          // Information MID
+    BYTE    InfoByte3;          // Information LSB
+    BYTE    AddSenLen;          // Additional Sense Length
+    BYTE    ComSpecInf0;        // Command Specific Information MSB
+    BYTE    ComSpecInf1;        // Command Specific Information MID
+    BYTE    ComSpecInf2;        // Command Specific Information MID
+    BYTE    ComSpecInf3;        // Command Specific Information LSB
+    BYTE    AddSenseCode;       // Additional Sense Code
+    BYTE    AddSenQual;         // Additional Sense Code Qualifier
+    BYTE    FieldRepUCode;      // Field Replaceable Unit Code
+    BYTE    SenKeySpec15;       // Sense Key Specific 15th byte
+    BYTE    SenKeySpec16;       // Sense Key Specific 16th byte
+    BYTE    SenKeySpec17;       // Sense Key Specific 17th byte
+    BYTE    AddSenseBytes;      // Additional Sense Bytes
+
+} SENSE_DATA_FMT;
+
+//***************************************************************************
+//                       %%% REQUEST SENSE ERROR CODE %%%
+//***************************************************************************
+#define SERROR_CURRENT  0x70    // Current Errors
+#define SERROR_DEFERED  0x71    // Deferred Errors
+
+//***************************************************************************
+//                   %%% REQUEST SENSE BIT DEFINITIONS %%%
+//***************************************************************************
+#define SENSE_VALID     0x80    // Byte 0 Bit 7
+#define SENSE_FILEMRK   0x80    // Byte 2 Bit 7
+#define SENSE_EOM       0x40    // Byte 2 Bit 6
+#define SENSE_ILI       0x20    // Byte 2 Bit 5
+
+//***************************************************************************
+//               %%% REQUEST SENSE SENSE KEY DEFINITIONS %%%
+//***************************************************************************
+#define KEY_NOSENSE     0x00    // No Sense
+#define KEY_RECERROR    0x01    // Recovered Error
+#define KEY_NOTREADY    0x02    // Not Ready
+#define KEY_MEDIUMERR   0x03    // Medium Error
+#define KEY_HARDERROR   0x04    // Hardware Error
+#define KEY_ILLGLREQ    0x05    // Illegal Request
+#define KEY_UNITATT     0x06    // Unit Attention
+#define KEY_DATAPROT    0x07    // Data Protect
+#define KEY_BLANKCHK    0x08    // Blank Check
+#define KEY_VENDSPEC    0x09    // Vendor Specific
+#define KEY_COPYABORT   0x0A    // Copy Abort
+#define KEY_EQUAL       0x0C    // Equal (Search)
+#define KEY_VOLOVRFLW   0x0D    // Volume Overflow
+#define KEY_MISCOMP     0x0E    // Miscompare (Search)
+#define KEY_RESERVED    0x0F    // Reserved
+
+//***************************************************************************
+//                %%% PERIPHERAL DEVICE TYPE DEFINITIONS %%%
+//***************************************************************************
+#define DTYPE_DASD      0x00    // Disk Device
+#define DTYPE_SEQD      0x01    // Tape Device
+#define DTYPE_PRNT      0x02    // Printer
+#define DTYPE_PROC      0x03    // Processor
+#define DTYPE_WORM      0x04    // Write-once read-multiple
+#define DTYPE_CROM      0x05    // CD-ROM device
+#define DTYPE_CDROM     0x05    // CD-ROM device
+#define DTYPE_SCAN      0x06    // Scanner device
+#define DTYPE_OPTI      0x07    // Optical memory device
+#define DTYPE_JUKE      0x08    // Medium Changer device
+#define DTYPE_COMM      0x09    // Communications device
+#define DTYPE_RESL      0x0A    // Reserved (low)
+#define DTYPE_RESH      0x1E    // Reserved (high)
+#define DTYPE_UNKNOWN   0x1F    // Unknown or no device type
+
+//***************************************************************************
+//                %%% ANSI APPROVED VERSION DEFINITIONS %%%
+//***************************************************************************
+#define ANSI_MAYBE      0x0     // Device may or may not be ANSI approved stand
+#define ANSI_SCSI1      0x1     // Device complies to ANSI X3.131-1986 (SCSI-1)
+#define ANSI_SCSI2      0x2     // Device complies to SCSI-2
+#define ANSI_RESLO      0x3     // Reserved (low)
+#define ANSI_RESHI      0x7     // Reserved (high)
diff --git a/src/include/wnaspi32.h b/src/include/wnaspi32.h
new file mode 100644 (file)
index 0000000..b2c7ef5
--- /dev/null
@@ -0,0 +1,325 @@
+/******************************************************************************
+**
+**  Module Name:    wnaspi32.h
+**
+**  Description:    Header file for ASPI for Win32.  This header includes
+**                  macro and type declarations, and can be included without
+**                  modification when using Borland C++ or Microsoft Visual
+**                  C++ with 32-bit compilation.  If you are using a different
+**                  compiler then you MUST ensure that structures are packed
+**                  onto byte alignments, and that C++ name mangling is turned
+**                  off.
+**
+**  Notes:          This file created using 4 spaces per tab.
+**
+******************************************************************************/
+
+#ifndef __WNASPI32_H__
+#define __WNASPI32_H__
+
+/*
+** Make sure structures are packed and undecorated.
+*/
+
+#ifdef __BORLANDC__
+#pragma option -a1
+#endif //__BORLANDC__
+
+#ifdef _MSC_VER
+#pragma pack(1)
+#endif //__MSC_VER
+
+#ifdef __cplusplus
+extern "C" {
+#endif //__cplusplus
+
+//*****************************************************************************
+//      %%% SCSI MISCELLANEOUS EQUATES %%%
+//*****************************************************************************
+
+#define SENSE_LEN                   14          // Default sense buffer length
+#define SRB_DIR_SCSI                0x00        // Direction determined by SCSI
+#define SRB_POSTING                 0x01        // Enable ASPI posting
+#define SRB_ENABLE_RESIDUAL_COUNT   0x04        // Enable residual byte count reporting
+#define SRB_DIR_IN                  0x08        // Transfer from SCSI target to host
+#define SRB_DIR_OUT                 0x10        // Transfer from host to SCSI target
+#define SRB_EVENT_NOTIFY            0x40        // Enable ASPI event notification
+
+#define RESIDUAL_COUNT_SUPPORTED    0x02        // Extended buffer flag
+#define MAX_SRB_TIMEOUT             108000lu    // 30 hour maximum timeout in s
+#define DEFAULT_SRB_TIMEOUT         108000lu    // Max timeout by default
+
+
+//*****************************************************************************
+//      %%% ASPI Command Definitions %%%
+//*****************************************************************************
+
+#define SC_HA_INQUIRY               0x00        // Host adapter inquiry
+#define SC_GET_DEV_TYPE             0x01        // Get device type
+#define SC_EXEC_SCSI_CMD            0x02        // Execute SCSI command
+#define SC_ABORT_SRB                0x03        // Abort an SRB
+#define SC_RESET_DEV                0x04        // SCSI bus device reset
+#define SC_SET_HA_PARMS             0x05        // Set HA parameters
+#define SC_GET_DISK_INFO            0x06        // Get Disk information
+#define SC_RESCAN_SCSI_BUS          0x07        // ReBuild SCSI device map
+#define SC_GETSET_TIMEOUTS          0x08        // Get/Set target timeouts
+
+//*****************************************************************************
+//      %%% SRB Status %%%
+//*****************************************************************************
+
+#define SS_PENDING                  0x00        // SRB being processed
+#define SS_COMP                     0x01        // SRB completed without error
+#define SS_ABORTED                  0x02        // SRB aborted
+#define SS_ABORT_FAIL               0x03        // Unable to abort SRB
+#define SS_ERR                      0x04        // SRB completed with error
+
+#define SS_INVALID_CMD              0x80        // Invalid ASPI command
+#define SS_INVALID_HA               0x81        // Invalid host adapter number
+#define SS_NO_DEVICE                0x82        // SCSI device not installed
+
+#define SS_INVALID_SRB              0xE0        // Invalid parameter set in SRB
+#define SS_OLD_MANAGER              0xE1        // ASPI manager doesn't support Windows
+#define SS_BUFFER_ALIGN             0xE1        // Buffer not aligned (replaces OLD_MANAGER in Win32)
+#define SS_ILLEGAL_MODE             0xE2        // Unsupported Windows mode
+#define SS_NO_ASPI                  0xE3        // No ASPI managers resident
+#define SS_FAILED_INIT              0xE4        // ASPI for windows failed init
+#define SS_ASPI_IS_BUSY             0xE5        // No resources available to execute cmd
+#define SS_BUFFER_TO_BIG            0xE6        // Buffer size to big to handle!
+#define SS_MISMATCHED_COMPONENTS    0xE7        // The DLLs/EXEs of ASPI don't version check
+#define SS_NO_ADAPTERS              0xE8        // No host adapters to manage
+#define SS_INSUFFICIENT_RESOURCES   0xE9        // Couldn't allocate resources needed to init
+#define SS_ASPI_IS_SHUTDOWN         0xEA        // Call came to ASPI after PROCESS_DETACH
+#define SS_BAD_INSTALL              0xEB        // The DLL or other components are installed wrong
+
+//*****************************************************************************
+//      %%% Host Adapter Status %%%
+//*****************************************************************************
+
+#define HASTAT_OK                   0x00        // Host adapter did not detect an                                                                                                                       // error
+#define HASTAT_SEL_TO               0x11        // Selection Timeout
+#define HASTAT_DO_DU                0x12        // Data overrun data underrun
+#define HASTAT_BUS_FREE             0x13        // Unexpected bus free
+#define HASTAT_PHASE_ERR            0x14        // Target bus phase sequence                                                                                                                            // failure
+#define HASTAT_TIMEOUT              0x09        // Timed out while SRB was                                                                                                                                      waiting to beprocessed.
+#define HASTAT_COMMAND_TIMEOUT      0x0B        // Adapter timed out processing SRB.
+#define HASTAT_MESSAGE_REJECT       0x0D        // While processing SRB, the                                                                                                                            // adapter received a MESSAGE
+#define HASTAT_BUS_RESET            0x0E        // A bus reset was detected.
+#define HASTAT_PARITY_ERROR         0x0F        // A parity error was detected.
+#define HASTAT_REQUEST_SENSE_FAILED 0x10        // The adapter failed in issuing
+
+//*****************************************************************************
+//          %%% SRB - HOST ADAPTER INQUIRY - SC_HA_INQUIRY (0) %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_HA_INQUIRY
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 ASPI request flags
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved, MUST = 0
+    BYTE        HA_Count;                       // 08/008 Number of host adapters present
+    BYTE        HA_SCSI_ID;                     // 09/009 SCSI ID of host adapter
+    BYTE        HA_ManagerId[16];               // 0A/010 String describing the manager
+    BYTE        HA_Identifier[16];              // 1A/026 String describing the host adapter
+    BYTE        HA_Unique[16];                  // 2A/042 Host Adapter Unique parameters
+    WORD        HA_Rsvd1;                       // 3A/058 Reserved, MUST = 0
+}
+SRB_HAInquiry, *PSRB_HAInquiry, FAR *LPSRB_HAInquiry;
+
+//*****************************************************************************
+//          %%% SRB - GET DEVICE TYPE - SC_GET_DEV_TYPE (1) %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_GET_DEV_TYPE
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 Reserved, MUST = 0
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved, MUST = 0
+    BYTE        SRB_Target;                     // 08/008 Target's SCSI ID
+    BYTE        SRB_Lun;                        // 09/009 Target's LUN number
+    BYTE        SRB_DeviceType;                 // 0A/010 Target's peripheral device type
+    BYTE        SRB_Rsvd1;                      // 0B/011 Reserved, MUST = 0
+}
+SRB_GDEVBlock, *PSRB_GDEVBlock, FAR *LPSRB_GDEVBlock;
+
+//*****************************************************************************
+//          %%% SRB - EXECUTE SCSI COMMAND - SC_EXEC_SCSI_CMD (2) %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_EXEC_SCSI_CMD
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 ASPI request flags
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved
+    BYTE        SRB_Target;                     // 08/008 Target's SCSI ID
+    BYTE        SRB_Lun;                        // 09/009 Target's LUN number
+    WORD        SRB_Rsvd1;                      // 0A/010 Reserved for Alignment
+    DWORD       SRB_BufLen;                     // 0C/012 Data Allocation Length
+    BYTE        FAR *SRB_BufPointer;            // 10/016 Data Buffer Pointer
+    BYTE        SRB_SenseLen;                   // 14/020 Sense Allocation Length
+    BYTE        SRB_CDBLen;                     // 15/021 CDB Length
+    BYTE        SRB_HaStat;                     // 16/022 Host Adapter Status
+    BYTE        SRB_TargStat;                   // 17/023 Target Status
+    VOID        FAR *SRB_PostProc;              // 18/024 Post routine
+    BYTE        SRB_Rsvd2[20];                  // 1C/028 Reserved, MUST = 0
+    BYTE        CDBByte[16];                    // 30/048 SCSI CDB
+    BYTE        SenseArea[SENSE_LEN+2];         // 50/064 Request Sense buffer
+}
+SRB_ExecSCSICmd, *PSRB_ExecSCSICmd, FAR *LPSRB_ExecSCSICmd;
+
+//*****************************************************************************
+//          %%% SRB - ABORT AN SRB - SC_ABORT_SRB (3) %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_ABORT_SRB
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 Reserved
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved
+    VOID        FAR *SRB_ToAbort;               // 08/008 Pointer to SRB to abort
+}
+SRB_Abort, *PSRB_Abort, FAR *LPSRB_Abort;
+
+//*****************************************************************************
+//          %%% SRB - BUS DEVICE RESET - SC_RESET_DEV (4) %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_RESET_DEV
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 ASPI request flags
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved
+    BYTE        SRB_Target;                     // 08/008 Target's SCSI ID
+    BYTE        SRB_Lun;                        // 09/009 Target's LUN number
+    BYTE        SRB_Rsvd1[12];                  // 0A/010 Reserved for Alignment
+    BYTE        SRB_HaStat;                     // 16/022 Host Adapter Status
+    BYTE        SRB_TargStat;                   // 17/023 Target Status
+    VOID        FAR *SRB_PostProc;              // 18/024 Post routine
+    BYTE        SRB_Rsvd2[36];                  // 1C/028 Reserved, MUST = 0
+}
+SRB_BusDeviceReset, *PSRB_BusDeviceReset, FAR *LPSRB_BusDeviceReset;
+
+//*****************************************************************************
+//          %%% SRB - GET DISK INFORMATION - SC_GET_DISK_INFO %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_GET_DISK_INFO
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 Reserved, MUST = 0
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved, MUST = 0
+    BYTE        SRB_Target;                     // 08/008 Target's SCSI ID
+    BYTE        SRB_Lun;                        // 09/009 Target's LUN number
+    BYTE        SRB_DriveFlags;                 // 0A/010 Driver flags
+    BYTE        SRB_Int13HDriveInfo;            // 0B/011 Host Adapter Status
+    BYTE        SRB_Heads;                      // 0C/012 Preferred number of heads translation
+    BYTE        SRB_Sectors;                    // 0D/013 Preferred number of sectors translation
+    BYTE        SRB_Rsvd1[10];                  // 0E/014 Reserved, MUST = 0
+}
+SRB_GetDiskInfo, *PSRB_GetDiskInfo, FAR *LPSRB_GetDiskInfo;
+
+//*****************************************************************************
+//          %%%  SRB - RESCAN SCSI BUS(ES) ON SCSIPORT %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_RESCAN_SCSI_BUS
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 Reserved, MUST = 0
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved, MUST = 0
+}
+SRB_RescanPort, *PSRB_RescanPort, FAR *LPSRB_RescanPort;
+
+//*****************************************************************************
+//          %%% SRB - GET/SET TARGET TIMEOUTS %%%
+//*****************************************************************************
+
+typedef struct                                  // Offset
+{                                               // HX/DEC
+    BYTE        SRB_Cmd;                        // 00/000 ASPI command code = SC_GETSET_TIMEOUTS
+    BYTE        SRB_Status;                     // 01/001 ASPI command status byte
+    BYTE        SRB_HaId;                       // 02/002 ASPI host adapter number
+    BYTE        SRB_Flags;                      // 03/003 ASPI request flags
+    DWORD       SRB_Hdr_Rsvd;                   // 04/004 Reserved, MUST = 0
+    BYTE        SRB_Target;                     // 08/008 Target's SCSI ID
+    BYTE        SRB_Lun;                        // 09/009 Target's LUN number
+    DWORD       SRB_Timeout;                    // 0A/010 Timeout in half seconds
+}
+SRB_GetSetTimeouts, *PSRB_GetSetTimeouts, FAR *LPSRB_GetSetTimeouts;
+
+//*****************************************************************************
+//          %%% ASPIBUFF - Structure For Controllng I/O Buffers %%%
+//*****************************************************************************
+
+typedef struct tag_ASPI32BUFF                   // Offset
+{                                               // HX/DEC
+    PBYTE                   AB_BufPointer;      // 00/000 Pointer to the ASPI allocated buffer
+    DWORD                   AB_BufLen;          // 04/004 Length in bytes of the buffer
+    DWORD                   AB_ZeroFill;        // 08/008 Flag set to 1 if buffer should be zeroed
+    DWORD                   AB_Reserved;        // 0C/012 Reserved
+}
+ASPI32BUFF, *PASPI32BUFF, FAR *LPASPI32BUFF;
+
+//*****************************************************************************
+//          %%% PROTOTYPES - User Callable ASPI for Win32 Functions %%%
+//*****************************************************************************
+
+typedef void *LPSRB;
+
+#if defined(__BORLANDC__)
+
+DWORD _import GetASPI32SupportInfo( void );
+DWORD _import SendASPI32Command( LPSRB );
+BOOL _import GetASPI32Buffer( PASPI32BUFF );
+BOOL _import FreeASPI32Buffer( PASPI32BUFF );
+BOOL _import TranslateASPI32Address( PDWORD, PDWORD );
+
+#elif defined(_MSC_VER)
+
+__declspec(dllimport) DWORD GetASPI32SupportInfo( void );
+__declspec(dllimport) DWORD SendASPI32Command( LPSRB );
+__declspec(dllimport) BOOL GetASPI32Buffer( PASPI32BUFF );
+__declspec(dllimport) BOOL FreeASPI32Buffer( PASPI32BUFF );
+__declspec(dllimport) BOOL TranslateASPI32Address( PDWORD, PDWORD );
+
+#else
+
+extern DWORD GetASPI32SupportInfo( void );
+extern DWORD GetASPI32Command( LPSRB );
+extern BOOL GetASPI32Buffer( PASPI32BUFF );
+extern BOOL FreeASPI32Buffer( PASPI32BUFF );
+extern BOOL TranslateASPI32Address( PDWORD, PDWORD );
+
+#endif
+
+/*
+** Restore compiler default packing and close off the C declarations.
+*/
+
+#ifdef __BORLANDC__
+#pragma option -a.
+#endif //__BORLANDC__
+
+#ifdef _MSC_VER
+#pragma pack()
+#endif //_MSC_VER
+
+#ifdef __cplusplus
+}
+#endif //__cplusplus
+
+#endif //__WNASPI32_H__