⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 atadrvr.ug

📁 ATADRVR是DOS下的磁盘驱动程序,采用PIO传输 ,PCI DMA传输,ATA包,等非常全面代码示例... 内部有C与Asm描述. 编译环境:Borland C/C++ 4.52 与 Bo
💻 UG
📖 第 1 页 / 共 4 页
字号:
void pio_rep_indword( unsigned int addrDataReg,    // register address
                      unsigned int bufSeg,         // buffer address
                      unsigned int bufOff,         // buffer address
                      unsigned int dwordCnt );     // dword count

   NOTE: Normally this function is not called directly but
   is called by the pio_drq_block_in() function!

   Use the REP INSD instruction to read the ATA Data Register
   during PIO data transfer.  Note that this function is called
   by pio_drq_block_in() but only if:  1) pio_xfer_width is 32
   and 2) the number of bytes to be read is a multiple of 4.

void pio_rep_inword( unsigned int addrDataReg,     // register address
                     unsigned int bufSeg,          // buffer address
                     unsigned int bufOff,          // buffer address
                     unsigned int wordCnt );       // word count

   NOTE: Normally this function is not called directly but
   is called by the pio_drq_block_in() function!

   Use the REP INSW instruction to read the ATA Data Register
   during PIO data transfer.

void pio_rep_outbyte( unsigned int addrDataReg,   // register address
                      unsigned int bufSeg,        // buffer address
                      unsigned int bufOff,        // buffer address
                      unsigned int bytedCnt );    // byte count

   NOTE: Normally this function is not called directly but
   is called by the pio_drq_block_out() function!

   Use the REP OUTS instruction to write the ATA Data Register
   during PIO data transfer.

void pio_rep_outdword( unsigned int addrDataReg,   // register address
                       unsigned int bufSeg,        // buffer address
                       unsigned int bufOff,        // buffer address
                       unsigned int dwordCnt );    // dword count

   NOTE: Normally this function is not called directly but
   is called by the pio_drq_block_out() function!

   Use the REP OUTSD instruction to write the ATA Data Register
   during PIO data transfer.  Note that this function is called
   by pio_drq_block_out() but only if:  1) pio_xfer_width is 32
   and 2) the number of bytes to be written is a multiple of 4.

void pio_rep_outword( unsigned int addrDataReg,    // register address
                      unsigned int bufSeg,         // buffer address
                      unsigned int bufOff,         // buffer address
                      unsigned int wordCnt );      // word count

   NOTE: Normally this function is not called directly but
   is called by the pio_drq_block_out() function!

   Use the REP OUTSW instruction to write the ATA Data Register
   during PIO data transfer.

void pio_set_iobase_addr( unsigned int base1,
                          unsigned int base2 );

   Either pio_set_iobase_addr() or pio_set_memory_addr() must be
   called before any other ATADRVR functions can be used!

   Configure the ATA host adapter's I/O port addresses.  Normal
   calls to this function are:

      pio_set_iobase_addr( 0x1f0, 0x3f0 ) // primary
      pio_set_iobase_addr( 0x170, 0x370 ) // secondary

   For PCMCIA PC Card ATA Contiguous I/O mode use:

      pio_set_iobase_addr( addr, addr+8 )

   where the least significant 4 bits of addr are zero.  Note
   that the calling program must find a contiguous set of 16 I/O
   port addresses that are not in use in order to use this PCMCIA
   I/O mode.  See the documentation file PCC.UG!

void pio_set_memory_addr( unsigned int seg );

   Either pio_set_iobase_addr() or pio_set_memory_addr() must be
   called before any other ATADRVR functions can be used!

   Configure the ATA host adapter's memory address in PCMCIA PC
   Card ATA Memory mode.  Note that the calling program must find
   a 4K block of memory that is not in use in order to use this
   PCMCIA mode.  See the documentation file PCC.UG!

int pio_use_dword;

   NOTE: pio_use_dword has been replaced by pio_xfer_width !

int pio_xfer_width;

   This variable controls the width of PIO data transfers.
   This variable can have the following values:

   8 = 8-bits. PIO transfers will use REP INS and REP OUTS
       or 8-bit memory write/read in PCMCIA Memory mode.

   16 = 16-bits. PIO transfers will use REP INSW and REP OUTSW
        or 16-bit memory write/read in PCMCIA Memory mode.

   32 = 32-bits. PIO transfers will use REP INSD and REP OUTSD.

   Any other value is treated the same as 16.

   The default value is 16.

   See the pio_rep_*() functions above.

   Use this ATADRVR feature with great care and read the
   documentation file PIO.UG!


Functions And Data In ATAIOREG.C
--------------------------------

These functions provide the basic ATA and ATAPI command protocol
functions.  The function reg_config() MUST be called after
calling pio_set_iobase_addr() (or pio_set_memory_addr()).
Failure to call reg_config() will cause ATADRVR to operate
incorrectly.

unsigned char reg_atapi_cp_data[16];
int reg_atapi_cp_size;

   These values are READONLY -- DO NOT ALTER.

   reg_atapi_cp_size is the size of the most recent ATAPI command
   packet size (normally 12 or 16). reg_atapi_cp_data[16] is the
   most recent ATAPI command packet (SCSI CDB) data.

int reg_atapi_delay_flag;

   Many ATAPI devices are very poorly designed and do not follow
   the ATA or ATAPI protocols as defined by the ATA/ATAPI-4
   standard.  Setting this word to a non-zero value causes
   ATADRVR to insert an approximately 100ms delay into the ATA
   and/or ATAPI command protocols.  This delay seems to allow
   enough time for these non-conforming devices to operate
   correctly.

