]> git.proxmox.com Git - mirror_edk2.git/blobdiff - MdePkg/Library/BasePciCf8Lib/PciCf8Lib.c
MdePkg: Replace BSD License with BSD+Patent License
[mirror_edk2.git] / MdePkg / Library / BasePciCf8Lib / PciCf8Lib.c
index f0a23c3605ebe58e49f781bc08680c27c53d93b5..ba4190ab686cb9235fb7a9616799586d2f9ee3ee 100644 (file)
@@ -2,14 +2,8 @@
   PCI CF8 Library functions that use I/O ports 0xCF8 and 0xCFC to perform PCI Configuration cycles.\r
   Layers on top of an I/O Library instance.\r
 \r
-  Copyright (c) 2006 - 2009, Intel Corporation<BR>\r
-  All rights reserved. This program and the accompanying materials\r
-  are licensed and made available under the terms and conditions of the BSD License\r
-  which accompanies this distribution.  The full text of the license may be found at\r
-  http://opensource.org/licenses/bsd-license.php\r
-\r
-  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
-  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+  Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>\r
+  SPDX-License-Identifier: BSD-2-Clause-Patent\r
 \r
 **/\r
 \r
   ASSERT (((A) & (~0xffff0ff | (M))) == 0)\r
 \r
 /**\r
-  Registers a PCI device so PCI configuration registers may be accessed after \r
+  Registers a PCI device so PCI configuration registers may be accessed after\r
   SetVirtualAddressMap().\r
-  \r
-  Registers the PCI device specified by Address so all the PCI configuration registers \r
+\r
+  Registers the PCI device specified by Address so all the PCI configuration registers\r
   associated with that PCI device may be accessed after SetVirtualAddressMap() is called.\r
-  \r
+\r
   If Address > 0x0FFFFFFF, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
-  \r
+\r
   @retval RETURN_SUCCESS           The PCI device was registered for runtime access.\r
-  @retval RETURN_UNSUPPORTED       An attempt was made to call this function \r
+  @retval RETURN_UNSUPPORTED       An attempt was made to call this function\r
                                    after ExitBootServices().\r
   @retval RETURN_UNSUPPORTED       The resources required to access the PCI device\r
                                    at runtime could not be mapped.\r
@@ -102,7 +96,7 @@ PciCf8RegisterForRuntimeAccess (
   If Address > 0x0FFFFFFF, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
 \r
   @return The read value from the PCI configuration register.\r
@@ -114,9 +108,18 @@ PciCf8Read8 (
   IN      UINTN                     Address\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoRead8 (PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3));\r
+  Result = IoRead8 (PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3));\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -129,7 +132,7 @@ PciCf8Read8 (
   If Address > 0x0FFFFFFF, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  Value   The value to write.\r
 \r
@@ -143,12 +146,21 @@ PciCf8Write8 (
   IN      UINT8                     Value\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoWrite8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           Value\r
-           );\r
+  Result = IoWrite8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             Value\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -165,7 +177,7 @@ PciCf8Write8 (
   If Address > 0x0FFFFFFF, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  OrData  The value to OR with the PCI configuration register.\r
 \r
@@ -179,12 +191,21 @@ PciCf8Or8 (
   IN      UINT8                     OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoOr8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           OrData\r
-           );\r
+  Result = IoOr8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -201,7 +222,7 @@ PciCf8Or8 (
   If Address > 0x0FFFFFFF, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  AndData The value to AND with the PCI configuration register.\r
 \r
@@ -215,12 +236,21 @@ PciCf8And8 (
   IN      UINT8                     AndData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoAnd8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           AndData\r
-           );\r
+  Result = IoAnd8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             AndData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -238,7 +268,7 @@ PciCf8And8 (
   If Address > 0x0FFFFFFF, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  AndData The value to AND with the PCI configuration register.\r
   @param  OrData  The value to OR with the result of the AND operation.\r
@@ -254,13 +284,22 @@ PciCf8AndThenOr8 (
   IN      UINT8                     OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoAndThenOr8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           AndData,\r
-           OrData\r
-           );\r
+  Result = IoAndThenOr8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             AndData,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -276,7 +315,7 @@ PciCf8AndThenOr8 (
   If EndBit is greater than 7, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to read.\r
+  @param  Address   The PCI configuration register to read.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..7.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -293,13 +332,22 @@ PciCf8BitFieldRead8 (
   IN      UINTN                     EndBit\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldRead8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           StartBit,\r
-           EndBit\r
-           );\r
+  Result = IoBitFieldRead8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             StartBit,\r
+             EndBit\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -315,13 +363,14 @@ PciCf8BitFieldRead8 (
   If StartBit is greater than 7, then ASSERT().\r
   If EndBit is greater than 7, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..7.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
                     Range 0..7.\r
-  @param  Value     New value of the bit field.\r
+  @param  Value     The new value of the bit field.\r
 \r
   @return The value written back to the PCI configuration register.\r
 \r
@@ -335,14 +384,23 @@ PciCf8BitFieldWrite8 (
   IN      UINT8                     Value\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldWrite8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           StartBit,\r
-           EndBit,\r
-           Value\r
-           );\r
+  Result = IoBitFieldWrite8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             StartBit,\r
+             EndBit,\r
+             Value\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -361,8 +419,9 @@ PciCf8BitFieldWrite8 (
   If StartBit is greater than 7, then ASSERT().\r
   If EndBit is greater than 7, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..7.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -381,14 +440,23 @@ PciCf8BitFieldOr8 (
   IN      UINT8                     OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldOr8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           StartBit,\r
-           EndBit,\r
-           OrData\r
-           );\r
+  Result = IoBitFieldOr8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             StartBit,\r
+             EndBit,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -407,8 +475,9 @@ PciCf8BitFieldOr8 (
   If StartBit is greater than 7, then ASSERT().\r
   If EndBit is greater than 7, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..7.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -427,14 +496,23 @@ PciCf8BitFieldAnd8 (
   IN      UINT8                     AndData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldAnd8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           StartBit,\r
-           EndBit,\r
-           AndData\r
-           );\r
+  Result = IoBitFieldAnd8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             StartBit,\r
+             EndBit,\r
+             AndData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -455,8 +533,10 @@ PciCf8BitFieldAnd8 (
   If StartBit is greater than 7, then ASSERT().\r
   If EndBit is greater than 7, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
+  If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..7.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -477,15 +557,24 @@ PciCf8BitFieldAndThenOr8(
   IN      UINT8                     OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT8    Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 0);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldAndThenOr8 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
-           StartBit,\r
-           EndBit,\r
-           AndData,\r
-           OrData\r
-           );\r
+  Result = IoBitFieldAndThenOr8 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 3),\r
+             StartBit,\r
+             EndBit,\r
+             AndData,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -499,7 +588,7 @@ PciCf8BitFieldAndThenOr8(
   If Address is not aligned on a 16-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
 \r
   @return The read value from the PCI configuration register.\r
@@ -511,9 +600,18 @@ PciCf8Read16 (
   IN      UINTN                     Address\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoRead16 (PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2));\r
+  Result = IoRead16 (PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2));\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -527,7 +625,7 @@ PciCf8Read16 (
   If Address is not aligned on a 16-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  Value   The value to write.\r
 \r
@@ -541,12 +639,21 @@ PciCf8Write16 (
   IN      UINT16                    Value\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoWrite16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           Value\r
-           );\r
+  Result = IoWrite16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             Value\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -564,7 +671,7 @@ PciCf8Write16 (
   If Address is not aligned on a 16-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  OrData  The value to OR with the PCI configuration register.\r
 \r
@@ -578,12 +685,21 @@ PciCf8Or16 (
   IN      UINT16                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoOr16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           OrData\r
-           );\r
+  Result = IoOr16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -601,7 +717,7 @@ PciCf8Or16 (
   If Address is not aligned on a 16-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  AndData The value to AND with the PCI configuration register.\r
 \r
@@ -615,12 +731,21 @@ PciCf8And16 (
   IN      UINT16                    AndData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoAnd16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           AndData\r
-           );\r
+  Result = IoAnd16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             AndData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -639,7 +764,7 @@ PciCf8And16 (
   If Address is not aligned on a 16-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  AndData The value to AND with the PCI configuration register.\r
   @param  OrData  The value to OR with the result of the AND operation.\r
@@ -655,13 +780,22 @@ PciCf8AndThenOr16 (
   IN      UINT16                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoAndThenOr16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           AndData,\r
-           OrData\r
-           );\r
+  Result = IoAndThenOr16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             AndData,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -678,7 +812,7 @@ PciCf8AndThenOr16 (
   If EndBit is greater than 15, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to read.\r
+  @param  Address   The PCI configuration register to read.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..15.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -695,13 +829,22 @@ PciCf8BitFieldRead16 (
   IN      UINTN                     EndBit\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldRead16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           StartBit,\r
-           EndBit\r
-           );\r
+  Result = IoBitFieldRead16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             StartBit,\r
+             EndBit\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -718,13 +861,14 @@ PciCf8BitFieldRead16 (
   If StartBit is greater than 15, then ASSERT().\r
   If EndBit is greater than 15, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..15.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
                     Range 0..15.\r
-  @param  Value     New value of the bit field.\r
+  @param  Value     The new value of the bit field.\r
 \r
   @return The value written back to the PCI configuration register.\r
 \r
@@ -738,14 +882,23 @@ PciCf8BitFieldWrite16 (
   IN      UINT16                    Value\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldWrite16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           StartBit,\r
-           EndBit,\r
-           Value\r
-           );\r
+  Result = IoBitFieldWrite16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             StartBit,\r
+             EndBit,\r
+             Value\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -765,8 +918,9 @@ PciCf8BitFieldWrite16 (
   If StartBit is greater than 15, then ASSERT().\r
   If EndBit is greater than 15, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..15.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -785,14 +939,23 @@ PciCf8BitFieldOr16 (
   IN      UINT16                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldOr16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           StartBit,\r
-           EndBit,\r
-           OrData\r
-           );\r
+  Result = IoBitFieldOr16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             StartBit,\r
+             EndBit,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -812,8 +975,9 @@ PciCf8BitFieldOr16 (
   If StartBit is greater than 15, then ASSERT().\r
   If EndBit is greater than 15, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..15.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -832,14 +996,23 @@ PciCf8BitFieldAnd16 (
   IN      UINT16                    AndData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldAnd16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           StartBit,\r
-           EndBit,\r
-           AndData\r
-           );\r
+  Result = IoBitFieldAnd16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             StartBit,\r
+             EndBit,\r
+             AndData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -861,8 +1034,10 @@ PciCf8BitFieldAnd16 (
   If StartBit is greater than 15, then ASSERT().\r
   If EndBit is greater than 15, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
+  If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..15.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -883,15 +1058,24 @@ PciCf8BitFieldAndThenOr16(
   IN      UINT16                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT16   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 1);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldAndThenOr16 (\r
-           PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
-           StartBit,\r
-           EndBit,\r
-           AndData,\r
-           OrData\r
-           );\r
+  Result = IoBitFieldAndThenOr16 (\r
+             PCI_CONFIGURATION_DATA_PORT + (UINT16)(Address & 2),\r
+             StartBit,\r
+             EndBit,\r
+             AndData,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -905,7 +1089,7 @@ PciCf8BitFieldAndThenOr16(
   If Address is not aligned on a 32-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
 \r
   @return The read value from the PCI configuration register.\r
@@ -917,9 +1101,18 @@ PciCf8Read32 (
   IN      UINTN                     Address\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoRead32 (PCI_CONFIGURATION_DATA_PORT);\r
+  Result = IoRead32 (PCI_CONFIGURATION_DATA_PORT);\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -933,7 +1126,7 @@ PciCf8Read32 (
   If Address is not aligned on a 32-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  Value   The value to write.\r
 \r
@@ -947,12 +1140,21 @@ PciCf8Write32 (
   IN      UINT32                    Value\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoWrite32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           Value\r
-           );\r
+  Result = IoWrite32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             Value\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -970,7 +1172,7 @@ PciCf8Write32 (
   If Address is not aligned on a 32-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  OrData  The value to OR with the PCI configuration register.\r
 \r
@@ -984,12 +1186,21 @@ PciCf8Or32 (
   IN      UINT32                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoOr32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           OrData\r
-           );\r
+  Result = IoOr32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1007,7 +1218,7 @@ PciCf8Or32 (
   If Address is not aligned on a 32-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  AndData The value to AND with the PCI configuration register.\r
 \r
@@ -1021,12 +1232,21 @@ PciCf8And32 (
   IN      UINT32                    AndData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoAnd32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           AndData\r
-           );\r
+  Result = IoAnd32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             AndData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1045,7 +1265,7 @@ PciCf8And32 (
   If Address is not aligned on a 32-bit boundary, then ASSERT().\r
   If the register specified by Address >= 0x100, then ASSERT().\r
 \r
-  @param  Address Address that encodes the PCI Bus, Device, Function and\r
+  @param  Address The address that encodes the PCI Bus, Device, Function and\r
                   Register.\r
   @param  AndData The value to AND with the PCI configuration register.\r
   @param  OrData  The value to OR with the result of the AND operation.\r
@@ -1061,13 +1281,22 @@ PciCf8AndThenOr32 (
   IN      UINT32                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoAndThenOr32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           AndData,\r
-           OrData\r
-           );\r
+  Result = IoAndThenOr32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             AndData,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1084,7 +1313,7 @@ PciCf8AndThenOr32 (
   If EndBit is greater than 31, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to read.\r
+  @param  Address   The PCI configuration register to read.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..31.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -1101,13 +1330,22 @@ PciCf8BitFieldRead32 (
   IN      UINTN                     EndBit\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldRead32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           StartBit,\r
-           EndBit\r
-           );\r
+  Result = IoBitFieldRead32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             StartBit,\r
+             EndBit\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1124,13 +1362,14 @@ PciCf8BitFieldRead32 (
   If StartBit is greater than 31, then ASSERT().\r
   If EndBit is greater than 31, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..31.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
                     Range 0..31.\r
-  @param  Value     New value of the bit field.\r
+  @param  Value     The new value of the bit field.\r
 \r
   @return The value written back to the PCI configuration register.\r
 \r
@@ -1144,14 +1383,23 @@ PciCf8BitFieldWrite32 (
   IN      UINT32                    Value\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldWrite32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           StartBit,\r
-           EndBit,\r
-           Value\r
-           );\r
+  Result = IoBitFieldWrite32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             StartBit,\r
+             EndBit,\r
+             Value\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1171,8 +1419,9 @@ PciCf8BitFieldWrite32 (
   If StartBit is greater than 31, then ASSERT().\r
   If EndBit is greater than 31, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..31.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -1191,14 +1440,23 @@ PciCf8BitFieldOr32 (
   IN      UINT32                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldOr32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           StartBit,\r
-           EndBit,\r
-           OrData\r
-           );\r
+  Result = IoBitFieldOr32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             StartBit,\r
+             EndBit,\r
+             OrData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1218,8 +1476,9 @@ PciCf8BitFieldOr32 (
   If StartBit is greater than 31, then ASSERT().\r
   If EndBit is greater than 31, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..31.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -1238,14 +1497,23 @@ PciCf8BitFieldAnd32 (
   IN      UINT32                    AndData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldAnd32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           StartBit,\r
-           EndBit,\r
-           AndData\r
-           );\r
+  Result = IoBitFieldAnd32 (\r
+             PCI_CONFIGURATION_DATA_PORT,\r
+             StartBit,\r
+             EndBit,\r
+             AndData\r
+             );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1267,8 +1535,10 @@ PciCf8BitFieldAnd32 (
   If StartBit is greater than 31, then ASSERT().\r
   If EndBit is greater than 31, then ASSERT().\r
   If EndBit is less than StartBit, then ASSERT().\r
+  If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
+  If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().\r
 \r
-  @param  Address   PCI configuration register to write.\r
+  @param  Address   The PCI configuration register to write.\r
   @param  StartBit  The ordinal of the least significant bit in the bit field.\r
                     Range 0..31.\r
   @param  EndBit    The ordinal of the most significant bit in the bit field.\r
@@ -1289,15 +1559,24 @@ PciCf8BitFieldAndThenOr32(
   IN      UINT32                    OrData\r
   )\r
 {\r
+  BOOLEAN  InterruptState;\r
+  UINT32   AddressPort;\r
+  UINT32   Result;\r
+\r
   ASSERT_INVALID_PCI_ADDRESS (Address, 3);\r
+  InterruptState = SaveAndDisableInterrupts ();\r
+  AddressPort = IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT);\r
   IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, PCI_TO_CF8_ADDRESS (Address));\r
-  return IoBitFieldAndThenOr32 (\r
-           PCI_CONFIGURATION_DATA_PORT,\r
-           StartBit,\r
-           EndBit,\r
-           AndData,\r
-           OrData\r
-           );\r
+  Result = IoBitFieldAndThenOr32 (\r
+               PCI_CONFIGURATION_DATA_PORT,\r
+               StartBit,\r
+               EndBit,\r
+               AndData,\r
+               OrData\r
+               );\r
+  IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT, AddressPort);\r
+  SetInterruptState (InterruptState);\r
+  return Result;\r
 }\r
 \r
 /**\r
@@ -1316,10 +1595,10 @@ PciCf8BitFieldAndThenOr32(
   If ((StartAddress & 0xFFF) + Size) > 0x100, then ASSERT().\r
   If Size > 0 and Buffer is NULL, then ASSERT().\r
 \r
-  @param  StartAddress  Starting address that encodes the PCI Bus, Device,\r
+  @param  StartAddress  The starting address that encodes the PCI Bus, Device,\r
                         Function and Register.\r
-  @param  Size          Size in bytes of the transfer.\r
-  @param  Buffer        Pointer to a buffer receiving the data read.\r
+  @param  Size          The size in bytes of the transfer.\r
+  @param  Buffer        The pointer to a buffer receiving the data read.\r
 \r
   @return Size read from StartAddress.\r
 \r
@@ -1416,10 +1695,10 @@ PciCf8ReadBuffer (
   If ((StartAddress & 0xFFF) + Size) > 0x100, then ASSERT().\r
   If Size > 0 and Buffer is NULL, then ASSERT().\r
 \r
-  @param  StartAddress  Starting address that encodes the PCI Bus, Device,\r
+  @param  StartAddress  The starting address that encodes the PCI Bus, Device,\r
                         Function and Register.\r
-  @param  Size          Size in bytes of the transfer.\r
-  @param  Buffer        Pointer to a buffer containing the data to write.\r
+  @param  Size          The size in bytes of the transfer.\r
+  @param  Buffer        The pointer to a buffer containing the data to write.\r
 \r
   @return Size written to StartAddress.\r
 \r