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

📄 ataiotrc.c

📁 ~{S2EL~}wdm~{G}6/~}
💻 C
📖 第 1 页 / 共 3 页
字号:
//********************************************************************
// ATA LOW LEVEL I/O DRIVER -- ATAIOTRC.C
//
// by Hale Landis (hlandis@ibm.net)
//
// There is no copyright and there are no restrictions on the use
// of this ATA Low Level I/O Driver code.  It is distributed to
// help other programmers understand how the ATA device interface
// works and it is distributed without any warranty.  Use this
// code at your own risk.
//
// This code is based on the ATA-2, ATA-3 and ATA-4 standards and
// on interviews with various ATA controller and drive designers.
//
// This code has been run on many ATA (IDE) drives and
// MFM/RLL controllers.  This code may be a little
// more picky about the status it sees at various times.  A real
// BIOS probably would not check the status as carefully.
//
// Compile with one of the Borland C or C++ compilers.
//
// This C source contains the low level I/O trace functions.
//********************************************************************

#include <stdio.h>
#include <string.h>
#include <dos.h>

#include "ataio.h"

#include "ataiopd.h"

//**************************************************************

// trace dump buffer returned by trc_err_dump2()
// trc_cht_dump2() and trc_llt_dump2()

static unsigned char trcDmpBuf[100];

// buffer used to assemble print lines

static unsigned char prtBuf[64];

//**************************************************************

// command name lookup table and lookup function

static struct
{
   unsigned char cmdCode;
   unsigned char * cmdName;
} cmdNames[] =
   {
      0xC0 ,   "CFA ERASE SECTORS" ,
      0x03 ,   "CFA REQUEST EXT ERR CODE" ,
      0x87 ,   "CFA TRANSLATE SECTOR" ,
      0xCD ,   "CFA WRITE MULTIPLE WO ERASE" ,
      0x38 ,   "CFA WRITE SECTORS WO ERASE" ,
      0xE5 ,   "CHECK POWER MODE" ,
      0x98 ,   "CHECK POWER MODE" ,
      0x08 ,   "DEVICE RESET" ,
      0x90 ,   "EXECUTE DEVICE DIAGNOSTIC" ,
      0xE7 ,   "FLUSH CACHE" ,
      0x50 ,   "FORMAT TRACK" ,
      0xEC ,   "IDENTIFY DEVICE" ,
      0xA1 ,   "IDENTIFY PACKET DEVICE" ,
      0xE3 ,   "IDLE" ,
      0x97 ,   "IDLE" ,
      0xE1 ,   "IDLE IMMEDIATE" ,
      0x95 ,   "IDLE IMMEDIATE" ,
      0x91 ,   "INITIALIZE DEVICE PARAMETERS" ,
      0x00 ,   "NOP" ,
      0xA0 ,   "PACKET" ,
      0xE4 ,   "READ BUFFER" ,
      0xC7 ,   "READ DMA QUEUED" ,
      0xC8 ,   "READ DMA" ,
      0xC4 ,   "READ MULTIPLE" ,
      0x20 ,   "READ SECTORS" ,
      0x40 ,   "READ VERIFY SECTORS" ,
      0x10 ,   "RECALIBRATE" ,
      0x70 ,   "SEEK" ,
      0xEF ,   "SET FEATURES" ,
      0xC6 ,   "SET MULTIPLE MODE" ,
      0xE6 ,   "SLEEP" ,
      0x99 ,   "SLEEP" ,
      0xE2 ,   "STANDBY" ,
      0x96 ,   "STANDBY" ,
      0xE0 ,   "STANDBY IMMEDIATE" ,
      0x94 ,   "STANDBY IMMEDIATE" ,
      0xE8 ,   "WRITE BUFFER" ,
      0xCA ,   "WRITE DMA" ,
      0xCC ,   "WRITE DMA QUEUED" ,
      0xC5 ,   "WRITE MULTIPLE" ,
      0x30 ,   "WRITE SECTORS" ,
      0x3C ,   "WRITE VERIFY" ,
      0x00 ,   ""                   // end of table
   } ;

unsigned char * trc_get_cmd_name( unsigned char flg, unsigned char cc )

