Home | History | Annotate | Download | only in EmmcBlockIoPei
      1 /** @file
      2 
      3   Copyright (c) 2015, Intel Corporation. All rights reserved.<BR>
      4   This program and the accompanying materials
      5   are licensed and made available under the terms and conditions of the BSD License
      6   which accompanies this distribution.  The full text of the license may be found at
      7   http://opensource.org/licenses/bsd-license.php
      8 
      9   THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
     10   WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
     11 
     12 **/
     13 
     14 #ifndef _EMMC_BLOCK_IO_PEI_H_
     15 #define _EMMC_BLOCK_IO_PEI_H_
     16 
     17 #include <PiPei.h>
     18 
     19 #include <Ppi/SdMmcHostController.h>
     20 #include <Ppi/BlockIo.h>
     21 #include <Ppi/BlockIo2.h>
     22 
     23 #include <Library/DebugLib.h>
     24 #include <Library/BaseLib.h>
     25 #include <Library/BaseMemoryLib.h>
     26 #include <Library/MemoryAllocationLib.h>
     27 #include <Library/IoLib.h>
     28 #include <Library/TimerLib.h>
     29 #include <Library/PeiServicesLib.h>
     30 
     31 #include <IndustryStandard/Emmc.h>
     32 
     33 typedef struct _EMMC_PEIM_HC_PRIVATE_DATA EMMC_PEIM_HC_PRIVATE_DATA;
     34 typedef struct _EMMC_PEIM_HC_SLOT         EMMC_PEIM_HC_SLOT;
     35 typedef struct _EMMC_TRB                  EMMC_TRB;
     36 
     37 #include "EmmcHci.h"
     38 #include "EmmcHcMem.h"
     39 
     40 #define EMMC_PEIM_SIG               SIGNATURE_32 ('E', 'M', 'C', 'P')
     41 #define EMMC_PEIM_SLOT_SIG          SIGNATURE_32 ('E', 'M', 'C', 'S')
     42 
     43 #define EMMC_PEIM_MAX_SLOTS         6
     44 #define EMMC_PEIM_MAX_PARTITIONS    8
     45 
     46 struct _EMMC_PEIM_HC_SLOT {
     47   UINT32                            Signature;
     48   EFI_PEI_BLOCK_IO2_MEDIA           Media[EMMC_PEIM_MAX_PARTITIONS];
     49   UINT8                             MediaNum;
     50   EMMC_PARTITION_TYPE               PartitionType[EMMC_PEIM_MAX_PARTITIONS];
     51 
     52   UINTN                             EmmcHcBase;
     53   EMMC_HC_SLOT_CAP                  Capability;
     54   EMMC_CSD                          Csd;
     55   EMMC_EXT_CSD                      ExtCsd;
     56   BOOLEAN                           SectorAddressing;
     57   EMMC_PEIM_HC_PRIVATE_DATA         *Private;
     58 };
     59 
     60 struct _EMMC_PEIM_HC_PRIVATE_DATA {
     61   UINT32                            Signature;
     62   EMMC_PEIM_MEM_POOL                *Pool;
     63   EFI_PEI_RECOVERY_BLOCK_IO_PPI     BlkIoPpi;
     64   EFI_PEI_RECOVERY_BLOCK_IO2_PPI    BlkIo2Ppi;
     65   EFI_PEI_PPI_DESCRIPTOR            BlkIoPpiList;
     66   EFI_PEI_PPI_DESCRIPTOR            BlkIo2PpiList;
     67   EMMC_PEIM_HC_SLOT                 Slot[EMMC_PEIM_MAX_SLOTS];
     68   UINT8                             SlotNum;
     69   UINT8                             TotalBlkIoDevices;
     70 };
     71 
     72 #define EMMC_TIMEOUT                MultU64x32((UINT64)(3), 1000000)
     73 #define GET_EMMC_PEIM_HC_PRIVATE_DATA_FROM_THIS(a) CR (a, EMMC_PEIM_HC_PRIVATE_DATA, BlkIoPpi, EMMC_PEIM_SIG)
     74 #define GET_EMMC_PEIM_HC_PRIVATE_DATA_FROM_THIS2(a) CR (a, EMMC_PEIM_HC_PRIVATE_DATA, BlkIo2Ppi, EMMC_PEIM_SIG)
     75 
     76 struct _EMMC_TRB {
     77   EMMC_PEIM_HC_SLOT                   *Slot;
     78   UINT16                              BlockSize;
     79 
     80   EMMC_COMMAND_PACKET                 *Packet;
     81   VOID                                *Data;
     82   UINT32                              DataLen;
     83   BOOLEAN                             Read;
     84   EMMC_HC_TRANSFER_MODE               Mode;
     85 
     86   UINT64                              Timeout;
     87 
     88   EMMC_HC_ADMA_DESC_LINE              *AdmaDesc;
     89   UINTN                               AdmaDescSize;
     90 };
     91 
     92 /**
     93   Gets the count of block I/O devices that one specific block driver detects.
     94 
     95   This function is used for getting the count of block I/O devices that one
     96   specific block driver detects.  To the PEI ATAPI driver, it returns the number
     97   of all the detected ATAPI devices it detects during the enumeration process.
     98   To the PEI legacy floppy driver, it returns the number of all the legacy
     99   devices it finds during its enumeration process. If no device is detected,
    100   then the function will return zero.
    101 
    102   @param[in]  PeiServices          General-purpose services that are available
    103                                    to every PEIM.
    104   @param[in]  This                 Indicates the EFI_PEI_RECOVERY_BLOCK_IO_PPI
    105                                    instance.
    106   @param[out] NumberBlockDevices   The number of block I/O devices discovered.
    107 
    108   @retval     EFI_SUCCESS          The operation performed successfully.
    109 
    110 **/
    111 EFI_STATUS
    112 EFIAPI
    113 EmmcBlockIoPeimGetDeviceNo (
    114   IN  EFI_PEI_SERVICES               **PeiServices,
    115   IN  EFI_PEI_RECOVERY_BLOCK_IO_PPI  *This,
    116   OUT UINTN                          *NumberBlockDevices
    117   );
    118 
    119 /**
    120   Gets a block device's media information.
    121 
    122   This function will provide the caller with the specified block device's media
    123   information. If the media changes, calling this function will update the media
    124   information accordingly.
    125 
    126   @param[in]  PeiServices   General-purpose services that are available to every
    127                             PEIM
    128   @param[in]  This          Indicates the EFI_PEI_RECOVERY_BLOCK_IO_PPI instance.
    129   @param[in]  DeviceIndex   Specifies the block device to which the function wants
    130                             to talk. Because the driver that implements Block I/O
    131                             PPIs will manage multiple block devices, the PPIs that
    132                             want to talk to a single device must specify the
    133                             device index that was assigned during the enumeration
    134                             process. This index is a number from one to
    135                             NumberBlockDevices.
    136   @param[out] MediaInfo     The media information of the specified block media.
    137                             The caller is responsible for the ownership of this
    138                             data structure.
    139 
    140   @par Note:
    141       The MediaInfo structure describes an enumeration of possible block device
    142       types.  This enumeration exists because no device paths are actually passed
    143       across interfaces that describe the type or class of hardware that is publishing
    144       the block I/O interface. This enumeration will allow for policy decisions
    145       in the Recovery PEIM, such as "Try to recover from legacy floppy first,
    146       LS-120 second, CD-ROM third." If there are multiple partitions abstracted
    147       by a given device type, they should be reported in ascending order; this
    148       order also applies to nested partitions, such as legacy MBR, where the
    149       outermost partitions would have precedence in the reporting order. The
    150       same logic applies to systems such as IDE that have precedence relationships
    151       like "Master/Slave" or "Primary/Secondary". The master device should be
    152       reported first, the slave second.
    153 
    154   @retval EFI_SUCCESS        Media information about the specified block device
    155                              was obtained successfully.
    156   @retval EFI_DEVICE_ERROR   Cannot get the media information due to a hardware
    157                              error.
    158 
    159 **/
    160 EFI_STATUS
    161 EFIAPI
    162 EmmcBlockIoPeimGetMediaInfo (
    163   IN  EFI_PEI_SERVICES               **PeiServices,
    164   IN  EFI_PEI_RECOVERY_BLOCK_IO_PPI  *This,
    165   IN  UINTN                          DeviceIndex,
    166   OUT EFI_PEI_BLOCK_IO_MEDIA         *MediaInfo
    167   );
    168 
    169 /**
    170   Reads the requested number of blocks from the specified block device.
    171 
    172   The function reads the requested number of blocks from the device. All the
    173   blocks are read, or an error is returned. If there is no media in the device,
    174   the function returns EFI_NO_MEDIA.
    175 
    176   @param[in]  PeiServices   General-purpose services that are available to
    177                             every PEIM.
    178   @param[in]  This          Indicates the EFI_PEI_RECOVERY_BLOCK_IO_PPI instance.
    179   @param[in]  DeviceIndex   Specifies the block device to which the function wants
    180                             to talk. Because the driver that implements Block I/O
    181                             PPIs will manage multiple block devices, PPIs that
    182                             want to talk to a single device must specify the device
    183                             index that was assigned during the enumeration process.
    184                             This index is a number from one to NumberBlockDevices.
    185   @param[in]  StartLBA      The starting logical block address (LBA) to read from
    186                             on the device
    187   @param[in]  BufferSize    The size of the Buffer in bytes. This number must be
    188                             a multiple of the intrinsic block size of the device.
    189   @param[out] Buffer        A pointer to the destination buffer for the data.
    190                             The caller is responsible for the ownership of the
    191                             buffer.
    192 
    193   @retval EFI_SUCCESS             The data was read correctly from the device.
    194   @retval EFI_DEVICE_ERROR        The device reported an error while attempting
    195                                   to perform the read operation.
    196   @retval EFI_INVALID_PARAMETER   The read request contains LBAs that are not
    197                                   valid, or the buffer is not properly aligned.
    198   @retval EFI_NO_MEDIA            There is no media in the device.
    199   @retval EFI_BAD_BUFFER_SIZE     The BufferSize parameter is not a multiple of
    200                                   the intrinsic block size of the device.
    201 
    202 **/
    203 EFI_STATUS
    204 EFIAPI
    205 EmmcBlockIoPeimReadBlocks (
    206   IN  EFI_PEI_SERVICES               **PeiServices,
    207   IN  EFI_PEI_RECOVERY_BLOCK_IO_PPI  *This,
    208   IN  UINTN                          DeviceIndex,
    209   IN  EFI_PEI_LBA                    StartLBA,
    210   IN  UINTN                          BufferSize,
    211   OUT VOID                           *Buffer
    212   );
    213 
    214 /**
    215   Gets the count of block I/O devices that one specific block driver detects.
    216 
    217   This function is used for getting the count of block I/O devices that one
    218   specific block driver detects.  To the PEI ATAPI driver, it returns the number
    219   of all the detected ATAPI devices it detects during the enumeration process.
    220   To the PEI legacy floppy driver, it returns the number of all the legacy
    221   devices it finds during its enumeration process. If no device is detected,
    222   then the function will return zero.
    223 
    224   @param[in]  PeiServices          General-purpose services that are available
    225                                    to every PEIM.
    226   @param[in]  This                 Indicates the EFI_PEI_RECOVERY_BLOCK_IO2_PPI
    227                                    instance.
    228   @param[out] NumberBlockDevices   The number of block I/O devices discovered.
    229 
    230   @retval     EFI_SUCCESS          The operation performed successfully.
    231 
    232 **/
    233 EFI_STATUS
    234 EFIAPI
    235 EmmcBlockIoPeimGetDeviceNo2 (
    236   IN  EFI_PEI_SERVICES               **PeiServices,
    237   IN  EFI_PEI_RECOVERY_BLOCK_IO2_PPI *This,
    238   OUT UINTN                          *NumberBlockDevices
    239   );
    240 
    241 /**
    242   Gets a block device's media information.
    243 
    244   This function will provide the caller with the specified block device's media
    245   information. If the media changes, calling this function will update the media
    246   information accordingly.
    247 
    248   @param[in]  PeiServices   General-purpose services that are available to every
    249                             PEIM
    250   @param[in]  This          Indicates the EFI_PEI_RECOVERY_BLOCK_IO2_PPI instance.
    251   @param[in]  DeviceIndex   Specifies the block device to which the function wants
    252                             to talk. Because the driver that implements Block I/O
    253                             PPIs will manage multiple block devices, the PPIs that
    254                             want to talk to a single device must specify the
    255                             device index that was assigned during the enumeration
    256                             process. This index is a number from one to
    257                             NumberBlockDevices.
    258   @param[out] MediaInfo     The media information of the specified block media.
    259                             The caller is responsible for the ownership of this
    260                             data structure.
    261 
    262   @par Note:
    263       The MediaInfo structure describes an enumeration of possible block device
    264       types.  This enumeration exists because no device paths are actually passed
    265       across interfaces that describe the type or class of hardware that is publishing
    266       the block I/O interface. This enumeration will allow for policy decisions
    267       in the Recovery PEIM, such as "Try to recover from legacy floppy first,
    268       LS-120 second, CD-ROM third." If there are multiple partitions abstracted
    269       by a given device type, they should be reported in ascending order; this
    270       order also applies to nested partitions, such as legacy MBR, where the
    271       outermost partitions would have precedence in the reporting order. The
    272       same logic applies to systems such as IDE that have precedence relationships
    273       like "Master/Slave" or "Primary/Secondary". The master device should be
    274       reported first, the slave second.
    275 
    276   @retval EFI_SUCCESS        Media information about the specified block device
    277                              was obtained successfully.
    278   @retval EFI_DEVICE_ERROR   Cannot get the media information due to a hardware
    279                              error.
    280 
    281 **/
    282 EFI_STATUS
    283 EFIAPI
    284 EmmcBlockIoPeimGetMediaInfo2 (
    285   IN  EFI_PEI_SERVICES               **PeiServices,
    286   IN  EFI_PEI_RECOVERY_BLOCK_IO2_PPI *This,
    287   IN  UINTN                          DeviceIndex,
    288   OUT EFI_PEI_BLOCK_IO2_MEDIA        *MediaInfo
    289   );
    290 
    291 /**
    292   Reads the requested number of blocks from the specified block device.
    293 
    294   The function reads the requested number of blocks from the device. All the
    295   blocks are read, or an error is returned. If there is no media in the device,
    296   the function returns EFI_NO_MEDIA.
    297 
    298   @param[in]  PeiServices   General-purpose services that are available to
    299                             every PEIM.
    300   @param[in]  This          Indicates the EFI_PEI_RECOVERY_BLOCK_IO2_PPI instance.
    301   @param[in]  DeviceIndex   Specifies the block device to which the function wants
    302                             to talk. Because the driver that implements Block I/O
    303                             PPIs will manage multiple block devices, PPIs that
    304                             want to talk to a single device must specify the device
    305                             index that was assigned during the enumeration process.
    306                             This index is a number from one to NumberBlockDevices.
    307   @param[in]  StartLBA      The starting logical block address (LBA) to read from
    308                             on the device
    309   @param[in]  BufferSize    The size of the Buffer in bytes. This number must be
    310                             a multiple of the intrinsic block size of the device.
    311   @param[out] Buffer        A pointer to the destination buffer for the data.
    312                             The caller is responsible for the ownership of the
    313                             buffer.
    314 
    315   @retval EFI_SUCCESS             The data was read correctly from the device.
    316   @retval EFI_DEVICE_ERROR        The device reported an error while attempting
    317                                   to perform the read operation.
    318   @retval EFI_INVALID_PARAMETER   The read request contains LBAs that are not
    319                                   valid, or the buffer is not properly aligned.
    320   @retval EFI_NO_MEDIA            There is no media in the device.
    321   @retval EFI_BAD_BUFFER_SIZE     The BufferSize parameter is not a multiple of
    322                                   the intrinsic block size of the device.
    323 
    324 **/
    325 EFI_STATUS
    326 EFIAPI
    327 EmmcBlockIoPeimReadBlocks2 (
    328   IN  EFI_PEI_SERVICES               **PeiServices,
    329   IN  EFI_PEI_RECOVERY_BLOCK_IO2_PPI *This,
    330   IN  UINTN                          DeviceIndex,
    331   IN  EFI_PEI_LBA                    StartLBA,
    332   IN  UINTN                          BufferSize,
    333   OUT VOID                           *Buffer
    334   );
    335 
    336 /**
    337   Initialize the memory management pool for the host controller.
    338 
    339   @param  Private               The Emmc Peim driver private data.
    340 
    341   @retval EFI_SUCCESS           The memory pool is initialized.
    342   @retval Others                Fail to init the memory pool.
    343 
    344 **/
    345 EFI_STATUS
    346 EmmcPeimInitMemPool (
    347   IN  EMMC_PEIM_HC_PRIVATE_DATA      *Private
    348   );
    349 
    350 /**
    351   Allocate some memory from the host controller's memory pool
    352   which can be used to communicate with host controller.
    353 
    354   @param  Pool      The host controller's memory pool.
    355   @param  Size      Size of the memory to allocate.
    356 
    357   @return The allocated memory or NULL.
    358 
    359 **/
    360 VOID *
    361 EmmcPeimAllocateMem (
    362   IN  EMMC_PEIM_MEM_POOL        *Pool,
    363   IN  UINTN                    Size
    364   );
    365 
    366 /**
    367   Free the allocated memory back to the memory pool.
    368 
    369   @param  Pool           The memory pool of the host controller.
    370   @param  Mem            The memory to free.
    371   @param  Size           The size of the memory to free.
    372 
    373 **/
    374 VOID
    375 EmmcPeimFreeMem (
    376   IN EMMC_PEIM_MEM_POOL    *Pool,
    377   IN VOID                 *Mem,
    378   IN UINTN                Size
    379   );
    380 
    381 #endif
    382