Home | History | Annotate | Download | only in AtapiPassThruDxe
      1 /** @file
      2   Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.<BR>
      3   This program and the accompanying materials
      4   are licensed and made available under the terms and conditions of the BSD License
      5   which accompanies this distribution.  The full text of the license may be found at
      6   http://opensource.org/licenses/bsd-license.php
      7 
      8   THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
      9   WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
     10 
     11   Module Name:  AtapiPassThru.h
     12 
     13 **/
     14 
     15 #ifndef _APT_H
     16 #define _APT_H
     17 
     18 
     19 
     20 #include <Uefi.h>
     21 
     22 #include <Protocol/ScsiPassThru.h>
     23 #include <Protocol/ScsiPassThruExt.h>
     24 #include <Protocol/PciIo.h>
     25 #include <Protocol/DriverSupportedEfiVersion.h>
     26 
     27 #include <Library/DebugLib.h>
     28 #include <Library/UefiDriverEntryPoint.h>
     29 #include <Library/BaseLib.h>
     30 #include <Library/UefiLib.h>
     31 #include <Library/BaseMemoryLib.h>
     32 #include <Library/MemoryAllocationLib.h>
     33 #include <Library/UefiBootServicesTableLib.h>
     34 #include <Library/PcdLib.h>
     35 #include <Library/DevicePathLib.h>
     36 
     37 #include <IndustryStandard/Pci.h>
     38 
     39 #define MAX_TARGET_ID 4
     40 
     41 //
     42 // IDE Registers
     43 //
     44 typedef union {
     45   UINT16  Command;        /* when write */
     46   UINT16  Status;         /* when read */
     47 } IDE_CMD_OR_STATUS;
     48 
     49 typedef union {
     50   UINT16  Error;          /* when read */
     51   UINT16  Feature;        /* when write */
     52 } IDE_ERROR_OR_FEATURE;
     53 
     54 typedef union {
     55   UINT16  AltStatus;      /* when read */
     56   UINT16  DeviceControl;  /* when write */
     57 } IDE_AltStatus_OR_DeviceControl;
     58 
     59 
     60 typedef enum {
     61   IdePrimary    = 0,
     62   IdeSecondary  = 1,
     63   IdeMaxChannel = 2
     64 } EFI_IDE_CHANNEL;
     65 
     66 ///
     67 
     68 
     69 //
     70 // Bit definitions in Programming Interface byte of the Class Code field
     71 // in PCI IDE controller's Configuration Space
     72 //
     73 #define IDE_PRIMARY_OPERATING_MODE            BIT0
     74 #define IDE_PRIMARY_PROGRAMMABLE_INDICATOR    BIT1
     75 #define IDE_SECONDARY_OPERATING_MODE          BIT2
     76 #define IDE_SECONDARY_PROGRAMMABLE_INDICATOR  BIT3
     77 
     78 
     79 #define ATAPI_MAX_CHANNEL 2
     80 
     81 ///
     82 /// IDE registers set
     83 ///
     84 typedef struct {
     85   UINT16                          Data;
     86   IDE_ERROR_OR_FEATURE            Reg1;
     87   UINT16                          SectorCount;
     88   UINT16                          SectorNumber;
     89   UINT16                          CylinderLsb;
     90   UINT16                          CylinderMsb;
     91   UINT16                          Head;
     92   IDE_CMD_OR_STATUS               Reg;
     93   IDE_AltStatus_OR_DeviceControl  Alt;
     94   UINT16                          DriveAddress;
     95 } IDE_BASE_REGISTERS;
     96 
     97 #define ATAPI_SCSI_PASS_THRU_DEV_SIGNATURE  SIGNATURE_32 ('a', 's', 'p', 't')
     98 
     99 typedef struct {
    100   UINTN                            Signature;
    101   EFI_HANDLE                       Handle;
    102   EFI_SCSI_PASS_THRU_PROTOCOL      ScsiPassThru;
    103   EFI_EXT_SCSI_PASS_THRU_PROTOCOL  ExtScsiPassThru;
    104   EFI_PCI_IO_PROTOCOL              *PciIo;
    105   UINT64                           OriginalPciAttributes;
    106   //
    107   // Local Data goes here
    108   //
    109   IDE_BASE_REGISTERS               *IoPort;
    110   IDE_BASE_REGISTERS               AtapiIoPortRegisters[2];
    111   UINT32                           LatestTargetId;
    112   UINT64                           LatestLun;
    113 } ATAPI_SCSI_PASS_THRU_DEV;
    114 
    115 //
    116 // IDE registers' base addresses
    117 //
    118 typedef struct {
    119   UINT16  CommandBlockBaseAddr;
    120   UINT16  ControlBlockBaseAddr;
    121 } IDE_REGISTERS_BASE_ADDR;
    122 
    123 #define ATAPI_SCSI_PASS_THRU_DEV_FROM_THIS(a) \
    124   CR (a, \
    125       ATAPI_SCSI_PASS_THRU_DEV, \
    126       ScsiPassThru, \
    127       ATAPI_SCSI_PASS_THRU_DEV_SIGNATURE \
    128       )
    129 
    130 #define ATAPI_EXT_SCSI_PASS_THRU_DEV_FROM_THIS(a) \
    131   CR (a, \
    132       ATAPI_SCSI_PASS_THRU_DEV, \
    133       ExtScsiPassThru, \
    134       ATAPI_SCSI_PASS_THRU_DEV_SIGNATURE \
    135       )
    136 
    137 //
    138 // Global Variables
    139 //
    140 extern EFI_DRIVER_BINDING_PROTOCOL                gAtapiScsiPassThruDriverBinding;
    141 extern EFI_COMPONENT_NAME_PROTOCOL                gAtapiScsiPassThruComponentName;
    142 extern EFI_COMPONENT_NAME2_PROTOCOL               gAtapiScsiPassThruComponentName2;
    143 extern EFI_DRIVER_SUPPORTED_EFI_VERSION_PROTOCOL  gAtapiScsiPassThruDriverSupportedEfiVersion;
    144 
    145 //
    146 // ATAPI Command op code
    147 //
    148 #define OP_INQUIRY                      0x12
    149 #define OP_LOAD_UNLOAD_CD               0xa6
    150 #define OP_MECHANISM_STATUS             0xbd
    151 #define OP_MODE_SELECT_10               0x55
    152 #define OP_MODE_SENSE_10                0x5a
    153 #define OP_PAUSE_RESUME                 0x4b
    154 #define OP_PLAY_AUDIO_10                0x45
    155 #define OP_PLAY_AUDIO_MSF               0x47
    156 #define OP_PLAY_CD                      0xbc
    157 #define OP_PLAY_CD_MSF                  0xb4
    158 #define OP_PREVENT_ALLOW_MEDIUM_REMOVAL 0x1e
    159 #define OP_READ_10                      0x28
    160 #define OP_READ_12                      0xa8
    161 #define OP_READ_CAPACITY                0x25
    162 #define OP_READ_CD                      0xbe
    163 #define OP_READ_CD_MSF                  0xb9
    164 #define OP_READ_HEADER                  0x44
    165 #define OP_READ_SUB_CHANNEL             0x42
    166 #define OP_READ_TOC                     0x43
    167 #define OP_REQUEST_SENSE                0x03
    168 #define OP_SCAN                         0xba
    169 #define OP_SEEK_10                      0x2b
    170 #define OP_SET_CD_SPEED                 0xbb
    171 #define OP_STOPPLAY_SCAN                0x4e
    172 #define OP_START_STOP_UNIT              0x1b
    173 #define OP_TEST_UNIT_READY              0x00
    174 
    175 #define OP_FORMAT_UNIT                  0x04
    176 #define OP_READ_FORMAT_CAPACITIES       0x23
    177 #define OP_VERIFY                       0x2f
    178 #define OP_WRITE_10                     0x2a
    179 #define OP_WRITE_12                     0xaa
    180 #define OP_WRITE_AND_VERIFY             0x2e
    181 
    182 //
    183 // ATA Command
    184 //
    185 #define ATAPI_SOFT_RESET_CMD  0x08
    186 
    187 typedef enum {
    188   DataIn  = 0,
    189   DataOut = 1,
    190   DataBi  = 2,
    191   NoData  = 3,
    192   End     = 0xff
    193 } DATA_DIRECTION;
    194 
    195 typedef struct {
    196   UINT8           OpCode;
    197   DATA_DIRECTION  Direction;
    198 } SCSI_COMMAND_SET;
    199 
    200 #define MAX_CHANNEL         2
    201 
    202 #define ValidCdbLength(Len) ((Len) == 6 || (Len) == 10 || (Len) == 12) ? 1 : 0
    203 
    204 //
    205 // IDE registers bit definitions
    206 //
    207 // ATA Err Reg bitmap
    208 //
    209 #define BBK_ERR   BIT7 ///< Bad block detected
    210 #define UNC_ERR   BIT6 ///< Uncorrectable Data
    211 #define MC_ERR    BIT5 ///< Media Change
    212 #define IDNF_ERR  BIT4 ///< ID Not Found
    213 #define MCR_ERR   BIT3 ///< Media Change Requested
    214 #define ABRT_ERR  BIT2 ///< Aborted Command
    215 #define TK0NF_ERR BIT1 ///< Track 0 Not Found
    216 #define AMNF_ERR  BIT0 ///< Address Mark Not Found
    217 
    218 //
    219 // ATAPI Err Reg bitmap
    220 //
    221 #define SENSE_KEY_ERR (BIT7 | BIT6 | BIT5 | BIT4)
    222 #define EOM_ERR BIT1 ///< End of Media Detected
    223 #define ILI_ERR BIT0 ///< Illegal Length Indication
    224 
    225 //
    226 // Device/Head Reg
    227 //
    228 #define LBA_MODE  BIT6
    229 #define DEV       BIT4
    230 #define HS3       BIT3
    231 #define HS2       BIT2
    232 #define HS1       BIT1
    233 #define HS0       BIT0
    234 #define CHS_MODE  (0)
    235 #define DRV0      (0)
    236 #define DRV1      (1)
    237 #define MST_DRV   DRV0
    238 #define SLV_DRV   DRV1
    239 
    240 //
    241 // Status Reg
    242 //
    243 #define BSY   BIT7 ///< Controller Busy
    244 #define DRDY  BIT6 ///< Drive Ready
    245 #define DWF   BIT5 ///< Drive Write Fault
    246 #define DSC   BIT4 ///< Disk Seek Complete
    247 #define DRQ   BIT3 ///< Data Request
    248 #define CORR  BIT2 ///< Corrected Data
    249 #define IDX   BIT1 ///< Index
    250 #define ERR   BIT0 ///< Error
    251 #define CHECK BIT0 ///< Check bit for ATAPI Status Reg
    252 
    253 //
    254 // Device Control Reg
    255 //
    256 #define SRST  BIT2 ///< Software Reset
    257 #define IEN_L BIT1 ///< Interrupt Enable
    258 
    259 //
    260 // ATAPI Feature Register
    261 //
    262 #define OVERLAP BIT1
    263 #define DMA     BIT0
    264 
    265 //
    266 // ATAPI Interrupt Reason Reson Reg (ATA Sector Count Register)
    267 //
    268 #define RELEASE     BIT2
    269 #define IO          BIT1
    270 #define CoD         BIT0
    271 
    272 #define PACKET_CMD  0xA0
    273 
    274 #define DEFAULT_CMD (0xa0)
    275 //
    276 // default content of device control register, disable INT
    277 //
    278 #define DEFAULT_CTL           (0x0a)
    279 #define MAX_ATAPI_BYTE_COUNT  (0xfffe)
    280 
    281 //
    282 // function prototype
    283 //
    284 
    285 EFI_STATUS
    286 EFIAPI
    287 AtapiScsiPassThruDriverBindingSupported (
    288   IN EFI_DRIVER_BINDING_PROTOCOL  *This,
    289   IN EFI_HANDLE                   Controller,
    290   IN EFI_DEVICE_PATH_PROTOCOL     *RemainingDevicePath
    291   );
    292 
    293 EFI_STATUS
    294 EFIAPI
    295 AtapiScsiPassThruDriverBindingStart (
    296   IN EFI_DRIVER_BINDING_PROTOCOL  *This,
    297   IN EFI_HANDLE                   Controller,
    298   IN EFI_DEVICE_PATH_PROTOCOL     *RemainingDevicePath
    299   );
    300 
    301 EFI_STATUS
    302 EFIAPI
    303 AtapiScsiPassThruDriverBindingStop (
    304   IN  EFI_DRIVER_BINDING_PROTOCOL     *This,
    305   IN  EFI_HANDLE                      Controller,
    306   IN  UINTN                           NumberOfChildren,
    307   IN  EFI_HANDLE                      *ChildHandleBuffer
    308   );
    309 
    310 //
    311 // EFI Component Name Functions
    312 //
    313 /**
    314   Retrieves a Unicode string that is the user readable name of the driver.
    315 
    316   This function retrieves the user readable name of a driver in the form of a
    317   Unicode string. If the driver specified by This has a user readable name in
    318   the language specified by Language, then a pointer to the driver name is
    319   returned in DriverName, and EFI_SUCCESS is returned. If the driver specified
    320   by This does not support the language specified by Language,
    321   then EFI_UNSUPPORTED is returned.
    322 
    323   @param  This[in]              A pointer to the EFI_COMPONENT_NAME2_PROTOCOL or
    324                                 EFI_COMPONENT_NAME_PROTOCOL instance.
    325 
    326   @param  Language[in]          A pointer to a Null-terminated ASCII string
    327                                 array indicating the language. This is the
    328                                 language of the driver name that the caller is
    329                                 requesting, and it must match one of the
    330                                 languages specified in SupportedLanguages. The
    331                                 number of languages supported by a driver is up
    332                                 to the driver writer. Language is specified
    333                                 in RFC 4646 or ISO 639-2 language code format.
    334 
    335   @param  DriverName[out]       A pointer to the Unicode string to return.
    336                                 This Unicode string is the name of the
    337                                 driver specified by This in the language
    338                                 specified by Language.
    339 
    340   @retval EFI_SUCCESS           The Unicode string for the Driver specified by
    341                                 This and the language specified by Language was
    342                                 returned in DriverName.
    343 
    344   @retval EFI_INVALID_PARAMETER Language is NULL.
    345 
    346   @retval EFI_INVALID_PARAMETER DriverName is NULL.
    347 
    348   @retval EFI_UNSUPPORTED       The driver specified by This does not support
    349                                 the language specified by Language.
    350 
    351 **/
    352 EFI_STATUS
    353 EFIAPI
    354 AtapiScsiPassThruComponentNameGetDriverName (
    355   IN  EFI_COMPONENT_NAME_PROTOCOL  *This,
    356   IN  CHAR8                        *Language,
    357   OUT CHAR16                       **DriverName
    358   );
    359 
    360 
    361 /**
    362   Retrieves a Unicode string that is the user readable name of the controller
    363   that is being managed by a driver.
    364 
    365   This function retrieves the user readable name of the controller specified by
    366   ControllerHandle and ChildHandle in the form of a Unicode string. If the
    367   driver specified by This has a user readable name in the language specified by
    368   Language, then a pointer to the controller name is returned in ControllerName,
    369   and EFI_SUCCESS is returned.  If the driver specified by This is not currently
    370   managing the controller specified by ControllerHandle and ChildHandle,
    371   then EFI_UNSUPPORTED is returned.  If the driver specified by This does not
    372   support the language specified by Language, then EFI_UNSUPPORTED is returned.
    373 
    374   @param  This[in]              A pointer to the EFI_COMPONENT_NAME2_PROTOCOL or
    375                                 EFI_COMPONENT_NAME_PROTOCOL instance.
    376 
    377   @param  ControllerHandle[in]  The handle of a controller that the driver
    378                                 specified by This is managing.  This handle
    379                                 specifies the controller whose name is to be
    380                                 returned.
    381 
    382   @param  ChildHandle[in]       The handle of the child controller to retrieve
    383                                 the name of.  This is an optional parameter that
    384                                 may be NULL.  It will be NULL for device
    385                                 drivers.  It will also be NULL for a bus drivers
    386                                 that wish to retrieve the name of the bus
    387                                 controller.  It will not be NULL for a bus
    388                                 driver that wishes to retrieve the name of a
    389                                 child controller.
    390 
    391   @param  Language[in]          A pointer to a Null-terminated ASCII string
    392                                 array indicating the language.  This is the
    393                                 language of the driver name that the caller is
    394                                 requesting, and it must match one of the
    395                                 languages specified in SupportedLanguages. The
    396                                 number of languages supported by a driver is up
    397                                 to the driver writer. Language is specified in
    398                                 RFC 4646 or ISO 639-2 language code format.
    399 
    400   @param  ControllerName[out]   A pointer to the Unicode string to return.
    401                                 This Unicode string is the name of the
    402                                 controller specified by ControllerHandle and
    403                                 ChildHandle in the language specified by
    404                                 Language from the point of view of the driver
    405                                 specified by This.
    406 
    407   @retval EFI_SUCCESS           The Unicode string for the user readable name in
    408                                 the language specified by Language for the
    409                                 driver specified by This was returned in
    410                                 DriverName.
    411 
    412   @retval EFI_INVALID_PARAMETER ControllerHandle is NULL.
    413 
    414   @retval EFI_INVALID_PARAMETER ChildHandle is not NULL and it is not a valid
    415                                 EFI_HANDLE.
    416 
    417   @retval EFI_INVALID_PARAMETER Language is NULL.
    418 
    419   @retval EFI_INVALID_PARAMETER ControllerName is NULL.
    420 
    421   @retval EFI_UNSUPPORTED       The driver specified by This is not currently
    422                                 managing the controller specified by
    423                                 ControllerHandle and ChildHandle.
    424 
    425   @retval EFI_UNSUPPORTED       The driver specified by This does not support
    426                                 the language specified by Language.
    427 
    428 **/
    429 EFI_STATUS
    430 EFIAPI
    431 AtapiScsiPassThruComponentNameGetControllerName (
    432   IN  EFI_COMPONENT_NAME_PROTOCOL                     *This,
    433   IN  EFI_HANDLE                                      ControllerHandle,
    434   IN  EFI_HANDLE                                      ChildHandle        OPTIONAL,
    435   IN  CHAR8                                           *Language,
    436   OUT CHAR16                                          **ControllerName
    437   );
    438 
    439 
    440 EFI_STATUS
    441 EFIAPI
    442 AtapiScsiPassThruDriverEntryPoint (
    443   IN EFI_HANDLE         ImageHandle,
    444   IN EFI_SYSTEM_TABLE   *SystemTable
    445   )
    446  /*++
    447 
    448 Routine Description:
    449 
    450   Entry point for EFI drivers.
    451 
    452 Arguments:
    453 
    454   ImageHandle - EFI_HANDLE
    455   SystemTable - EFI_SYSTEM_TABLE
    456 
    457 Returns:
    458 
    459   EFI_SUCCESS
    460   Others
    461 
    462 --*/
    463 ;
    464 
    465 EFI_STATUS
    466 RegisterAtapiScsiPassThru (
    467   IN  EFI_DRIVER_BINDING_PROTOCOL *This,
    468   IN  EFI_HANDLE                  Controller,
    469   IN  EFI_PCI_IO_PROTOCOL         *PciIo,
    470   IN  UINT64                      OriginalPciAttributes
    471   )
    472 /*++
    473 
    474 Routine Description:
    475   Attaches SCSI Pass Thru Protocol for specified IDE channel.
    476 
    477 Arguments:
    478   This              - Protocol instance pointer.
    479   Controller        - Parent device handle to the IDE channel.
    480   PciIo             - PCI I/O protocol attached on the "Controller".
    481 
    482 Returns:
    483   Always return EFI_SUCCESS unless installing SCSI Pass Thru Protocol failed.
    484 
    485 --*/
    486 ;
    487 
    488 EFI_STATUS
    489 EFIAPI
    490 AtapiScsiPassThruFunction (
    491   IN EFI_SCSI_PASS_THRU_PROTOCOL                        *This,
    492   IN UINT32                                             Target,
    493   IN UINT64                                             Lun,
    494   IN OUT EFI_SCSI_PASS_THRU_SCSI_REQUEST_PACKET         *Packet,
    495   IN EFI_EVENT                                          Event OPTIONAL
    496   )
    497 /*++
    498 
    499 Routine Description:
    500 
    501   Implements EFI_SCSI_PASS_THRU_PROTOCOL.PassThru() function.
    502 
    503 Arguments:
    504 
    505   This:     The EFI_SCSI_PASS_THRU_PROTOCOL instance.
    506   Target:   The Target ID of the ATAPI device to send the SCSI
    507             Request Packet. To ATAPI devices attached on an IDE
    508             Channel, Target ID 0 indicates Master device;Target
    509             ID 1 indicates Slave device.
    510   Lun:      The LUN of the ATAPI device to send the SCSI Request
    511             Packet. To the ATAPI device, Lun is always 0.
    512   Packet:   The SCSI Request Packet to send to the ATAPI device
    513             specified by Target and Lun.
    514   Event:    If non-blocking I/O is not supported then Event is ignored,
    515             and blocking I/O is performed.
    516             If Event is NULL, then blocking I/O is performed.
    517             If Event is not NULL and non blocking I/O is supported,
    518             then non-blocking I/O is performed, and Event will be signaled
    519             when the SCSI Request Packet completes.
    520 
    521 Returns:
    522 
    523    EFI_STATUS
    524 
    525 --*/
    526 ;
    527 
    528 EFI_STATUS
    529 EFIAPI
    530 AtapiScsiPassThruGetNextDevice (
    531   IN  EFI_SCSI_PASS_THRU_PROTOCOL    *This,
    532   IN OUT UINT32                      *Target,
    533   IN OUT UINT64                      *Lun
    534   )
    535 /*++
    536 
    537 Routine Description:
    538 
    539   Used to retrieve the list of legal Target IDs for SCSI devices
    540   on a SCSI channel.
    541 
    542 Arguments:
    543 
    544   This                  - Protocol instance pointer.
    545   Target                - On input, a pointer to the Target ID of a SCSI
    546                           device present on the SCSI channel.  On output,
    547                           a pointer to the Target ID of the next SCSI device
    548                           present on a SCSI channel.  An input value of
    549                           0xFFFFFFFF retrieves the Target ID of the first
    550                           SCSI device present on a SCSI channel.
    551   Lun                   - On input, a pointer to the LUN of a SCSI device
    552                           present on the SCSI channel. On output, a pointer
    553                           to the LUN of the next SCSI device present on
    554                           a SCSI channel.
    555 Returns:
    556 
    557   EFI_SUCCESS           - The Target ID and Lun of the next SCSI device
    558                           on the SCSI channel was returned in Target and Lun.
    559   EFI_NOT_FOUND         - There are no more SCSI devices on this SCSI channel.
    560   EFI_INVALID_PARAMETER - Target is not 0xFFFFFFFF,and Target and Lun were not
    561                            returned on a previous call to GetNextDevice().
    562 
    563 --*/
    564 ;
    565 
    566 EFI_STATUS
    567 EFIAPI
    568 AtapiScsiPassThruBuildDevicePath (
    569   IN     EFI_SCSI_PASS_THRU_PROTOCOL    *This,
    570   IN     UINT32                         Target,
    571   IN     UINT64                         Lun,
    572   IN OUT EFI_DEVICE_PATH_PROTOCOL       **DevicePath
    573   )
    574 /*++
    575 
    576 Routine Description:
    577 
    578   Used to allocate and build a device path node for a SCSI device
    579   on a SCSI channel. Would not build device path for a SCSI Host Controller.
    580 
    581 Arguments:
    582 
    583   This                  - Protocol instance pointer.
    584   Target                - The Target ID of the SCSI device for which
    585                           a device path node is to be allocated and built.
    586   Lun                   - The LUN of the SCSI device for which a device
    587                           path node is to be allocated and built.
    588   DevicePath            - A pointer to a single device path node that
    589                           describes the SCSI device specified by
    590                           Target and Lun. This function is responsible
    591                           for allocating the buffer DevicePath with the boot
    592                           service AllocatePool().  It is the caller's
    593                           responsibility to free DevicePath when the caller
    594                           is finished with DevicePath.
    595   Returns:
    596   EFI_SUCCESS           - The device path node that describes the SCSI device
    597                           specified by Target and Lun was allocated and
    598                           returned in DevicePath.
    599   EFI_NOT_FOUND         - The SCSI devices specified by Target and Lun does
    600                           not exist on the SCSI channel.
    601   EFI_INVALID_PARAMETER - DevicePath is NULL.
    602   EFI_OUT_OF_RESOURCES  - There are not enough resources to allocate
    603                           DevicePath.
    604 
    605 --*/
    606 ;
    607 
    608 EFI_STATUS
    609 EFIAPI
    610 AtapiScsiPassThruGetTargetLun (
    611   IN  EFI_SCSI_PASS_THRU_PROTOCOL    *This,
    612   IN  EFI_DEVICE_PATH_PROTOCOL       *DevicePath,
    613   OUT UINT32                         *Target,
    614   OUT UINT64                         *Lun
    615   )
    616 /*++
    617 
    618 Routine Description:
    619 
    620   Used to translate a device path node to a Target ID and LUN.
    621 
    622 Arguments:
    623 
    624   This                  - Protocol instance pointer.
    625   DevicePath            - A pointer to the device path node that
    626                           describes a SCSI device on the SCSI channel.
    627   Target                - A pointer to the Target ID of a SCSI device
    628                           on the SCSI channel.
    629   Lun                   - A pointer to the LUN of a SCSI device on
    630                           the SCSI channel.
    631 Returns:
    632 
    633   EFI_SUCCESS           - DevicePath was successfully translated to a
    634                           Target ID and LUN, and they were returned
    635                           in Target and Lun.
    636   EFI_INVALID_PARAMETER - DevicePath/Target/Lun is NULL.
    637   EFI_UNSUPPORTED       - This driver does not support the device path
    638                           node type in DevicePath.
    639   EFI_NOT_FOUND         - A valid translation from DevicePath to a
    640                           Target ID and LUN does not exist.
    641 
    642 --*/
    643 ;
    644 
    645 EFI_STATUS
    646 EFIAPI
    647 AtapiScsiPassThruResetChannel (
    648   IN  EFI_SCSI_PASS_THRU_PROTOCOL   *This
    649   )
    650 /*++
    651 
    652 Routine Description:
    653 
    654   Resets a SCSI channel.This operation resets all the
    655   SCSI devices connected to the SCSI channel.
    656 
    657 Arguments:
    658 
    659   This                  - Protocol instance pointer.
    660 
    661 Returns:
    662 
    663   EFI_SUCCESS           - The SCSI channel was reset.
    664   EFI_UNSUPPORTED       - The SCSI channel does not support
    665                           a channel reset operation.
    666   EFI_DEVICE_ERROR      - A device error occurred while
    667                           attempting to reset the SCSI channel.
    668   EFI_TIMEOUT           - A timeout occurred while attempting
    669                           to reset the SCSI channel.
    670 
    671 --*/
    672 ;
    673 
    674 EFI_STATUS
    675 EFIAPI
    676 AtapiScsiPassThruResetTarget (
    677   IN EFI_SCSI_PASS_THRU_PROTOCOL    *This,
    678   IN UINT32                         Target,
    679   IN UINT64                         Lun
    680   )
    681 /*++
    682 
    683 Routine Description:
    684 
    685   Resets a SCSI device that is connected to a SCSI channel.
    686 
    687 Arguments:
    688 
    689   This                  - Protocol instance pointer.
    690   Target                - The Target ID of the SCSI device to reset.
    691   Lun                   - The LUN of the SCSI device to reset.
    692 
    693 Returns:
    694 
    695   EFI_SUCCESS           - The SCSI device specified by Target and
    696                           Lun was reset.
    697   EFI_UNSUPPORTED       - The SCSI channel does not support a target
    698                           reset operation.
    699   EFI_INVALID_PARAMETER - Target or Lun are invalid.
    700   EFI_DEVICE_ERROR      - A device error occurred while attempting
    701                           to reset the SCSI device specified by Target
    702                           and Lun.
    703   EFI_TIMEOUT           - A timeout occurred while attempting to reset
    704                           the SCSI device specified by Target and Lun.
    705 
    706 --*/
    707 ;
    708 
    709 EFI_STATUS
    710 EFIAPI
    711 AtapiExtScsiPassThruFunction (
    712   IN EFI_EXT_SCSI_PASS_THRU_PROTOCOL                    *This,
    713   IN UINT8                                              *Target,
    714   IN UINT64                                             Lun,
    715   IN OUT EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET     *Packet,
    716   IN EFI_EVENT                                          Event OPTIONAL
    717   )
    718 /*++
    719 
    720 Routine Description:
    721 
    722   Implements EFI_EXT_SCSI_PASS_THRU_PROTOCOL.PassThru() function.
    723 
    724 Arguments:
    725 
    726   This:     The EFI_EXT_SCSI_PASS_THRU_PROTOCOL instance.
    727   Target:   The Target ID of the ATAPI device to send the SCSI
    728             Request Packet. To ATAPI devices attached on an IDE
    729             Channel, Target ID 0 indicates Master device;Target
    730             ID 1 indicates Slave device.
    731   Lun:      The LUN of the ATAPI device to send the SCSI Request
    732             Packet. To the ATAPI device, Lun is always 0.
    733   Packet:   The SCSI Request Packet to send to the ATAPI device
    734             specified by Target and Lun.
    735   Event:    If non-blocking I/O is not supported then Event is ignored,
    736             and blocking I/O is performed.
    737             If Event is NULL, then blocking I/O is performed.
    738             If Event is not NULL and non blocking I/O is supported,
    739             then non-blocking I/O is performed, and Event will be signaled
    740             when the SCSI Request Packet completes.
    741 
    742 Returns:
    743 
    744   EFI_STATUS
    745 
    746 --*/
    747 ;
    748 
    749 EFI_STATUS
    750 EFIAPI
    751 AtapiExtScsiPassThruGetNextTargetLun (
    752   IN  EFI_EXT_SCSI_PASS_THRU_PROTOCOL    *This,
    753   IN OUT UINT8                           **Target,
    754   IN OUT UINT64                          *Lun
    755   )
    756 /*++
    757 
    758 Routine Description:
    759 
    760   Used to retrieve the list of legal Target IDs for SCSI devices
    761   on a SCSI channel.
    762 
    763 Arguments:
    764 
    765   This                  - Protocol instance pointer.
    766   Target                - On input, a pointer to the Target ID of a SCSI
    767                           device present on the SCSI channel.  On output,
    768                           a pointer to the Target ID of the next SCSI device
    769                           present on a SCSI channel.  An input value of
    770                           0xFFFFFFFF retrieves the Target ID of the first
    771                           SCSI device present on a SCSI channel.
    772   Lun                   - On input, a pointer to the LUN of a SCSI device
    773                           present on the SCSI channel. On output, a pointer
    774                           to the LUN of the next SCSI device present on
    775                           a SCSI channel.
    776 Returns:
    777 
    778   EFI_SUCCESS           - The Target ID and Lun of the next SCSI device
    779                           on the SCSI channel was returned in Target and Lun.
    780   EFI_NOT_FOUND         - There are no more SCSI devices on this SCSI channel.
    781   EFI_INVALID_PARAMETER - Target is not 0xFFFFFFFF,and Target and Lun were not
    782                            returned on a previous call to GetNextDevice().
    783 
    784 --*/
    785 ;
    786 
    787 EFI_STATUS
    788 EFIAPI
    789 AtapiExtScsiPassThruBuildDevicePath (
    790   IN     EFI_EXT_SCSI_PASS_THRU_PROTOCOL    *This,
    791   IN     UINT8                              *Target,
    792   IN     UINT64                             Lun,
    793   IN OUT EFI_DEVICE_PATH_PROTOCOL           **DevicePath
    794   )
    795 /*++
    796 
    797 Routine Description:
    798 
    799   Used to allocate and build a device path node for a SCSI device
    800   on a SCSI channel. Would not build device path for a SCSI Host Controller.
    801 
    802 Arguments:
    803 
    804   This                  - Protocol instance pointer.
    805   Target                - The Target ID of the SCSI device for which
    806                           a device path node is to be allocated and built.
    807   Lun                   - The LUN of the SCSI device for which a device
    808                           path node is to be allocated and built.
    809   DevicePath            - A pointer to a single device path node that
    810                           describes the SCSI device specified by
    811                           Target and Lun. This function is responsible
    812                           for allocating the buffer DevicePath with the boot
    813                           service AllocatePool().  It is the caller's
    814                           responsibility to free DevicePath when the caller
    815                           is finished with DevicePath.
    816   Returns:
    817   EFI_SUCCESS           - The device path node that describes the SCSI device
    818                           specified by Target and Lun was allocated and
    819                           returned in DevicePath.
    820   EFI_NOT_FOUND         - The SCSI devices specified by Target and Lun does
    821                           not exist on the SCSI channel.
    822   EFI_INVALID_PARAMETER - DevicePath is NULL.
    823   EFI_OUT_OF_RESOURCES  - There are not enough resources to allocate
    824                           DevicePath.
    825 
    826 --*/
    827 ;
    828 
    829 EFI_STATUS
    830 EFIAPI
    831 AtapiExtScsiPassThruGetTargetLun (
    832   IN  EFI_EXT_SCSI_PASS_THRU_PROTOCOL    *This,
    833   IN  EFI_DEVICE_PATH_PROTOCOL       *DevicePath,
    834   OUT UINT8                          **Target,
    835   OUT UINT64                         *Lun
    836   )
    837 /*++
    838 
    839 Routine Description:
    840 
    841   Used to translate a device path node to a Target ID and LUN.
    842 
    843 Arguments:
    844 
    845   This                  - Protocol instance pointer.
    846   DevicePath            - A pointer to the device path node that
    847                           describes a SCSI device on the SCSI channel.
    848   Target                - A pointer to the Target ID of a SCSI device
    849                           on the SCSI channel.
    850   Lun                   - A pointer to the LUN of a SCSI device on
    851                           the SCSI channel.
    852 Returns:
    853 
    854   EFI_SUCCESS           - DevicePath was successfully translated to a
    855                           Target ID and LUN, and they were returned
    856                           in Target and Lun.
    857   EFI_INVALID_PARAMETER - DevicePath/Target/Lun is NULL.
    858   EFI_UNSUPPORTED       - This driver does not support the device path
    859                           node type in DevicePath.
    860   EFI_NOT_FOUND         - A valid translation from DevicePath to a
    861                           Target ID and LUN does not exist.
    862 
    863 --*/
    864 ;
    865 
    866 EFI_STATUS
    867 EFIAPI
    868 AtapiExtScsiPassThruResetChannel (
    869   IN  EFI_EXT_SCSI_PASS_THRU_PROTOCOL   *This
    870   )
    871 /*++
    872 
    873 Routine Description:
    874 
    875   Resets a SCSI channel.This operation resets all the
    876   SCSI devices connected to the SCSI channel.
    877 
    878 Arguments:
    879 
    880   This                  - Protocol instance pointer.
    881 
    882 Returns:
    883 
    884   EFI_SUCCESS           - The SCSI channel was reset.
    885   EFI_UNSUPPORTED       - The SCSI channel does not support
    886                           a channel reset operation.
    887   EFI_DEVICE_ERROR      - A device error occurred while
    888                           attempting to reset the SCSI channel.
    889   EFI_TIMEOUT           - A timeout occurred while attempting
    890                           to reset the SCSI channel.
    891 
    892 --*/
    893 ;
    894 
    895 EFI_STATUS
    896 EFIAPI
    897 AtapiExtScsiPassThruResetTarget (
    898   IN EFI_EXT_SCSI_PASS_THRU_PROTOCOL    *This,
    899   IN UINT8                              *Target,
    900   IN UINT64                             Lun
    901   )
    902 /*++
    903 
    904 Routine Description:
    905 
    906   Resets a SCSI device that is connected to a SCSI channel.
    907 
    908 Arguments:
    909 
    910   This                  - Protocol instance pointer.
    911   Target                - The Target ID of the SCSI device to reset.
    912   Lun                   - The LUN of the SCSI device to reset.
    913 
    914 Returns:
    915 
    916   EFI_SUCCESS           - The SCSI device specified by Target and
    917                           Lun was reset.
    918   EFI_UNSUPPORTED       - The SCSI channel does not support a target
    919                           reset operation.
    920   EFI_INVALID_PARAMETER - Target or Lun are invalid.
    921   EFI_DEVICE_ERROR      - A device error occurred while attempting
    922                           to reset the SCSI device specified by Target
    923                           and Lun.
    924   EFI_TIMEOUT           - A timeout occurred while attempting to reset
    925                           the SCSI device specified by Target and Lun.
    926 
    927 --*/
    928 ;
    929 
    930 EFI_STATUS
    931 EFIAPI
    932 AtapiExtScsiPassThruGetNextTarget (
    933   IN  EFI_EXT_SCSI_PASS_THRU_PROTOCOL    *This,
    934   IN OUT UINT8                           **Target
    935   )
    936 /*++
    937 
    938 Routine Description:
    939   Used to retrieve the list of legal Target IDs for SCSI devices
    940   on a SCSI channel.
    941 
    942 Arguments:
    943   This                  - Protocol instance pointer.
    944   Target                - On input, a pointer to the Target ID of a SCSI
    945                           device present on the SCSI channel.  On output,
    946                           a pointer to the Target ID of the next SCSI device
    947                            present on a SCSI channel.  An input value of
    948                            0xFFFFFFFF retrieves the Target ID of the first
    949                            SCSI device present on a SCSI channel.
    950   Lun                   - On input, a pointer to the LUN of a SCSI device
    951                           present on the SCSI channel. On output, a pointer
    952                           to the LUN of the next SCSI device present on
    953                           a SCSI channel.
    954 
    955 Returns:
    956   EFI_SUCCESS           - The Target ID and Lun of the next SCSI device
    957                           on the SCSI channel was returned in Target and Lun.
    958   EFI_NOT_FOUND         - There are no more SCSI devices on this SCSI channel.
    959   EFI_INVALID_PARAMETER - Target is not 0xFFFFFFFF,and Target and Lun were not
    960                           returned on a previous call to GetNextDevice().
    961 
    962 --*/
    963 ;
    964 
    965 EFI_STATUS
    966 CheckSCSIRequestPacket (
    967   EFI_SCSI_PASS_THRU_SCSI_REQUEST_PACKET      *Packet
    968   )
    969 /*++
    970 
    971 Routine Description:
    972 
    973   Checks the parameters in the SCSI Request Packet to make sure
    974   they are valid for a SCSI Pass Thru request.
    975 
    976 Arguments:
    977 
    978   Packet         -  The pointer of EFI_SCSI_PASS_THRU_SCSI_REQUEST_PACKET
    979 
    980 Returns:
    981 
    982   EFI_STATUS
    983 
    984 --*/
    985 ;
    986 
    987 EFI_STATUS
    988 SubmitBlockingIoCommand (
    989   ATAPI_SCSI_PASS_THRU_DEV                  *AtapiScsiPrivate,
    990   UINT32                                    Target,
    991   EFI_SCSI_PASS_THRU_SCSI_REQUEST_PACKET    *Packet
    992   )
    993 /*++
    994 
    995 Routine Description:
    996 
    997   Performs blocking I/O request.
    998 
    999 Arguments:
   1000 
   1001   AtapiScsiPrivate:   Private data structure for the specified channel.
   1002   Target:             The Target ID of the ATAPI device to send the SCSI
   1003                       Request Packet. To ATAPI devices attached on an IDE
   1004                       Channel, Target ID 0 indicates Master device;Target
   1005                       ID 1 indicates Slave device.
   1006   Packet:             The SCSI Request Packet to send to the ATAPI device
   1007                       specified by Target.
   1008 
   1009   Returns:            EFI_STATUS
   1010 
   1011 --*/
   1012 ;
   1013 
   1014 BOOLEAN
   1015 IsCommandValid (
   1016   EFI_SCSI_PASS_THRU_SCSI_REQUEST_PACKET   *Packet
   1017   )
   1018  /*++
   1019 
   1020 Routine Description:
   1021 
   1022   Checks the requested SCSI command:
   1023   Is it supported by this driver?
   1024   Is the Data transfer direction reasonable?
   1025 
   1026 Arguments:
   1027 
   1028   Packet         -  The pointer of EFI_SCSI_PASS_THRU_SCSI_REQUEST_PACKET
   1029 
   1030 Returns:
   1031 
   1032   EFI_STATUS
   1033 
   1034 --*/
   1035 ;
   1036 
   1037 EFI_STATUS
   1038 CheckExtSCSIRequestPacket (
   1039   EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET      *Packet
   1040   )
   1041 /*++
   1042 
   1043 Routine Description:
   1044 
   1045   Checks the parameters in the SCSI Request Packet to make sure
   1046   they are valid for a SCSI Pass Thru request.
   1047 
   1048 Arguments:
   1049 
   1050   Packet       - The pointer of EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET
   1051 
   1052 Returns:
   1053 
   1054   EFI_STATUS
   1055 
   1056 --*/
   1057 ;
   1058 
   1059 
   1060 BOOLEAN
   1061 IsExtCommandValid (
   1062   EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET   *Packet
   1063   )
   1064 /*++
   1065 
   1066 Routine Description:
   1067 
   1068   Checks the requested SCSI command:
   1069   Is it supported by this driver?
   1070   Is the Data transfer direction reasonable?
   1071 
   1072 Arguments:
   1073 
   1074   Packet         -  The pointer of EFI_SCSI_PASS_THRU_SCSI_REQUEST_PACKET
   1075 
   1076 Returns:
   1077 
   1078   EFI_STATUS
   1079 
   1080 --*/
   1081 ;
   1082 
   1083 EFI_STATUS
   1084 SubmitExtBlockingIoCommand (
   1085   ATAPI_SCSI_PASS_THRU_DEV                      *AtapiScsiPrivate,
   1086   UINT8                                         Target,
   1087   EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET    *Packet
   1088   )
   1089 /*++
   1090 
   1091 Routine Description:
   1092 
   1093   Performs blocking I/O request.
   1094 
   1095 Arguments:
   1096 
   1097   AtapiScsiPrivate:   Private data structure for the specified channel.
   1098   Target:             The Target ID of the ATAPI device to send the SCSI
   1099                       Request Packet. To ATAPI devices attached on an IDE
   1100                       Channel, Target ID 0 indicates Master device;Target
   1101                       ID 1 indicates Slave device.
   1102   Packet:             The SCSI Request Packet to send to the ATAPI device
   1103                       specified by Target.
   1104 
   1105   Returns:            EFI_STATUS
   1106 
   1107 --*/
   1108 ;
   1109 
   1110 EFI_STATUS
   1111 RequestSenseCommand (
   1112   ATAPI_SCSI_PASS_THRU_DEV    *AtapiScsiPrivate,
   1113   UINT32                      Target,
   1114   UINT64                      Timeout,
   1115   VOID                        *SenseData,
   1116   UINT8                       *SenseDataLength
   1117   )
   1118 /*++
   1119 
   1120 Routine Description:
   1121 
   1122   Submit request sense command
   1123 
   1124 Arguments:
   1125 
   1126   AtapiScsiPrivate  - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1127   Target            - The target ID
   1128   Timeout           - The time to complete the command
   1129   SenseData         - The buffer to fill in sense data
   1130   SenseDataLength   - The length of buffer
   1131 
   1132 Returns:
   1133 
   1134   EFI_STATUS
   1135 
   1136 --*/
   1137 ;
   1138 
   1139 EFI_STATUS
   1140 AtapiPacketCommand (
   1141   ATAPI_SCSI_PASS_THRU_DEV                  *AtapiScsiPrivate,
   1142   UINT32                                    Target,
   1143   UINT8                                     *PacketCommand,
   1144   VOID                                      *Buffer,
   1145   UINT32                                    *ByteCount,
   1146   DATA_DIRECTION                            Direction,
   1147   UINT64                                    TimeOutInMicroSeconds
   1148   )
   1149 /*++
   1150 
   1151 Routine Description:
   1152 
   1153   Submits ATAPI command packet to the specified ATAPI device.
   1154 
   1155 Arguments:
   1156 
   1157   AtapiScsiPrivate:   Private data structure for the specified channel.
   1158   Target:             The Target ID of the ATAPI device to send the SCSI
   1159                       Request Packet. To ATAPI devices attached on an IDE
   1160                       Channel, Target ID 0 indicates Master device;Target
   1161                       ID 1 indicates Slave device.
   1162   PacketCommand:      Points to the ATAPI command packet.
   1163   Buffer:             Points to the transferred data.
   1164   ByteCount:          When input,indicates the buffer size; when output,
   1165                       indicates the actually transferred data size.
   1166   Direction:          Indicates the data transfer direction.
   1167   TimeoutInMicroSeconds:
   1168                       The timeout, in micro second units, to use for the
   1169                       execution of this ATAPI command.
   1170                       A TimeoutInMicroSeconds value of 0 means that
   1171                       this function will wait indefinitely for the ATAPI
   1172                       command to execute.
   1173                       If TimeoutInMicroSeconds is greater than zero, then
   1174                       this function will return EFI_TIMEOUT if the time
   1175                       required to execute the ATAPI command is greater
   1176                       than TimeoutInMicroSeconds.
   1177 
   1178 Returns:
   1179 
   1180   EFI_STATUS
   1181 
   1182 --*/
   1183 ;
   1184 
   1185 
   1186 UINT8
   1187 ReadPortB (
   1188   IN  EFI_PCI_IO_PROTOCOL   *PciIo,
   1189   IN  UINT16                Port
   1190   )
   1191 /*++
   1192 
   1193 Routine Description:
   1194 
   1195   Read one byte from a specified I/O port.
   1196 
   1197 Arguments:
   1198 
   1199   PciIo      - The pointer of EFI_PCI_IO_PROTOCOL
   1200   Port       - IO port
   1201 
   1202 Returns:
   1203 
   1204   A byte read out
   1205 
   1206 --*/
   1207 ;
   1208 
   1209 
   1210 UINT16
   1211 ReadPortW (
   1212   IN  EFI_PCI_IO_PROTOCOL   *PciIo,
   1213   IN  UINT16                Port
   1214   )
   1215 /*++
   1216 
   1217 Routine Description:
   1218 
   1219   Read one word from a specified I/O port.
   1220 
   1221 Arguments:
   1222 
   1223   PciIo      - The pointer of EFI_PCI_IO_PROTOCOL
   1224   Port       - IO port
   1225 
   1226 Returns:
   1227 
   1228   A word read out
   1229 
   1230 --*/
   1231 ;
   1232 
   1233 
   1234 VOID
   1235 WritePortB (
   1236   IN  EFI_PCI_IO_PROTOCOL   *PciIo,
   1237   IN  UINT16                Port,
   1238   IN  UINT8                 Data
   1239   )
   1240 /*++
   1241 
   1242 Routine Description:
   1243 
   1244   Write one byte to a specified I/O port.
   1245 
   1246 Arguments:
   1247 
   1248   PciIo      - The pointer of EFI_PCI_IO_PROTOCOL
   1249   Port       - IO port
   1250   Data       - The data to write
   1251 
   1252 Returns:
   1253 
   1254   NONE
   1255 
   1256 --*/
   1257 ;
   1258 
   1259 
   1260 VOID
   1261 WritePortW (
   1262   IN  EFI_PCI_IO_PROTOCOL   *PciIo,
   1263   IN  UINT16                Port,
   1264   IN  UINT16                Data
   1265   )
   1266 /*++
   1267 
   1268 Routine Description:
   1269 
   1270   Write one word to a specified I/O port.
   1271 
   1272 Arguments:
   1273 
   1274   PciIo      - The pointer of EFI_PCI_IO_PROTOCOL
   1275   Port       - IO port
   1276   Data       - The data to write
   1277 
   1278 Returns:
   1279 
   1280   NONE
   1281 
   1282 --*/
   1283 ;
   1284 
   1285 EFI_STATUS
   1286 StatusDRQClear (
   1287   ATAPI_SCSI_PASS_THRU_DEV        *AtapiScsiPrivate,
   1288   UINT64                          TimeOutInMicroSeconds
   1289   )
   1290 /*++
   1291 
   1292 Routine Description:
   1293 
   1294   Check whether DRQ is clear in the Status Register. (BSY must also be cleared)
   1295   If TimeoutInMicroSeconds is zero, this routine should wait infinitely for
   1296   DRQ clear. Otherwise, it will return EFI_TIMEOUT when specified time is
   1297   elapsed.
   1298 
   1299 Arguments:
   1300 
   1301   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1302   TimeoutInMicroSeconds       - The time to wait for
   1303 
   1304 Returns:
   1305 
   1306   EFI_STATUS
   1307 
   1308 --*/
   1309 ;
   1310 
   1311 EFI_STATUS
   1312 AltStatusDRQClear (
   1313   ATAPI_SCSI_PASS_THRU_DEV        *AtapiScsiPrivate,
   1314   UINT64                          TimeOutInMicroSeconds
   1315   )
   1316 /*++
   1317 
   1318 Routine Description:
   1319 
   1320   Check whether DRQ is clear in the Alternate Status Register.
   1321   (BSY must also be cleared).If TimeoutInMicroSeconds is zero, this routine should
   1322   wait infinitely for DRQ clear. Otherwise, it will return EFI_TIMEOUT when specified time is
   1323   elapsed.
   1324 
   1325 Arguments:
   1326 
   1327   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1328   TimeoutInMicroSeconds       - The time to wait for
   1329 
   1330 Returns:
   1331 
   1332   EFI_STATUS
   1333 
   1334 --*/
   1335 ;
   1336 
   1337 EFI_STATUS
   1338 StatusDRQReady (
   1339   ATAPI_SCSI_PASS_THRU_DEV        *AtapiScsiPrivate,
   1340   UINT64                          TimeOutInMicroSeconds
   1341   )
   1342 /*++
   1343 
   1344 Routine Description:
   1345 
   1346   Check whether DRQ is ready in the Status Register. (BSY must also be cleared)
   1347   If TimeoutInMicroSeconds is zero, this routine should wait infinitely for
   1348   DRQ ready. Otherwise, it will return EFI_TIMEOUT when specified time is
   1349   elapsed.
   1350 
   1351 Arguments:
   1352 
   1353   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1354   TimeoutInMicroSeconds       - The time to wait for
   1355 
   1356 Returns:
   1357 
   1358   EFI_STATUS
   1359 
   1360 --*/
   1361 ;
   1362 
   1363 EFI_STATUS
   1364 AltStatusDRQReady (
   1365   ATAPI_SCSI_PASS_THRU_DEV        *AtapiScsiPrivate,
   1366   UINT64                          TimeOutInMicroSeconds
   1367   )
   1368 /*++
   1369 
   1370 Routine Description:
   1371 
   1372   Check whether DRQ is ready in the Alternate Status Register.
   1373   (BSY must also be cleared)
   1374   If TimeoutInMicroSeconds is zero, this routine should wait infinitely for
   1375   DRQ ready. Otherwise, it will return EFI_TIMEOUT when specified time is
   1376   elapsed.
   1377 
   1378 Arguments:
   1379 
   1380   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1381   TimeoutInMicroSeconds       - The time to wait for
   1382 
   1383 Returns:
   1384 
   1385   EFI_STATUS
   1386 
   1387 --*/
   1388 ;
   1389 
   1390 EFI_STATUS
   1391 StatusWaitForBSYClear (
   1392   ATAPI_SCSI_PASS_THRU_DEV    *AtapiScsiPrivate,
   1393   UINT64                      TimeoutInMicroSeconds
   1394   )
   1395 /*++
   1396 
   1397 Routine Description:
   1398 
   1399   Check whether BSY is clear in the Status Register.
   1400   If TimeoutInMicroSeconds is zero, this routine should wait infinitely for
   1401   BSY clear. Otherwise, it will return EFI_TIMEOUT when specified time is
   1402   elapsed.
   1403 
   1404 Arguments:
   1405 
   1406   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1407   TimeoutInMicroSeconds       - The time to wait for
   1408 
   1409 Returns:
   1410 
   1411   EFI_STATUS
   1412 
   1413 --*/
   1414 ;
   1415 
   1416 EFI_STATUS
   1417 AltStatusWaitForBSYClear (
   1418   ATAPI_SCSI_PASS_THRU_DEV    *AtapiScsiPrivate,
   1419   UINT64                      TimeoutInMicroSeconds
   1420   )
   1421 /*++
   1422 
   1423 Routine Description:
   1424 
   1425   Check whether BSY is clear in the Alternate Status Register.
   1426   If TimeoutInMicroSeconds is zero, this routine should wait infinitely for
   1427   BSY clear. Otherwise, it will return EFI_TIMEOUT when specified time is
   1428   elapsed.
   1429 
   1430 Arguments:
   1431 
   1432   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1433   TimeoutInMicroSeconds       - The time to wait for
   1434 
   1435 Returns:
   1436 
   1437   EFI_STATUS
   1438 
   1439 --*/
   1440 ;
   1441 
   1442 EFI_STATUS
   1443 StatusDRDYReady (
   1444   ATAPI_SCSI_PASS_THRU_DEV    *AtapiScsiPrivate,
   1445   UINT64                      TimeoutInMicroSeconds
   1446   )
   1447 /*++
   1448 
   1449 Routine Description:
   1450 
   1451   Check whether DRDY is ready in the Status Register.
   1452   (BSY must also be cleared)
   1453   If TimeoutInMicroSeconds is zero, this routine should wait infinitely for
   1454   DRDY ready. Otherwise, it will return EFI_TIMEOUT when specified time is
   1455   elapsed.
   1456 
   1457 Arguments:
   1458 
   1459   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1460   TimeoutInMicroSeconds       - The time to wait for
   1461 
   1462 Returns:
   1463 
   1464   EFI_STATUS
   1465 
   1466 --*/
   1467 ;
   1468 
   1469 EFI_STATUS
   1470 AltStatusDRDYReady (
   1471   ATAPI_SCSI_PASS_THRU_DEV    *AtapiScsiPrivate,
   1472   UINT64                      TimeoutInMicroSeconds
   1473   )
   1474 /*++
   1475 
   1476 Routine Description:
   1477 
   1478   Check whether DRDY is ready in the Alternate Status Register.
   1479   (BSY must also be cleared)
   1480   If TimeoutInMicroSeconds is zero, this routine should wait infinitely for
   1481   DRDY ready. Otherwise, it will return EFI_TIMEOUT when specified time is
   1482   elapsed.
   1483 
   1484 Arguments:
   1485 
   1486   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1487   TimeoutInMicroSeconds       - The time to wait for
   1488 
   1489 Returns:
   1490 
   1491   EFI_STATUS
   1492 
   1493 --*/
   1494 ;
   1495 
   1496 EFI_STATUS
   1497 AtapiPassThruPioReadWriteData (
   1498   ATAPI_SCSI_PASS_THRU_DEV  *AtapiScsiPrivate,
   1499   UINT16                    *Buffer,
   1500   UINT32                    *ByteCount,
   1501   DATA_DIRECTION            Direction,
   1502   UINT64                    TimeOutInMicroSeconds
   1503   )
   1504 /*++
   1505 
   1506 Routine Description:
   1507 
   1508   Performs data transfer between ATAPI device and host after the
   1509   ATAPI command packet is sent.
   1510 
   1511 Arguments:
   1512 
   1513   AtapiScsiPrivate:   Private data structure for the specified channel.
   1514   Buffer:             Points to the transferred data.
   1515   ByteCount:          When input,indicates the buffer size; when output,
   1516                       indicates the actually transferred data size.
   1517   Direction:          Indicates the data transfer direction.
   1518   TimeoutInMicroSeconds:
   1519                       The timeout, in micro second units, to use for the
   1520                       execution of this ATAPI command.
   1521                       A TimeoutInMicroSeconds value of 0 means that
   1522                       this function will wait indefinitely for the ATAPI
   1523                       command to execute.
   1524                       If TimeoutInMicroSeconds is greater than zero, then
   1525                       this function will return EFI_TIMEOUT if the time
   1526                       required to execute the ATAPI command is greater
   1527                       than TimeoutInMicroSeconds.
   1528  Returns:
   1529 
   1530   EFI_STATUS
   1531 
   1532 --*/
   1533 ;
   1534 
   1535 EFI_STATUS
   1536 AtapiPassThruCheckErrorStatus (
   1537   ATAPI_SCSI_PASS_THRU_DEV        *AtapiScsiPrivate
   1538   )
   1539 /*++
   1540 
   1541 Routine Description:
   1542 
   1543   Check Error Register for Error Information.
   1544 
   1545 Arguments:
   1546 
   1547   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1548 
   1549 Returns:
   1550 
   1551   EFI_STATUS
   1552 
   1553 --*/
   1554 ;
   1555 
   1556 
   1557 EFI_STATUS
   1558 GetIdeRegistersBaseAddr (
   1559   IN  EFI_PCI_IO_PROTOCOL         *PciIo,
   1560   OUT IDE_REGISTERS_BASE_ADDR     *IdeRegsBaseAddr
   1561   )
   1562 /*++
   1563 
   1564 Routine Description:
   1565   Get IDE IO port registers' base addresses by mode. In 'Compatibility' mode,
   1566   use fixed addresses. In Native-PCI mode, get base addresses from BARs in
   1567   the PCI IDE controller's Configuration Space.
   1568 
   1569 Arguments:
   1570   PciIo             - Pointer to the EFI_PCI_IO_PROTOCOL instance
   1571   IdeRegsBaseAddr   - Pointer to IDE_REGISTERS_BASE_ADDR to
   1572                       receive IDE IO port registers' base addresses
   1573 
   1574 Returns:
   1575 
   1576   EFI_STATUS
   1577 
   1578 --*/
   1579 ;
   1580 
   1581 
   1582 VOID
   1583 InitAtapiIoPortRegisters (
   1584   IN  ATAPI_SCSI_PASS_THRU_DEV     *AtapiScsiPrivate,
   1585   IN  IDE_REGISTERS_BASE_ADDR      *IdeRegsBaseAddr
   1586   )
   1587 /*++
   1588 
   1589 Routine Description:
   1590 
   1591   Initialize each Channel's Base Address of CommandBlock and ControlBlock.
   1592 
   1593 Arguments:
   1594 
   1595   AtapiScsiPrivate            - The pointer of ATAPI_SCSI_PASS_THRU_DEV
   1596   IdeRegsBaseAddr             - The pointer of IDE_REGISTERS_BASE_ADDR
   1597 
   1598 Returns:
   1599 
   1600   None
   1601 
   1602 --*/
   1603 ;
   1604 
   1605 /**
   1606   Installs Scsi Pass Thru and/or Ext Scsi Pass Thru
   1607   protocols based on feature flags.
   1608 
   1609   @param Controller         The controller handle to
   1610                             install these protocols on.
   1611   @param AtapiScsiPrivate   A pointer to the protocol private
   1612                             data structure.
   1613 
   1614   @retval EFI_SUCCESS       The installation succeeds.
   1615   @retval other             The installation fails.
   1616 
   1617 **/
   1618 EFI_STATUS
   1619 InstallScsiPassThruProtocols (
   1620   IN EFI_HANDLE                 *ControllerHandle,
   1621   IN ATAPI_SCSI_PASS_THRU_DEV   *AtapiScsiPrivate
   1622   );
   1623 
   1624 #endif
   1625