{
   int ndx = 0;

   if ( ( flg == TRC_FLAG_EMPTY ) || ( flg == TRC_FLAG_CDB ) )
      return "";
   if ( flg == TRC_FLAG_SRST )
      return "SOFT RESET";
   while ( * cmdNames[ndx].cmdName )
   {
      if ( cc == cmdNames[ndx].cmdCode )
         return cmdNames[ndx].cmdName;
      ndx ++ ;
   }
   return "";
}

//**************************************************************

// ATA status names lookup table and lookup function

static struct
{
   unsigned char bitPos;
   unsigned char * bitName;
} ataStatusNames[] =
   {
      0x80 , "BSY "  ,
      0x40 , "DRDY " ,
      0x20 , "DF "   ,
      0x10 , "DSC "  ,
      0x08 , "DRQ "  ,
      0x04 , "CORR " ,
      0x02 , "IDX "  ,
      0x01 , "ERR "
   } ;

static unsigned char ataStatusNameBuf[48];

unsigned char * trc_get_st_bit_name( unsigned char st )

{
   int ndx;

   if ( st & 0x80 )
      st = 0x80;
   * ataStatusNameBuf = 0;
   for ( ndx = 0; ndx < 8; ndx ++ )
   {
      if ( st & ataStatusNames[ndx].bitPos )
         strcat( ataStatusNameBuf, ataStatusNames[ndx].bitName );
   }
   return ataStatusNameBuf;
}

//**************************************************************

// ATA error names lookup table and lookup function

static struct
{
   unsigned char bitPos;
   unsigned char * bitName;
} ataErrorNames[] =
   {
      0x80 , "BBK:ICRC " ,
      0x40 , "UNC "      ,
      0x20 , "MC "       ,
      0x10 , "IDNF "     ,
      0x08 , "MCR "      ,
      0x04 , "ABRT "     ,
      0x02 , "TK0NF "    ,
      0x01 , "AMNF "
   } ;

static unsigned char ataErrorNameBuf[48];

unsigned char * trc_get_er_bit_name( unsigned char er )

{
   int ndx;

   * ataErrorNameBuf = 0;
   for ( ndx = 0; ndx < 8; ndx ++ )
   {
      if ( er & ataErrorNames[ndx].bitPos )
         strcat( ataErrorNameBuf, ataErrorNames[ndx].bitName );
   }
   return ataErrorNameBuf;
}

//**************************************************************

// error name lookup table and lookup function

static struct
{
   int errCode;
   unsigned char * errName;
} errNames[] =
   {
       1 ,  "Soft Reset timed out polling for device 0 to set BSY=0"  ,
       2 ,  "Soft Reset timed out polling device 1"                   ,
       3 ,  "Soft Reset timed out polling for device 1 to set BSY=0"  ,

      11 ,  "Device selection timed out polling for BSY=0"            ,
      12 ,  "Device selection timed out polling for RDY=1"            ,

      21 ,  "Non-Data command ended with bad status"                  ,
      22 ,  "Non-Data command timed out waiting for an interrupt"     ,
      23 ,  "Non-Data command timed out polling for BSY=0"            ,
      24 ,  "Exec Dev Diag command timed out polling device 1"        ,

      31 ,  "PIO Data In command terminated by error status"          ,
      32 ,  "Device should be ready to transfer data but DRQ=0"       ,
      33 ,  "PIO Data In command ended with bad status"               ,
      34 ,  "PIO Data In command timed out waiting for an interrupt"  ,
      35 ,  "PIO Data In command timed out polling for BSY=0"         ,

      41 ,  "PIO Data Out command terminated by error status"         ,
      42 ,  "Device should be ready to transfer data but DRQ=0"       ,
      43 ,  "PIO Data Out command ended with bad status"              ,
      44 ,  "PIO Data Out command timed out waiting for an interrupt" ,
      45 ,  "PIO Data Out command timed out polling for BSY=0"        ,
      46 ,  "Extra interrupt at start of a PIO Data Out command"      ,
      47 ,  "PIO Data Out command timed out polling for BSY=0"        ,

      51 ,  "Timeout waiting for BSY=0/DRQ=1 for cmd packet transfer" ,
      52 ,  "Bad status at command packet transfer time"              ,
      53 ,  "Timeout waiting for interrupt for data packet transfer"  ,
      54 ,  "Timeout polling for BSY=0/DRQ=1 for a data packet"       ,
      55 ,  "Bad status at data packet transfer time"                 ,
      56 ,  "Timout waiting for final interrupt at end of command"    ,
      57 ,  "Timeout polling for final BSY=0 at end of command"       ,
      58 ,  "Bad status at end of command"                            ,
      59 ,  "Buffer overrun (host buffer too small)"                  ,
      60 ,  "Byte count for data packet is zero"                      ,

      70 ,  "No DMA channel is setup"                                 ,
      71 ,  "End of command without complete data transfer"           ,
      72 ,  "Timeout waiting for 1st transfer to complete"            ,
      73 ,  "Timeout waiting for command to complete"                 ,
      74 ,  "Bad status at end of command"                            ,
      75 ,  "Timeout waiting for BSY=0/DRQ=1 for cmd packet transfer" ,
      76 ,  "Bad status at command packet transfer time"              ,
      77 ,  "ATA command code is not C8H or CAH"                      ,

      80 ,  "No tag available now"                                    ,
      81 ,  "Timeout polling for SERV=1"                              ,

      0  ,  ""                      // end of table
   } ;