unsigned char reg_atapi_reg_fr;  // 0x01 OR'ed in for DMA
unsigned char reg_atapi_reg_sc;
unsigned char reg_atapi_reg_sn;
unsigned char reg_atapi_reg_dh;  // only bits 3,2,1,0 are used

   These values are placed into the Feature, Sector Count, Sector
   Number and Device/Head register by the reg_packet(),
   dma_isa_packet() and dma_pci_packet() functions before the A0H
   command is started.  These values are then set to zero before
   reg_packet() returns.

long reg_buffer_size;

   This must be set to the size in bytes of the data buffer
   provided by the caller.

struct REG_CMD_INFO
{
   unsigned char flg;         // see TRC_FLAG_xxx in ATAIO.H
   unsigned char ct;          // see TRC_TYPE_xxx in ATAIO.H
   unsigned char cmd;         // command code
   unsigned char fr1;         // feature reg before
      ... See ATAIO.H ...
   unsigned char dc1;         // device control before
   unsigned char ec;          // ATADRVR error code
   unsigned char to;          // not zero if time out error
   unsigned char st2;         // status reg after
      ... See ATAIO.H ...
   unsigned char dh2;         // device head after
   long totalBytesXfer;       // total bytes transferred
   unsigned int failbits;     // failure bits (protocol violation bits)
   long drqPackets;           // number of PIO DRQ data packets
   long drqPacketSize;        // number of bytes in current DRQ block
} ;
struct REG_CMD_INFO reg_cmd_info;

   This data structure contains all the "before" and "after"
   information for the last command or reset executed.

   When the PIO data transfer call back function is called
   drqPackets is the DRQ block number (1, 2, 3, ...) and
   drqPacketSize is the number of bytes in the current DRQ block
   See reg_drq_block_call_back.

int reg_config( void );

   This function MUST be called so that ATADRVR can correctly
   configure itself. reg_config() sets the values into
   reg_config_info[2].

int reg_config_info[2];

   This array is set by calling reg_config(). reg_config_info[0]
   describes device 0 and reg_config_info[1] describes device 1.
   The possible values in these words are (see ATAIO.H):
   REG_CONFIG_TYPE_NONE, REG_CONFIG_TYPE_UNKN,
   REG_CONFIG_TYPE_ATA, REG_CONFIG_TYPE_ATAPI.

   Note that ATADRVR is not able to determine the type of some
   devices.  However, after issuing some commands the calling
   program may be able to determine the exact type of a device.
   The calling program may change the values in this array but
   this must be done very carefully:

   a) DO NOT CHANGE the value REG_CONFIG_TYPE_NONE.
   b) DO NOT CHANGE a value to REG_CONFIG_TYPE_NONE.
   c) The value REG_CONFIG_TYPE_UNKN can be changed to either
      REG_CONFIG_TYPE_ATA or REG_CONFIG_TYPE_ATAPI.

void ( * reg_drq_block_call_back ) ( struct REG_CMD_INFO * )

   When this value is not NULL the PIO Data In/Out functions
   place the data for each DRQ block at the beginning of the data
   buffer.  This function is called after each DRQ data block is
   read from the device or before each DRQ data block is written
   to the device.  The call back function receives a pointer to a
   REG_CMD_INFO structure.  Do not assume this pointer contains
   the address of the static structure reg_cmd_info.  To
   determine what is happening the call back function should use
   these variables in the structure:  flg, ct, cmd, drqPackets
   and drqPacketSize.  The call back function must not modify the
   contents of the REG_CMD_INFO structure.

   This value is set back to NULL before the PIO Data In/Out
   functions return.

int reg_non_data_chs( int dev,                   // device (0 or 1)
                      int cmd,                   // command register
                      int fr,                    // feature register
                      int sc,                    // sector count
                      unsigned int cyl,          // CHS cylinder high/low
                      int head,                  // CHS head
                      int sect );                // CHS sector

   Execute an ATA Non-Data command using CHS sector addressing.

   Returns 0 if no error or 1 if there is an error.  See the
   contents of reg_cmd_info.

int reg_non_data_lba28( int dev,               // device (0 or 1)
                        int cmd,               // command register
                        int fr,                // feature register
                        int sc,                // sector count
                        long lba );            // LBA

   Execute an ATA Non-Data command using LBA sector addressing.

   Returns 0 if no error or 1 if there is an error.  See the
   contents of reg_cmd_info.

int reg_non_data_lba48( int dev,               // device (0 or 1)
                        int cmd,               // command register
                        int fr,                // feature register
                        int sc,                // sector count
                        long lbahi,            // LBA upper 16-bits
                        long lbalo );          // LBA lower 32 bits

   Execute an ATA Non-Data command using LBA sector addressing.

   Returns 0 if no error or 1 if there is an error.  See the
   contents of reg_cmd_info.

int reg_packet( int dev,                     // device (0 or 1)
                unsigned int cpbc,           // command packet size
                unsigned int cpseg,          // command packet buffer
                unsigned int cpoff,          // command packet buffer
                int dir,                     // 0 for no data or read, 1 for write
                unsigned int dpbc,           // max data packet size
                unsigned int dpseg,          // data packet buffer
                unsigned int dpoff );        // data packet buffer

   Execute an ATAPI Packet (A0H) command in PIO mode.  Note that
   the first byte of the Commmand Packet buffer is the command
   code of the "SCSI CDB" that is to be executed by the device.

   Returns 0 if no error or 1 if there is an error.  See the
   contents of reg_cmd_info.

int reg_pio_data_in_chs( int dev,                // device (0 or 1)
                         int cmd,                // command register
                         int fr,                 // feature register
                         int sc,                 // sector count

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -