Home | History | Annotate | Download | only in DxeIoLibCpuIo2
      1 /** @file
      2   I/O Library instance based on EFI_CPU_IO2_PROTOCOL.
      3 
      4   Copyright (c) 2010, Intel Corporation. All rights reserved.<BR>
      5   This program and the accompanying materials are licensed and made available
      6   under the terms and conditions of the BSD License which accompanies this
      7   distribution.  The full text of the license may be found at
      8   http://opensource.org/licenses/bsd-license.php.
      9 
     10   THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
     11   WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
     12 
     13 **/
     14 
     15 #include "DxeCpuIo2LibInternal.h"
     16 
     17 //
     18 // Globle varible to cache pointer to CpuIo2 protocol.
     19 //
     20 EFI_CPU_IO2_PROTOCOL  *mCpuIo = NULL;
     21 
     22 /**
     23   The constructor function caches the pointer to CpuIo2 protocol.
     24 
     25   The constructor function locates CpuIo2 protocol from protocol database.
     26   It will ASSERT() if that operation fails and it will always return EFI_SUCCESS.
     27 
     28   @param  ImageHandle   The firmware allocated handle for the EFI image.
     29   @param  SystemTable   A pointer to the EFI System Table.
     30 
     31   @retval EFI_SUCCESS   The constructor always returns EFI_SUCCESS.
     32 
     33 **/
     34 EFI_STATUS
     35 EFIAPI
     36 IoLibConstructor (
     37   IN      EFI_HANDLE                ImageHandle,
     38   IN      EFI_SYSTEM_TABLE          *SystemTable
     39   )
     40 {
     41   EFI_STATUS  Status;
     42 
     43   Status = gBS->LocateProtocol (&gEfiCpuIo2ProtocolGuid, NULL, (VOID **) &mCpuIo);
     44   ASSERT_EFI_ERROR (Status);
     45 
     46   return Status;
     47 }
     48 
     49 /**
     50   Reads registers in the EFI CPU I/O space.
     51 
     52   Reads the I/O port specified by Port with registers width specified by Width.
     53   The read value is returned. If such operations are not supported, then ASSERT().
     54   This function must guarantee that all I/O read and write operations are serialized.
     55 
     56   @param  Port          The base address of the I/O operation.
     57                         The caller is responsible for aligning the Address if required.
     58   @param  Width         The width of the I/O operation.
     59 
     60   @return Data read from registers in the EFI CPU I/O space.
     61 
     62 **/
     63 UINT64
     64 EFIAPI
     65 IoReadWorker (
     66   IN      UINTN                      Port,
     67   IN      EFI_CPU_IO_PROTOCOL_WIDTH  Width
     68   )
     69 {
     70   EFI_STATUS                        Status;
     71   UINT64                            Data;
     72 
     73   Status = mCpuIo->Io.Read (mCpuIo, Width, Port, 1, &Data);
     74   ASSERT_EFI_ERROR (Status);
     75 
     76   return Data;
     77 }
     78 
     79 /**
     80   Writes registers in the EFI CPU I/O space.
     81 
     82   Writes the I/O port specified by Port with registers width and value specified by Width
     83   and Data respectively.  Data is returned. If such operations are not supported, then ASSERT().
     84   This function must guarantee that all I/O read and write operations are serialized.
     85 
     86   @param  Port          The base address of the I/O operation.
     87                         The caller is responsible for aligning the Address if required.
     88   @param  Width         The width of the I/O operation.
     89   @param  Data          The value to write to the I/O port.
     90 
     91   @return The parameter of Data.
     92 
     93 **/
     94 UINT64
     95 EFIAPI
     96 IoWriteWorker (
     97   IN      UINTN                      Port,
     98   IN      EFI_CPU_IO_PROTOCOL_WIDTH  Width,
     99   IN      UINT64                     Data
    100   )
    101 {
    102   EFI_STATUS  Status;
    103 
    104   Status = mCpuIo->Io.Write (mCpuIo, Width, Port, 1, &Data);
    105   ASSERT_EFI_ERROR (Status);
    106 
    107   return Data;
    108 }
    109 
    110 /**
    111   Reads memory-mapped registers in the EFI system memory space.
    112 
    113   Reads the MMIO registers specified by Address with registers width specified by Width.
    114   The read value is returned. If such operations are not supported, then ASSERT().
    115   This function must guarantee that all MMIO read and write operations are serialized.
    116 
    117   @param  Address       The MMIO register to read.
    118                         The caller is responsible for aligning the Address if required.
    119   @param  Width         The width of the I/O operation.
    120 
    121   @return Data read from registers in the EFI system memory space.
    122 
    123 **/
    124 UINT64
    125 EFIAPI
    126 MmioReadWorker (
    127   IN      UINTN                      Address,
    128   IN      EFI_CPU_IO_PROTOCOL_WIDTH  Width
    129   )
    130 {
    131   EFI_STATUS  Status;
    132   UINT64      Data;
    133 
    134   Status = mCpuIo->Mem.Read (mCpuIo, Width, Address, 1, &Data);
    135   ASSERT_EFI_ERROR (Status);
    136 
    137   return Data;
    138 }
    139 
    140 /**
    141   Writes memory-mapped registers in the EFI system memory space.
    142 
    143   Writes the MMIO registers specified by Address with registers width and value specified by Width
    144   and Data respectively. Data is returned. If such operations are not supported, then ASSERT().
    145   This function must guarantee that all MMIO read and write operations are serialized.
    146 
    147   @param  Address       The MMIO register to read.
    148                         The caller is responsible for aligning the Address if required.
    149   @param  Width         The width of the I/O operation.
    150   @param  Data          The value to write to the I/O port.
    151 
    152   @return Data read from registers in the EFI system memory space.
    153 
    154 **/
    155 UINT64
    156 EFIAPI
    157 MmioWriteWorker (
    158   IN      UINTN                      Address,
    159   IN      EFI_CPU_IO_PROTOCOL_WIDTH  Width,
    160   IN      UINT64                     Data
    161   )
    162 {
    163   EFI_STATUS  Status;
    164 
    165   Status = mCpuIo->Mem.Write (mCpuIo, Width, Address, 1, &Data);
    166   ASSERT_EFI_ERROR (Status);
    167 
    168   return Data;
    169 }
    170 
    171 /**
    172   Reads an 8-bit I/O port.
    173 
    174   Reads the 8-bit I/O port specified by Port. The 8-bit read value is returned.
    175   This function must guarantee that all I/O read and write operations are
    176   serialized.
    177 
    178   If 8-bit I/O port operations are not supported, then ASSERT().
    179 
    180   @param  Port  The I/O port to read.
    181 
    182   @return The value read.
    183 
    184 **/
    185 UINT8
    186 EFIAPI
    187 IoRead8 (
    188   IN      UINTN                     Port
    189   )
    190 {
    191   return (UINT8)IoReadWorker (Port, EfiCpuIoWidthUint8);
    192 }
    193 
    194 /**
    195   Writes an 8-bit I/O port.
    196 
    197   Writes the 8-bit I/O port specified by Port with the value specified by Value
    198   and returns Value. This function must guarantee that all I/O read and write
    199   operations are serialized.
    200 
    201   If 8-bit I/O port operations are not supported, then ASSERT().
    202 
    203   @param  Port  The I/O port to write.
    204   @param  Value The value to write to the I/O port.
    205 
    206   @return The value written the I/O port.
    207 
    208 **/
    209 UINT8
    210 EFIAPI
    211 IoWrite8 (
    212   IN      UINTN                     Port,
    213   IN      UINT8                     Value
    214   )
    215 {
    216   return (UINT8)IoWriteWorker (Port, EfiCpuIoWidthUint8, Value);
    217 }
    218 
    219 /**
    220   Reads a 16-bit I/O port.
    221 
    222   Reads the 16-bit I/O port specified by Port. The 16-bit read value is returned.
    223   This function must guarantee that all I/O read and write operations are
    224   serialized.
    225 
    226   If Port is not aligned on a 16-bit boundary, then ASSERT().
    227 
    228   If 16-bit I/O port operations are not supported, then ASSERT().
    229 
    230   @param  Port  The I/O port to read.
    231 
    232   @return The value read.
    233 
    234 **/
    235 UINT16
    236 EFIAPI
    237 IoRead16 (
    238   IN      UINTN                     Port
    239   )
    240 {
    241   //
    242   // Make sure Port is aligned on a 16-bit boundary.
    243   //
    244   ASSERT ((Port & 1) == 0);
    245   return (UINT16)IoReadWorker (Port, EfiCpuIoWidthUint16);
    246 }
    247 
    248 /**
    249   Writes a 16-bit I/O port.
    250 
    251   Writes the 16-bit I/O port specified by Port with the value specified by Value
    252   and returns Value. This function must guarantee that all I/O read and write
    253   operations are serialized.
    254 
    255   If Port is not aligned on a 16-bit boundary, then ASSERT().
    256 
    257   If 16-bit I/O port operations are not supported, then ASSERT().
    258 
    259   @param  Port  The I/O port to write.
    260   @param  Value The value to write to the I/O port.
    261 
    262   @return The value written the I/O port.
    263 
    264 **/
    265 UINT16
    266 EFIAPI
    267 IoWrite16 (
    268   IN      UINTN                     Port,
    269   IN      UINT16                    Value
    270   )
    271 {
    272   //
    273   // Make sure Port is aligned on a 16-bit boundary.
    274   //
    275   ASSERT ((Port & 1) == 0);
    276   return (UINT16)IoWriteWorker (Port, EfiCpuIoWidthUint16, Value);
    277 }
    278 
    279 /**
    280   Reads a 32-bit I/O port.
    281 
    282   Reads the 32-bit I/O port specified by Port. The 32-bit read value is returned.
    283   This function must guarantee that all I/O read and write operations are
    284   serialized.
    285 
    286   If Port is not aligned on a 32-bit boundary, then ASSERT().
    287 
    288   If 32-bit I/O port operations are not supported, then ASSERT().
    289 
    290   @param  Port  The I/O port to read.
    291 
    292   @return The value read.
    293 
    294 **/
    295 UINT32
    296 EFIAPI
    297 IoRead32 (
    298   IN      UINTN                     Port
    299   )
    300 {
    301   //
    302   // Make sure Port is aligned on a 32-bit boundary.
    303   //
    304   ASSERT ((Port & 3) == 0);
    305   return (UINT32)IoReadWorker (Port, EfiCpuIoWidthUint32);
    306 }
    307 
    308 /**
    309   Writes a 32-bit I/O port.
    310 
    311   Writes the 32-bit I/O port specified by Port with the value specified by Value
    312   and returns Value. This function must guarantee that all I/O read and write
    313   operations are serialized.
    314 
    315   If Port is not aligned on a 32-bit boundary, then ASSERT().
    316 
    317   If 32-bit I/O port operations are not supported, then ASSERT().
    318 
    319   @param  Port  The I/O port to write.
    320   @param  Value The value to write to the I/O port.
    321 
    322   @return The value written the I/O port.
    323 
    324 **/
    325 UINT32
    326 EFIAPI
    327 IoWrite32 (
    328   IN      UINTN                     Port,
    329   IN      UINT32                    Value
    330   )
    331 {
    332   //
    333   // Make sure Port is aligned on a 32-bit boundary.
    334   //
    335   ASSERT ((Port & 3) == 0);
    336   return (UINT32)IoWriteWorker (Port, EfiCpuIoWidthUint32, Value);
    337 }
    338 
    339 /**
    340   Reads a 64-bit I/O port.
    341 
    342   Reads the 64-bit I/O port specified by Port. The 64-bit read value is returned.
    343   This function must guarantee that all I/O read and write operations are
    344   serialized.
    345 
    346   If Port is not aligned on a 64-bit boundary, then ASSERT().
    347 
    348   If 64-bit I/O port operations are not supported, then ASSERT().
    349 
    350   @param  Port  The I/O port to read.
    351 
    352   @return The value read.
    353 
    354 **/
    355 UINT64
    356 EFIAPI
    357 IoRead64 (
    358   IN      UINTN                     Port
    359   )
    360 {
    361   //
    362   // Make sure Port is aligned on a 64-bit boundary.
    363   //
    364   ASSERT ((Port & 7) == 0);
    365   return IoReadWorker (Port, EfiCpuIoWidthUint64);
    366 }
    367 
    368 /**
    369   Writes a 64-bit I/O port.
    370 
    371   Writes the 64-bit I/O port specified by Port with the value specified by Value
    372   and returns Value. This function must guarantee that all I/O read and write
    373   operations are serialized.
    374 
    375   If Port is not aligned on a 64-bit boundary, then ASSERT().
    376 
    377   If 64-bit I/O port operations are not supported, then ASSERT().
    378 
    379   @param  Port  The I/O port to write.
    380   @param  Value The value to write to the I/O port.
    381 
    382   @return The value written the I/O port.
    383 
    384 **/
    385 UINT64
    386 EFIAPI
    387 IoWrite64 (
    388   IN      UINTN                     Port,
    389   IN      UINT64                    Value
    390   )
    391 {
    392   //
    393   // Make sure Port is aligned on a 64-bit boundary.
    394   //
    395   ASSERT ((Port & 7) == 0);
    396   return IoWriteWorker (Port, EfiCpuIoWidthUint64, Value);
    397 }
    398 
    399 /**
    400   Reads an 8-bit MMIO register.
    401 
    402   Reads the 8-bit MMIO register specified by Address. The 8-bit read value is
    403   returned. This function must guarantee that all MMIO read and write
    404   operations are serialized.
    405 
    406   If 8-bit MMIO register operations are not supported, then ASSERT().
    407 
    408   @param  Address The MMIO register to read.
    409 
    410   @return The value read.
    411 
    412 **/
    413 UINT8
    414 EFIAPI
    415 MmioRead8 (
    416   IN      UINTN                     Address
    417   )
    418 {
    419   return (UINT8)MmioReadWorker (Address, EfiCpuIoWidthUint8);
    420 }
    421 
    422 /**
    423   Writes an 8-bit MMIO register.
    424 
    425   Writes the 8-bit MMIO register specified by Address with the value specified
    426   by Value and returns Value. This function must guarantee that all MMIO read
    427   and write operations are serialized.
    428 
    429   If 8-bit MMIO register operations are not supported, then ASSERT().
    430 
    431   @param  Address The MMIO register to write.
    432   @param  Value   The value to write to the MMIO register.
    433 
    434 **/
    435 UINT8
    436 EFIAPI
    437 MmioWrite8 (
    438   IN      UINTN                     Address,
    439   IN      UINT8                     Value
    440   )
    441 {
    442   return (UINT8)MmioWriteWorker (Address, EfiCpuIoWidthUint8, Value);
    443 }
    444 
    445 /**
    446   Reads a 16-bit MMIO register.
    447 
    448   Reads the 16-bit MMIO register specified by Address. The 16-bit read value is
    449   returned. This function must guarantee that all MMIO read and write
    450   operations are serialized.
    451 
    452   If Address is not aligned on a 16-bit boundary, then ASSERT().
    453 
    454   If 16-bit MMIO register operations are not supported, then ASSERT().
    455 
    456   @param  Address The MMIO register to read.
    457 
    458   @return The value read.
    459 
    460 **/
    461 UINT16
    462 EFIAPI
    463 MmioRead16 (
    464   IN      UINTN                     Address
    465   )
    466 {
    467   //
    468   // Make sure Address is aligned on a 16-bit boundary.
    469   //
    470   ASSERT ((Address & 1) == 0);
    471   return (UINT16)MmioReadWorker (Address, EfiCpuIoWidthUint16);
    472 }
    473 
    474 /**
    475   Writes a 16-bit MMIO register.
    476 
    477   Writes the 16-bit MMIO register specified by Address with the value specified
    478   by Value and returns Value. This function must guarantee that all MMIO read
    479   and write operations are serialized.
    480 
    481   If Address is not aligned on a 16-bit boundary, then ASSERT().
    482 
    483   If 16-bit MMIO register operations are not supported, then ASSERT().
    484 
    485   @param  Address The MMIO register to write.
    486   @param  Value   The value to write to the MMIO register.
    487 
    488 **/
    489 UINT16
    490 EFIAPI
    491 MmioWrite16 (
    492   IN      UINTN                     Address,
    493   IN      UINT16                    Value
    494   )
    495 {
    496   //
    497   // Make sure Address is aligned on a 16-bit boundary.
    498   //
    499   ASSERT ((Address & 1) == 0);
    500   return (UINT16)MmioWriteWorker (Address, EfiCpuIoWidthUint16, Value);
    501 }
    502 
    503 /**
    504   Reads a 32-bit MMIO register.
    505 
    506   Reads the 32-bit MMIO register specified by Address. The 32-bit read value is
    507   returned. This function must guarantee that all MMIO read and write
    508   operations are serialized.
    509 
    510   If Address is not aligned on a 32-bit boundary, then ASSERT().
    511 
    512   If 32-bit MMIO register operations are not supported, then ASSERT().
    513 
    514   @param  Address The MMIO register to read.
    515 
    516   @return The value read.
    517 
    518 **/
    519 UINT32
    520 EFIAPI
    521 MmioRead32 (
    522   IN      UINTN                     Address
    523   )
    524 {
    525   //
    526   // Make sure Address is aligned on a 32-bit boundary.
    527   //
    528   ASSERT ((Address & 3) == 0);
    529   return (UINT32)MmioReadWorker (Address, EfiCpuIoWidthUint32);
    530 }
    531 
    532 /**
    533   Writes a 32-bit MMIO register.
    534 
    535   Writes the 32-bit MMIO register specified by Address with the value specified
    536   by Value and returns Value. This function must guarantee that all MMIO read
    537   and write operations are serialized.
    538 
    539   If Address is not aligned on a 32-bit boundary, then ASSERT().
    540 
    541   If 32-bit MMIO register operations are not supported, then ASSERT().
    542 
    543   @param  Address The MMIO register to write.
    544   @param  Value   The value to write to the MMIO register.
    545 
    546 **/
    547 UINT32
    548 EFIAPI
    549 MmioWrite32 (
    550   IN      UINTN                     Address,
    551   IN      UINT32                    Value
    552   )
    553 {
    554   //
    555   // Make sure Address is aligned on a 32-bit boundary.
    556   //
    557   ASSERT ((Address & 3) == 0);
    558   return (UINT32)MmioWriteWorker (Address, EfiCpuIoWidthUint32, Value);
    559 }
    560 
    561 /**
    562   Reads a 64-bit MMIO register.
    563 
    564   Reads the 64-bit MMIO register specified by Address. The 64-bit read value is
    565   returned. This function must guarantee that all MMIO read and write
    566   operations are serialized.
    567 
    568   If Address is not aligned on a 64-bit boundary, then ASSERT().
    569 
    570   If 64-bit MMIO register operations are not supported, then ASSERT().
    571 
    572   @param  Address The MMIO register to read.
    573 
    574   @return The value read.
    575 
    576 **/
    577 UINT64
    578 EFIAPI
    579 MmioRead64 (
    580   IN      UINTN                     Address
    581   )
    582 {
    583   //
    584   // Make sure Address is aligned on a 64-bit boundary.
    585   //
    586   ASSERT ((Address & 7) == 0);
    587   return (UINT64)MmioReadWorker (Address, EfiCpuIoWidthUint64);
    588 }
    589 
    590 /**
    591   Writes a 64-bit MMIO register.
    592 
    593   Writes the 64-bit MMIO register specified by Address with the value specified
    594   by Value and returns Value. This function must guarantee that all MMIO read
    595   and write operations are serialized.
    596 
    597   If Address is not aligned on a 64-bit boundary, then ASSERT().
    598 
    599   If 64-bit MMIO register operations are not supported, then ASSERT().
    600 
    601   @param  Address The MMIO register to write.
    602   @param  Value   The value to write to the MMIO register.
    603 
    604 **/
    605 UINT64
    606 EFIAPI
    607 MmioWrite64 (
    608   IN      UINTN                     Address,
    609   IN      UINT64                    Value
    610   )
    611 {
    612   //
    613   // Make sure Address is aligned on a 64-bit boundary.
    614   //
    615   ASSERT ((Address & 7) == 0);
    616   return (UINT64)MmioWriteWorker (Address, EfiCpuIoWidthUint64, Value);
    617 }
    618