unsigned char * trc_get_err_name( int ec )

{
   int ndx = 0;

   while ( * errNames[ndx].errName )
   {
      if ( ec == errNames[ndx].errCode )
         return errNames[ndx].errName;
      ndx ++ ;
   }
   return "";
}

//**************************************************************

static struct
{
   unsigned int pErrCode;
   unsigned char * pErrName;
} pErrNames[] =
   {
      FAILBIT0  , "slow setting BSY=1 or DRQ=1 after A0 cmd"   ,
      FAILBIT1  , "got interrupt before cmd packet xfer"       ,
      FAILBIT2  , "SC wrong at cmd packet xfer time"           ,
      FAILBIT3  , "byte count wrong at cmd packet xfer time"   ,
      FAILBIT4  , "SC (CD bit) wrong at data packet xfer time" ,
      FAILBIT5  , "SC (IO bit) wrong at data packet xfer time" ,
      FAILBIT6  , "byte count wrong at data packet xfer time"  ,
      FAILBIT7  , "byte count odd at data packet xfer time"    ,
      FAILBIT8  , "SC (CD and IO bits) wrong at end of cmd"    ,
      FAILBIT9  , "fail bit 9"                                 ,
      FAILBIT10 , "fail bit 10"                                ,
      FAILBIT11 , "fail bit 11"                                ,
      FAILBIT12 , "fail bit 12"                                ,
      FAILBIT13 , "fail bit 13"                                ,
      FAILBIT14 , "fail bit 14"                                ,
      FAILBIT15 , "extra interrupts detected"
   } ;

//**************************************************************

// command or reset error display data

static int errDmpLine = 0;
static int errDmpLine2 = 0;

//**************************************************************

// start the display of a command or reset error display

void trc_err_dump1( void )

{

   errDmpLine = 1;
   errDmpLine2 = 0;
}

//**************************************************************

// return one line of a command or reset error display,
// returns NULL at end

unsigned char * trc_err_dump2( void )

{

   if ( reg_cmd_info.flg == TRC_FLAG_EMPTY )
      return NULL;
   if ( errDmpLine == 1 )
   {
      errDmpLine = 2;
      if ( reg_cmd_info.flg == TRC_FLAG_SRST )
         sprintf( trcDmpBuf, "  Command Code: -- %s ",
                             trc_get_cmd_name( TRC_FLAG_SRST, 0 ) );
      else
         sprintf( trcDmpBuf, "  Command Code: %02X = %s ",
                             reg_cmd_info.cmd,
                             trc_get_cmd_name( TRC_FLAG_CMD, reg_cmd_info.cmd ) );
      return trcDmpBuf;
   }
   if ( errDmpLine == 2 )
   {
      errDmpLine = 3;

⌨️ 快捷键说明

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