2 PCI CF8 Library functions that use I/O ports 0xCF8 and 0xCFC to perform PCI Configuration cycles.
3 Layers on top of an I/O Library instance.
5 Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
6 SPDX-License-Identifier: BSD-2-Clause-Patent
12 #include <Library/BaseLib.h>
13 #include <Library/PciCf8Lib.h>
14 #include <Library/IoLib.h>
15 #include <Library/DebugLib.h>
18 // Declare I/O Ports used to perform PCI Confguration Cycles
20 #define PCI_CONFIGURATION_ADDRESS_PORT 0xCF8
21 #define PCI_CONFIGURATION_DATA_PORT 0xCFC
24 Convert a PCI Library address to PCI CF8 formatted address.
26 Declare macro to convert PCI Library address to PCI CF8 formatted address.
27 Bit fields of PCI Library and CF8 formatted address is as follows:
28 PCI Library formatted address CF8 Formatted Address
29 ============================= ======================
30 Bits 00..11 Register Bits 00..07 Register
31 Bits 12..14 Function Bits 08..10 Function
32 Bits 15..19 Device Bits 11..15 Device
33 Bits 20..27 Bus Bits 16..23 Bus
34 Bits 28..31 Reserved(MBZ) Bits 24..30 Reserved(MBZ)
37 @param A The address to convert.
39 @retval The coverted address.
42 #define PCI_TO_CF8_ADDRESS(A) \
43 ((UINT32) ((((A) >> 4) & 0x00ffff00) | ((A) & 0xfc) | 0x80000000))
46 Assert the validity of a PCI CF8 address. A valid PCI CF8 address should contain 1's
47 only in the low 28 bits, excluding bits 08..11.
49 @param A The address to validate.
50 @param M Additional bits to assert to be zero.
53 #define ASSERT_INVALID_PCI_ADDRESS(A, M) \
54 ASSERT (((A) & (~0xffff0ff | (M))) == 0)
57 Registers a PCI device so PCI configuration registers may be accessed after
58 SetVirtualAddressMap().
60 Registers the PCI device specified by Address so all the PCI configuration registers
61 associated with that PCI device may be accessed after SetVirtualAddressMap() is called.
63 If Address > 0x0FFFFFFF, then ASSERT().
64 If the register specified by Address >= 0x100, then ASSERT().
66 @param Address The address that encodes the PCI Bus, Device, Function and
69 @retval RETURN_SUCCESS The PCI device was registered for runtime access.
70 @retval RETURN_UNSUPPORTED An attempt was made to call this function
71 after ExitBootServices().
72 @retval RETURN_UNSUPPORTED The resources required to access the PCI device
73 at runtime could not be mapped.
74 @retval RETURN_OUT_OF_RESOURCES There are not enough resources available to
75 complete the registration.
80 PciCf8RegisterForRuntimeAccess (
84 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
85 return RETURN_SUCCESS
;
89 Reads an 8-bit PCI configuration register.
91 Reads and returns the 8-bit PCI configuration register specified by Address.
92 This function must guarantee that all PCI read and write operations are
95 If Address > 0x0FFFFFFF, then ASSERT().
96 If the register specified by Address >= 0x100, then ASSERT().
98 @param Address The address that encodes the PCI Bus, Device, Function and
101 @return The read value from the PCI configuration register.
110 BOOLEAN InterruptState
;
114 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
115 InterruptState
= SaveAndDisableInterrupts ();
116 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
117 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
118 Result
= IoRead8 (PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3));
119 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
120 SetInterruptState (InterruptState
);
125 Writes an 8-bit PCI configuration register.
127 Writes the 8-bit PCI configuration register specified by Address with the
128 value specified by Value. Value is returned. This function must guarantee
129 that all PCI read and write operations are serialized.
131 If Address > 0x0FFFFFFF, then ASSERT().
132 If the register specified by Address >= 0x100, then ASSERT().
134 @param Address The address that encodes the PCI Bus, Device, Function and
136 @param Value The value to write.
138 @return The value written to the PCI configuration register.
148 BOOLEAN InterruptState
;
152 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
153 InterruptState
= SaveAndDisableInterrupts ();
154 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
155 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
157 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
160 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
161 SetInterruptState (InterruptState
);
166 Performs a bitwise OR of an 8-bit PCI configuration register with
169 Reads the 8-bit PCI configuration register specified by Address, performs a
170 bitwise OR between the read result and the value specified by
171 OrData, and writes the result to the 8-bit PCI configuration register
172 specified by Address. The value written to the PCI configuration register is
173 returned. This function must guarantee that all PCI read and write operations
176 If Address > 0x0FFFFFFF, then ASSERT().
177 If the register specified by Address >= 0x100, then ASSERT().
179 @param Address The address that encodes the PCI Bus, Device, Function and
181 @param OrData The value to OR with the PCI configuration register.
183 @return The value written back to the PCI configuration register.
193 BOOLEAN InterruptState
;
197 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
198 InterruptState
= SaveAndDisableInterrupts ();
199 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
200 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
202 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
205 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
206 SetInterruptState (InterruptState
);
211 Performs a bitwise AND of an 8-bit PCI configuration register with an 8-bit
214 Reads the 8-bit PCI configuration register specified by Address, performs a
215 bitwise AND between the read result and the value specified by AndData, and
216 writes the result to the 8-bit PCI configuration register specified by
217 Address. The value written to the PCI configuration register is returned.
218 This function must guarantee that all PCI read and write operations are
221 If Address > 0x0FFFFFFF, then ASSERT().
222 If the register specified by Address >= 0x100, then ASSERT().
224 @param Address The address that encodes the PCI Bus, Device, Function and
226 @param AndData The value to AND with the PCI configuration register.
228 @return The value written back to the PCI configuration register.
238 BOOLEAN InterruptState
;
242 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
243 InterruptState
= SaveAndDisableInterrupts ();
244 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
245 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
247 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
250 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
251 SetInterruptState (InterruptState
);
256 Performs a bitwise AND of an 8-bit PCI configuration register with an 8-bit
257 value, followed a bitwise OR with another 8-bit value.
259 Reads the 8-bit PCI configuration register specified by Address, performs a
260 bitwise AND between the read result and the value specified by AndData,
261 performs a bitwise OR between the result of the AND operation and
262 the value specified by OrData, and writes the result to the 8-bit PCI
263 configuration register specified by Address. The value written to the PCI
264 configuration register is returned. This function must guarantee that all PCI
265 read and write operations are serialized.
267 If Address > 0x0FFFFFFF, then ASSERT().
268 If the register specified by Address >= 0x100, then ASSERT().
270 @param Address The address that encodes the PCI Bus, Device, Function and
272 @param AndData The value to AND with the PCI configuration register.
273 @param OrData The value to OR with the result of the AND operation.
275 @return The value written back to the PCI configuration register.
286 BOOLEAN InterruptState
;
290 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
291 InterruptState
= SaveAndDisableInterrupts ();
292 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
293 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
294 Result
= IoAndThenOr8 (
295 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
299 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
300 SetInterruptState (InterruptState
);
305 Reads a bit field of a PCI configuration register.
307 Reads the bit field in an 8-bit PCI configuration register. The bit field is
308 specified by the StartBit and the EndBit. The value of the bit field is
311 If Address > 0x0FFFFFFF, then ASSERT().
312 If the register specified by Address >= 0x100, then ASSERT().
313 If StartBit is greater than 7, then ASSERT().
314 If EndBit is greater than 7, then ASSERT().
315 If EndBit is less than StartBit, then ASSERT().
317 @param Address The PCI configuration register to read.
318 @param StartBit The ordinal of the least significant bit in the bit field.
320 @param EndBit The ordinal of the most significant bit in the bit field.
323 @return The value of the bit field read from the PCI configuration register.
328 PciCf8BitFieldRead8 (
334 BOOLEAN InterruptState
;
338 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
339 InterruptState
= SaveAndDisableInterrupts ();
340 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
341 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
342 Result
= IoBitFieldRead8 (
343 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
347 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
348 SetInterruptState (InterruptState
);
353 Writes a bit field to a PCI configuration register.
355 Writes Value to the bit field of the PCI configuration register. The bit
356 field is specified by the StartBit and the EndBit. All other bits in the
357 destination PCI configuration register are preserved. The new value of the
358 8-bit register is returned.
360 If Address > 0x0FFFFFFF, then ASSERT().
361 If the register specified by Address >= 0x100, then ASSERT().
362 If StartBit is greater than 7, then ASSERT().
363 If EndBit is greater than 7, then ASSERT().
364 If EndBit is less than StartBit, then ASSERT().
365 If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
367 @param Address The PCI configuration register to write.
368 @param StartBit The ordinal of the least significant bit in the bit field.
370 @param EndBit The ordinal of the most significant bit in the bit field.
372 @param Value The new value of the bit field.
374 @return The value written back to the PCI configuration register.
379 PciCf8BitFieldWrite8 (
386 BOOLEAN InterruptState
;
390 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
391 InterruptState
= SaveAndDisableInterrupts ();
392 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
393 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
394 Result
= IoBitFieldWrite8 (
395 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
400 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
401 SetInterruptState (InterruptState
);
406 Reads a bit field in an 8-bit PCI configuration, performs a bitwise OR, and
407 writes the result back to the bit field in the 8-bit port.
409 Reads the 8-bit PCI configuration register specified by Address, performs a
410 bitwise OR between the read result and the value specified by
411 OrData, and writes the result to the 8-bit PCI configuration register
412 specified by Address. The value written to the PCI configuration register is
413 returned. This function must guarantee that all PCI read and write operations
414 are serialized. Extra left bits in OrData are stripped.
416 If Address > 0x0FFFFFFF, then ASSERT().
417 If the register specified by Address >= 0x100, then ASSERT().
418 If StartBit is greater than 7, then ASSERT().
419 If EndBit is greater than 7, then ASSERT().
420 If EndBit is less than StartBit, then ASSERT().
421 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
423 @param Address The PCI configuration register to write.
424 @param StartBit The ordinal of the least significant bit in the bit field.
426 @param EndBit The ordinal of the most significant bit in the bit field.
428 @param OrData The value to OR with the PCI configuration register.
430 @return The value written back to the PCI configuration register.
442 BOOLEAN InterruptState
;
446 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
447 InterruptState
= SaveAndDisableInterrupts ();
448 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
449 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
450 Result
= IoBitFieldOr8 (
451 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
456 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
457 SetInterruptState (InterruptState
);
462 Reads a bit field in an 8-bit PCI configuration register, performs a bitwise
463 AND, and writes the result back to the bit field in the 8-bit register.
465 Reads the 8-bit PCI configuration register specified by Address, performs a
466 bitwise AND between the read result and the value specified by AndData, and
467 writes the result to the 8-bit PCI configuration register specified by
468 Address. The value written to the PCI configuration register is returned.
469 This function must guarantee that all PCI read and write operations are
470 serialized. Extra left bits in AndData are stripped.
472 If Address > 0x0FFFFFFF, then ASSERT().
473 If the register specified by Address >= 0x100, then ASSERT().
474 If StartBit is greater than 7, then ASSERT().
475 If EndBit is greater than 7, then ASSERT().
476 If EndBit is less than StartBit, then ASSERT().
477 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
479 @param Address The PCI configuration register to write.
480 @param StartBit The ordinal of the least significant bit in the bit field.
482 @param EndBit The ordinal of the most significant bit in the bit field.
484 @param AndData The value to AND with the PCI configuration register.
486 @return The value written back to the PCI configuration register.
498 BOOLEAN InterruptState
;
502 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
503 InterruptState
= SaveAndDisableInterrupts ();
504 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
505 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
506 Result
= IoBitFieldAnd8 (
507 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
512 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
513 SetInterruptState (InterruptState
);
518 Reads a bit field in an 8-bit port, performs a bitwise AND followed by a
519 bitwise OR, and writes the result back to the bit field in the
522 Reads the 8-bit PCI configuration register specified by Address, performs a
523 bitwise AND followed by a bitwise OR between the read result and
524 the value specified by AndData, and writes the result to the 8-bit PCI
525 configuration register specified by Address. The value written to the PCI
526 configuration register is returned. This function must guarantee that all PCI
527 read and write operations are serialized. Extra left bits in both AndData and
530 If Address > 0x0FFFFFFF, then ASSERT().
531 If the register specified by Address >= 0x100, then ASSERT().
532 If StartBit is greater than 7, then ASSERT().
533 If EndBit is greater than 7, then ASSERT().
534 If EndBit is less than StartBit, then ASSERT().
535 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
536 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
538 @param Address The PCI configuration register to write.
539 @param StartBit The ordinal of the least significant bit in the bit field.
541 @param EndBit The ordinal of the most significant bit in the bit field.
543 @param AndData The value to AND with the PCI configuration register.
544 @param OrData The value to OR with the result of the AND operation.
546 @return The value written back to the PCI configuration register.
551 PciCf8BitFieldAndThenOr8 (
559 BOOLEAN InterruptState
;
563 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
564 InterruptState
= SaveAndDisableInterrupts ();
565 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
566 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
567 Result
= IoBitFieldAndThenOr8 (
568 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
574 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
575 SetInterruptState (InterruptState
);
580 Reads a 16-bit PCI configuration register.
582 Reads and returns the 16-bit PCI configuration register specified by Address.
583 This function must guarantee that all PCI read and write operations are
586 If Address > 0x0FFFFFFF, then ASSERT().
587 If Address is not aligned on a 16-bit boundary, then ASSERT().
588 If the register specified by Address >= 0x100, then ASSERT().
590 @param Address The address that encodes the PCI Bus, Device, Function and
593 @return The read value from the PCI configuration register.
602 BOOLEAN InterruptState
;
606 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
607 InterruptState
= SaveAndDisableInterrupts ();
608 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
609 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
610 Result
= IoRead16 (PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2));
611 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
612 SetInterruptState (InterruptState
);
617 Writes a 16-bit PCI configuration register.
619 Writes the 16-bit PCI configuration register specified by Address with the
620 value specified by Value. Value is returned. This function must guarantee
621 that all PCI read and write operations are serialized.
623 If Address > 0x0FFFFFFF, then ASSERT().
624 If Address is not aligned on a 16-bit boundary, then ASSERT().
625 If the register specified by Address >= 0x100, then ASSERT().
627 @param Address The address that encodes the PCI Bus, Device, Function and
629 @param Value The value to write.
631 @return The value written to the PCI configuration register.
641 BOOLEAN InterruptState
;
645 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
646 InterruptState
= SaveAndDisableInterrupts ();
647 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
648 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
650 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
653 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
654 SetInterruptState (InterruptState
);
659 Performs a bitwise OR of a 16-bit PCI configuration register with
662 Reads the 16-bit PCI configuration register specified by Address, performs a
663 bitwise OR between the read result and the value specified by
664 OrData, and writes the result to the 16-bit PCI configuration register
665 specified by Address. The value written to the PCI configuration register is
666 returned. This function must guarantee that all PCI read and write operations
669 If Address > 0x0FFFFFFF, then ASSERT().
670 If Address is not aligned on a 16-bit boundary, then ASSERT().
671 If the register specified by Address >= 0x100, then ASSERT().
673 @param Address The address that encodes the PCI Bus, Device, Function and
675 @param OrData The value to OR with the PCI configuration register.
677 @return The value written back to the PCI configuration register.
687 BOOLEAN InterruptState
;
691 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
692 InterruptState
= SaveAndDisableInterrupts ();
693 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
694 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
696 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
699 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
700 SetInterruptState (InterruptState
);
705 Performs a bitwise AND of a 16-bit PCI configuration register with a 16-bit
708 Reads the 16-bit PCI configuration register specified by Address, performs a
709 bitwise AND between the read result and the value specified by AndData, and
710 writes the result to the 16-bit PCI configuration register specified by
711 Address. The value written to the PCI configuration register is returned.
712 This function must guarantee that all PCI read and write operations are
715 If Address > 0x0FFFFFFF, then ASSERT().
716 If Address is not aligned on a 16-bit boundary, then ASSERT().
717 If the register specified by Address >= 0x100, then ASSERT().
719 @param Address The address that encodes the PCI Bus, Device, Function and
721 @param AndData The value to AND with the PCI configuration register.
723 @return The value written back to the PCI configuration register.
733 BOOLEAN InterruptState
;
737 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
738 InterruptState
= SaveAndDisableInterrupts ();
739 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
740 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
742 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
745 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
746 SetInterruptState (InterruptState
);
751 Performs a bitwise AND of a 16-bit PCI configuration register with a 16-bit
752 value, followed a bitwise OR with another 16-bit value.
754 Reads the 16-bit PCI configuration register specified by Address, performs a
755 bitwise AND between the read result and the value specified by AndData,
756 performs a bitwise OR between the result of the AND operation and
757 the value specified by OrData, and writes the result to the 16-bit PCI
758 configuration register specified by Address. The value written to the PCI
759 configuration register is returned. This function must guarantee that all PCI
760 read and write operations are serialized.
762 If Address > 0x0FFFFFFF, then ASSERT().
763 If Address is not aligned on a 16-bit boundary, then ASSERT().
764 If the register specified by Address >= 0x100, then ASSERT().
766 @param Address The address that encodes the PCI Bus, Device, Function and
768 @param AndData The value to AND with the PCI configuration register.
769 @param OrData The value to OR with the result of the AND operation.
771 @return The value written back to the PCI configuration register.
782 BOOLEAN InterruptState
;
786 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
787 InterruptState
= SaveAndDisableInterrupts ();
788 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
789 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
790 Result
= IoAndThenOr16 (
791 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
795 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
796 SetInterruptState (InterruptState
);
801 Reads a bit field of a PCI configuration register.
803 Reads the bit field in a 16-bit PCI configuration register. The bit field is
804 specified by the StartBit and the EndBit. The value of the bit field is
807 If Address > 0x0FFFFFFF, then ASSERT().
808 If Address is not aligned on a 16-bit boundary, then ASSERT().
809 If the register specified by Address >= 0x100, then ASSERT().
810 If StartBit is greater than 15, then ASSERT().
811 If EndBit is greater than 15, then ASSERT().
812 If EndBit is less than StartBit, then ASSERT().
814 @param Address The PCI configuration register to read.
815 @param StartBit The ordinal of the least significant bit in the bit field.
817 @param EndBit The ordinal of the most significant bit in the bit field.
820 @return The value of the bit field read from the PCI configuration register.
825 PciCf8BitFieldRead16 (
831 BOOLEAN InterruptState
;
835 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
836 InterruptState
= SaveAndDisableInterrupts ();
837 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
838 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
839 Result
= IoBitFieldRead16 (
840 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
844 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
845 SetInterruptState (InterruptState
);
850 Writes a bit field to a PCI configuration register.
852 Writes Value to the bit field of the PCI configuration register. The bit
853 field is specified by the StartBit and the EndBit. All other bits in the
854 destination PCI configuration register are preserved. The new value of the
855 16-bit register is returned.
857 If Address > 0x0FFFFFFF, then ASSERT().
858 If Address is not aligned on a 16-bit boundary, then ASSERT().
859 If the register specified by Address >= 0x100, then ASSERT().
860 If StartBit is greater than 15, then ASSERT().
861 If EndBit is greater than 15, then ASSERT().
862 If EndBit is less than StartBit, then ASSERT().
863 If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
865 @param Address The PCI configuration register to write.
866 @param StartBit The ordinal of the least significant bit in the bit field.
868 @param EndBit The ordinal of the most significant bit in the bit field.
870 @param Value The new value of the bit field.
872 @return The value written back to the PCI configuration register.
877 PciCf8BitFieldWrite16 (
884 BOOLEAN InterruptState
;
888 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
889 InterruptState
= SaveAndDisableInterrupts ();
890 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
891 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
892 Result
= IoBitFieldWrite16 (
893 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
898 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
899 SetInterruptState (InterruptState
);
904 Reads a bit field in a 16-bit PCI configuration, performs a bitwise OR, and
905 writes the result back to the bit field in the 16-bit port.
907 Reads the 16-bit PCI configuration register specified by Address, performs a
908 bitwise OR between the read result and the value specified by
909 OrData, and writes the result to the 16-bit PCI configuration register
910 specified by Address. The value written to the PCI configuration register is
911 returned. This function must guarantee that all PCI read and write operations
912 are serialized. Extra left bits in OrData are stripped.
914 If Address > 0x0FFFFFFF, then ASSERT().
915 If Address is not aligned on a 16-bit boundary, then ASSERT().
916 If the register specified by Address >= 0x100, then ASSERT().
917 If StartBit is greater than 15, then ASSERT().
918 If EndBit is greater than 15, then ASSERT().
919 If EndBit is less than StartBit, then ASSERT().
920 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
922 @param Address The PCI configuration register to write.
923 @param StartBit The ordinal of the least significant bit in the bit field.
925 @param EndBit The ordinal of the most significant bit in the bit field.
927 @param OrData The value to OR with the PCI configuration register.
929 @return The value written back to the PCI configuration register.
941 BOOLEAN InterruptState
;
945 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
946 InterruptState
= SaveAndDisableInterrupts ();
947 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
948 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
949 Result
= IoBitFieldOr16 (
950 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
955 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
956 SetInterruptState (InterruptState
);
961 Reads a bit field in a 16-bit PCI configuration register, performs a bitwise
962 AND, and writes the result back to the bit field in the 16-bit register.
964 Reads the 16-bit PCI configuration register specified by Address, performs a
965 bitwise AND between the read result and the value specified by AndData, and
966 writes the result to the 16-bit PCI configuration register specified by
967 Address. The value written to the PCI configuration register is returned.
968 This function must guarantee that all PCI read and write operations are
969 serialized. Extra left bits in AndData are stripped.
971 If Address > 0x0FFFFFFF, then ASSERT().
972 If Address is not aligned on a 16-bit boundary, then ASSERT().
973 If the register specified by Address >= 0x100, then ASSERT().
974 If StartBit is greater than 15, then ASSERT().
975 If EndBit is greater than 15, then ASSERT().
976 If EndBit is less than StartBit, then ASSERT().
977 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
979 @param Address The PCI configuration register to write.
980 @param StartBit The ordinal of the least significant bit in the bit field.
982 @param EndBit The ordinal of the most significant bit in the bit field.
984 @param AndData The value to AND with the PCI configuration register.
986 @return The value written back to the PCI configuration register.
991 PciCf8BitFieldAnd16 (
998 BOOLEAN InterruptState
;
1002 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
1003 InterruptState
= SaveAndDisableInterrupts ();
1004 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1005 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1006 Result
= IoBitFieldAnd16 (
1007 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
1012 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1013 SetInterruptState (InterruptState
);
1018 Reads a bit field in a 16-bit port, performs a bitwise AND followed by a
1019 bitwise OR, and writes the result back to the bit field in the
1022 Reads the 16-bit PCI configuration register specified by Address, performs a
1023 bitwise AND followed by a bitwise OR between the read result and
1024 the value specified by AndData, and writes the result to the 16-bit PCI
1025 configuration register specified by Address. The value written to the PCI
1026 configuration register is returned. This function must guarantee that all PCI
1027 read and write operations are serialized. Extra left bits in both AndData and
1028 OrData are stripped.
1030 If Address > 0x0FFFFFFF, then ASSERT().
1031 If Address is not aligned on a 16-bit boundary, then ASSERT().
1032 If the register specified by Address >= 0x100, then ASSERT().
1033 If StartBit is greater than 15, then ASSERT().
1034 If EndBit is greater than 15, then ASSERT().
1035 If EndBit is less than StartBit, then ASSERT().
1036 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1037 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1039 @param Address The PCI configuration register to write.
1040 @param StartBit The ordinal of the least significant bit in the bit field.
1042 @param EndBit The ordinal of the most significant bit in the bit field.
1044 @param AndData The value to AND with the PCI configuration register.
1045 @param OrData The value to OR with the result of the AND operation.
1047 @return The value written back to the PCI configuration register.
1052 PciCf8BitFieldAndThenOr16 (
1060 BOOLEAN InterruptState
;
1064 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
1065 InterruptState
= SaveAndDisableInterrupts ();
1066 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1067 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1068 Result
= IoBitFieldAndThenOr16 (
1069 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
1075 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1076 SetInterruptState (InterruptState
);
1081 Reads a 32-bit PCI configuration register.
1083 Reads and returns the 32-bit PCI configuration register specified by Address.
1084 This function must guarantee that all PCI read and write operations are
1087 If Address > 0x0FFFFFFF, then ASSERT().
1088 If Address is not aligned on a 32-bit boundary, then ASSERT().
1089 If the register specified by Address >= 0x100, then ASSERT().
1091 @param Address The address that encodes the PCI Bus, Device, Function and
1094 @return The read value from the PCI configuration register.
1103 BOOLEAN InterruptState
;
1107 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1108 InterruptState
= SaveAndDisableInterrupts ();
1109 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1110 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1111 Result
= IoRead32 (PCI_CONFIGURATION_DATA_PORT
);
1112 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1113 SetInterruptState (InterruptState
);
1118 Writes a 32-bit PCI configuration register.
1120 Writes the 32-bit PCI configuration register specified by Address with the
1121 value specified by Value. Value is returned. This function must guarantee
1122 that all PCI read and write operations are serialized.
1124 If Address > 0x0FFFFFFF, then ASSERT().
1125 If Address is not aligned on a 32-bit boundary, then ASSERT().
1126 If the register specified by Address >= 0x100, then ASSERT().
1128 @param Address The address that encodes the PCI Bus, Device, Function and
1130 @param Value The value to write.
1132 @return The value written to the PCI configuration register.
1142 BOOLEAN InterruptState
;
1146 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1147 InterruptState
= SaveAndDisableInterrupts ();
1148 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1149 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1150 Result
= IoWrite32 (
1151 PCI_CONFIGURATION_DATA_PORT
,
1154 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1155 SetInterruptState (InterruptState
);
1160 Performs a bitwise OR of a 32-bit PCI configuration register with
1163 Reads the 32-bit PCI configuration register specified by Address, performs a
1164 bitwise OR between the read result and the value specified by
1165 OrData, and writes the result to the 32-bit PCI configuration register
1166 specified by Address. The value written to the PCI configuration register is
1167 returned. This function must guarantee that all PCI read and write operations
1170 If Address > 0x0FFFFFFF, then ASSERT().
1171 If Address is not aligned on a 32-bit boundary, then ASSERT().
1172 If the register specified by Address >= 0x100, then ASSERT().
1174 @param Address The address that encodes the PCI Bus, Device, Function and
1176 @param OrData The value to OR with the PCI configuration register.
1178 @return The value written back to the PCI configuration register.
1188 BOOLEAN InterruptState
;
1192 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1193 InterruptState
= SaveAndDisableInterrupts ();
1194 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1195 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1197 PCI_CONFIGURATION_DATA_PORT
,
1200 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1201 SetInterruptState (InterruptState
);
1206 Performs a bitwise AND of a 32-bit PCI configuration register with a 32-bit
1209 Reads the 32-bit PCI configuration register specified by Address, performs a
1210 bitwise AND between the read result and the value specified by AndData, and
1211 writes the result to the 32-bit PCI configuration register specified by
1212 Address. The value written to the PCI configuration register is returned.
1213 This function must guarantee that all PCI read and write operations are
1216 If Address > 0x0FFFFFFF, then ASSERT().
1217 If Address is not aligned on a 32-bit boundary, then ASSERT().
1218 If the register specified by Address >= 0x100, then ASSERT().
1220 @param Address The address that encodes the PCI Bus, Device, Function and
1222 @param AndData The value to AND with the PCI configuration register.
1224 @return The value written back to the PCI configuration register.
1234 BOOLEAN InterruptState
;
1238 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1239 InterruptState
= SaveAndDisableInterrupts ();
1240 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1241 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1243 PCI_CONFIGURATION_DATA_PORT
,
1246 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1247 SetInterruptState (InterruptState
);
1252 Performs a bitwise AND of a 32-bit PCI configuration register with a 32-bit
1253 value, followed a bitwise OR with another 32-bit value.
1255 Reads the 32-bit PCI configuration register specified by Address, performs a
1256 bitwise AND between the read result and the value specified by AndData,
1257 performs a bitwise OR between the result of the AND operation and
1258 the value specified by OrData, and writes the result to the 32-bit PCI
1259 configuration register specified by Address. The value written to the PCI
1260 configuration register is returned. This function must guarantee that all PCI
1261 read and write operations are serialized.
1263 If Address > 0x0FFFFFFF, then ASSERT().
1264 If Address is not aligned on a 32-bit boundary, then ASSERT().
1265 If the register specified by Address >= 0x100, then ASSERT().
1267 @param Address The address that encodes the PCI Bus, Device, Function and
1269 @param AndData The value to AND with the PCI configuration register.
1270 @param OrData The value to OR with the result of the AND operation.
1272 @return The value written back to the PCI configuration register.
1283 BOOLEAN InterruptState
;
1287 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1288 InterruptState
= SaveAndDisableInterrupts ();
1289 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1290 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1291 Result
= IoAndThenOr32 (
1292 PCI_CONFIGURATION_DATA_PORT
,
1296 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1297 SetInterruptState (InterruptState
);
1302 Reads a bit field of a PCI configuration register.
1304 Reads the bit field in a 32-bit PCI configuration register. The bit field is
1305 specified by the StartBit and the EndBit. The value of the bit field is
1308 If Address > 0x0FFFFFFF, then ASSERT().
1309 If Address is not aligned on a 32-bit boundary, then ASSERT().
1310 If the register specified by Address >= 0x100, then ASSERT().
1311 If StartBit is greater than 31, then ASSERT().
1312 If EndBit is greater than 31, then ASSERT().
1313 If EndBit is less than StartBit, then ASSERT().
1315 @param Address The PCI configuration register to read.
1316 @param StartBit The ordinal of the least significant bit in the bit field.
1318 @param EndBit The ordinal of the most significant bit in the bit field.
1321 @return The value of the bit field read from the PCI configuration register.
1326 PciCf8BitFieldRead32 (
1332 BOOLEAN InterruptState
;
1336 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1337 InterruptState
= SaveAndDisableInterrupts ();
1338 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1339 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1340 Result
= IoBitFieldRead32 (
1341 PCI_CONFIGURATION_DATA_PORT
,
1345 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1346 SetInterruptState (InterruptState
);
1351 Writes a bit field to a PCI configuration register.
1353 Writes Value to the bit field of the PCI configuration register. The bit
1354 field is specified by the StartBit and the EndBit. All other bits in the
1355 destination PCI configuration register are preserved. The new value of the
1356 32-bit register is returned.
1358 If Address > 0x0FFFFFFF, then ASSERT().
1359 If Address is not aligned on a 32-bit boundary, then ASSERT().
1360 If the register specified by Address >= 0x100, then ASSERT().
1361 If StartBit is greater than 31, then ASSERT().
1362 If EndBit is greater than 31, then ASSERT().
1363 If EndBit is less than StartBit, then ASSERT().
1364 If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1366 @param Address The PCI configuration register to write.
1367 @param StartBit The ordinal of the least significant bit in the bit field.
1369 @param EndBit The ordinal of the most significant bit in the bit field.
1371 @param Value The new value of the bit field.
1373 @return The value written back to the PCI configuration register.
1378 PciCf8BitFieldWrite32 (
1385 BOOLEAN InterruptState
;
1389 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1390 InterruptState
= SaveAndDisableInterrupts ();
1391 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1392 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1393 Result
= IoBitFieldWrite32 (
1394 PCI_CONFIGURATION_DATA_PORT
,
1399 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1400 SetInterruptState (InterruptState
);
1405 Reads a bit field in a 32-bit PCI configuration, performs a bitwise OR, and
1406 writes the result back to the bit field in the 32-bit port.
1408 Reads the 32-bit PCI configuration register specified by Address, performs a
1409 bitwise OR between the read result and the value specified by
1410 OrData, and writes the result to the 32-bit PCI configuration register
1411 specified by Address. The value written to the PCI configuration register is
1412 returned. This function must guarantee that all PCI read and write operations
1413 are serialized. Extra left bits in OrData are stripped.
1415 If Address > 0x0FFFFFFF, then ASSERT().
1416 If Address is not aligned on a 32-bit boundary, then ASSERT().
1417 If the register specified by Address >= 0x100, then ASSERT().
1418 If StartBit is greater than 31, then ASSERT().
1419 If EndBit is greater than 31, then ASSERT().
1420 If EndBit is less than StartBit, then ASSERT().
1421 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1423 @param Address The PCI configuration register to write.
1424 @param StartBit The ordinal of the least significant bit in the bit field.
1426 @param EndBit The ordinal of the most significant bit in the bit field.
1428 @param OrData The value to OR with the PCI configuration register.
1430 @return The value written back to the PCI configuration register.
1435 PciCf8BitFieldOr32 (
1442 BOOLEAN InterruptState
;
1446 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1447 InterruptState
= SaveAndDisableInterrupts ();
1448 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1449 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1450 Result
= IoBitFieldOr32 (
1451 PCI_CONFIGURATION_DATA_PORT
,
1456 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1457 SetInterruptState (InterruptState
);
1462 Reads a bit field in a 32-bit PCI configuration register, performs a bitwise
1463 AND, and writes the result back to the bit field in the 32-bit register.
1465 Reads the 32-bit PCI configuration register specified by Address, performs a
1466 bitwise AND between the read result and the value specified by AndData, and
1467 writes the result to the 32-bit PCI configuration register specified by
1468 Address. The value written to the PCI configuration register is returned.
1469 This function must guarantee that all PCI read and write operations are
1470 serialized. Extra left bits in AndData are stripped.
1472 If Address > 0x0FFFFFFF, then ASSERT().
1473 If Address is not aligned on a 32-bit boundary, then ASSERT().
1474 If the register specified by Address >= 0x100, then ASSERT().
1475 If StartBit is greater than 31, then ASSERT().
1476 If EndBit is greater than 31, then ASSERT().
1477 If EndBit is less than StartBit, then ASSERT().
1478 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1480 @param Address The PCI configuration register to write.
1481 @param StartBit The ordinal of the least significant bit in the bit field.
1483 @param EndBit The ordinal of the most significant bit in the bit field.
1485 @param AndData The value to AND with the PCI configuration register.
1487 @return The value written back to the PCI configuration register.
1492 PciCf8BitFieldAnd32 (
1499 BOOLEAN InterruptState
;
1503 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1504 InterruptState
= SaveAndDisableInterrupts ();
1505 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1506 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1507 Result
= IoBitFieldAnd32 (
1508 PCI_CONFIGURATION_DATA_PORT
,
1513 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1514 SetInterruptState (InterruptState
);
1519 Reads a bit field in a 32-bit port, performs a bitwise AND followed by a
1520 bitwise OR, and writes the result back to the bit field in the
1523 Reads the 32-bit PCI configuration register specified by Address, performs a
1524 bitwise AND followed by a bitwise OR between the read result and
1525 the value specified by AndData, and writes the result to the 32-bit PCI
1526 configuration register specified by Address. The value written to the PCI
1527 configuration register is returned. This function must guarantee that all PCI
1528 read and write operations are serialized. Extra left bits in both AndData and
1529 OrData are stripped.
1531 If Address > 0x0FFFFFFF, then ASSERT().
1532 If Address is not aligned on a 32-bit boundary, then ASSERT().
1533 If the register specified by Address >= 0x100, then ASSERT().
1534 If StartBit is greater than 31, then ASSERT().
1535 If EndBit is greater than 31, then ASSERT().
1536 If EndBit is less than StartBit, then ASSERT().
1537 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1538 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1540 @param Address The PCI configuration register to write.
1541 @param StartBit The ordinal of the least significant bit in the bit field.
1543 @param EndBit The ordinal of the most significant bit in the bit field.
1545 @param AndData The value to AND with the PCI configuration register.
1546 @param OrData The value to OR with the result of the AND operation.
1548 @return The value written back to the PCI configuration register.
1553 PciCf8BitFieldAndThenOr32 (
1561 BOOLEAN InterruptState
;
1565 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1566 InterruptState
= SaveAndDisableInterrupts ();
1567 AddressPort
= IoRead32 (PCI_CONFIGURATION_ADDRESS_PORT
);
1568 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1569 Result
= IoBitFieldAndThenOr32 (
1570 PCI_CONFIGURATION_DATA_PORT
,
1576 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, AddressPort
);
1577 SetInterruptState (InterruptState
);
1582 Reads a range of PCI configuration registers into a caller supplied buffer.
1584 Reads the range of PCI configuration registers specified by StartAddress and
1585 Size into the buffer specified by Buffer. This function only allows the PCI
1586 configuration registers from a single PCI function to be read. Size is
1587 returned. When possible 32-bit PCI configuration read cycles are used to read
1588 from StartAdress to StartAddress + Size. Due to alignment restrictions, 8-bit
1589 and 16-bit PCI configuration read cycles may be used at the beginning and the
1592 If StartAddress > 0x0FFFFFFF, then ASSERT().
1593 If the register specified by StartAddress >= 0x100, then ASSERT().
1594 If ((StartAddress & 0xFFF) + Size) > 0x100, then ASSERT().
1595 If Size > 0 and Buffer is NULL, then ASSERT().
1597 @param StartAddress The starting address that encodes the PCI Bus, Device,
1598 Function and Register.
1599 @param Size The size in bytes of the transfer.
1600 @param Buffer The pointer to a buffer receiving the data read.
1602 @return Size read from StartAddress.
1608 IN UINTN StartAddress
,
1615 ASSERT_INVALID_PCI_ADDRESS (StartAddress
, 0);
1616 ASSERT (((StartAddress
& 0xFFF) + Size
) <= 0x100);
1622 ASSERT (Buffer
!= NULL
);
1625 // Save Size for return
1629 if ((StartAddress
& 1) != 0) {
1631 // Read a byte if StartAddress is byte aligned
1633 *(volatile UINT8
*)Buffer
= PciCf8Read8 (StartAddress
);
1634 StartAddress
+= sizeof (UINT8
);
1635 Size
-= sizeof (UINT8
);
1636 Buffer
= (UINT8
*)Buffer
+ 1;
1639 if ((Size
>= sizeof (UINT16
)) && ((StartAddress
& 2) != 0)) {
1641 // Read a word if StartAddress is word aligned
1643 WriteUnaligned16 ((UINT16
*)Buffer
, (UINT16
)PciCf8Read16 (StartAddress
));
1645 StartAddress
+= sizeof (UINT16
);
1646 Size
-= sizeof (UINT16
);
1647 Buffer
= (UINT16
*)Buffer
+ 1;
1650 while (Size
>= sizeof (UINT32
)) {
1652 // Read as many double words as possible
1654 WriteUnaligned32 ((UINT32
*)Buffer
, (UINT32
)PciCf8Read32 (StartAddress
));
1655 StartAddress
+= sizeof (UINT32
);
1656 Size
-= sizeof (UINT32
);
1657 Buffer
= (UINT32
*)Buffer
+ 1;
1660 if (Size
>= sizeof (UINT16
)) {
1662 // Read the last remaining word if exist
1664 WriteUnaligned16 ((UINT16
*)Buffer
, (UINT16
)PciCf8Read16 (StartAddress
));
1665 StartAddress
+= sizeof (UINT16
);
1666 Size
-= sizeof (UINT16
);
1667 Buffer
= (UINT16
*)Buffer
+ 1;
1670 if (Size
>= sizeof (UINT8
)) {
1672 // Read the last remaining byte if exist
1674 *(volatile UINT8
*)Buffer
= PciCf8Read8 (StartAddress
);
1681 Copies the data in a caller supplied buffer to a specified range of PCI
1682 configuration space.
1684 Writes the range of PCI configuration registers specified by StartAddress and
1685 Size from the buffer specified by Buffer. This function only allows the PCI
1686 configuration registers from a single PCI function to be written. Size is
1687 returned. When possible 32-bit PCI configuration write cycles are used to
1688 write from StartAdress to StartAddress + Size. Due to alignment restrictions,
1689 8-bit and 16-bit PCI configuration write cycles may be used at the beginning
1690 and the end of the range.
1692 If StartAddress > 0x0FFFFFFF, then ASSERT().
1693 If the register specified by StartAddress >= 0x100, then ASSERT().
1694 If ((StartAddress & 0xFFF) + Size) > 0x100, then ASSERT().
1695 If Size > 0 and Buffer is NULL, then ASSERT().
1697 @param StartAddress The starting address that encodes the PCI Bus, Device,
1698 Function and Register.
1699 @param Size The size in bytes of the transfer.
1700 @param Buffer The pointer to a buffer containing the data to write.
1702 @return Size written to StartAddress.
1708 IN UINTN StartAddress
,
1715 ASSERT_INVALID_PCI_ADDRESS (StartAddress
, 0);
1716 ASSERT (((StartAddress
& 0xFFF) + Size
) <= 0x100);
1722 ASSERT (Buffer
!= NULL
);
1725 // Save Size for return
1729 if ((StartAddress
& 1) != 0) {
1731 // Write a byte if StartAddress is byte aligned
1733 PciCf8Write8 (StartAddress
, *(UINT8
*)Buffer
);
1734 StartAddress
+= sizeof (UINT8
);
1735 Size
-= sizeof (UINT8
);
1736 Buffer
= (UINT8
*)Buffer
+ 1;
1739 if ((Size
>= sizeof (UINT16
)) && ((StartAddress
& 2) != 0)) {
1741 // Write a word if StartAddress is word aligned
1743 PciCf8Write16 (StartAddress
, ReadUnaligned16 ((UINT16
*)Buffer
));
1744 StartAddress
+= sizeof (UINT16
);
1745 Size
-= sizeof (UINT16
);
1746 Buffer
= (UINT16
*)Buffer
+ 1;
1749 while (Size
>= sizeof (UINT32
)) {
1751 // Write as many double words as possible
1753 PciCf8Write32 (StartAddress
, ReadUnaligned32 ((UINT32
*)Buffer
));
1754 StartAddress
+= sizeof (UINT32
);
1755 Size
-= sizeof (UINT32
);
1756 Buffer
= (UINT32
*)Buffer
+ 1;
1759 if (Size
>= sizeof (UINT16
)) {
1761 // Write the last remaining word if exist
1763 PciCf8Write16 (StartAddress
, ReadUnaligned16 ((UINT16
*)Buffer
));
1764 StartAddress
+= sizeof (UINT16
);
1765 Size
-= sizeof (UINT16
);
1766 Buffer
= (UINT16
*)Buffer
+ 1;
1769 if (Size
>= sizeof (UINT8
)) {
1771 // Write the last remaining byte if exist
1773 PciCf8Write8 (StartAddress
, *(UINT8
*)Buffer
);