4 Copyright (c) 2006, Intel Corporation<BR>
5 All rights reserved. This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
18 // Include common header file for this module.
20 #include "CommonHeader.h"
23 // Declare I/O Ports used to perform PCI Confguration Cycles
25 #define PCI_CONFIGURATION_ADDRESS_PORT 0xCF8
26 #define PCI_CONFIGURATION_DATA_PORT 0xCFC
29 // Declare macro to convert PCI Library formatted address to CF8 formatted address
31 // PCI Library formatted address CF8 Formatted Address
32 // ============================= ======================
33 // Bits 00..11 Register Bits 00..07 Register
34 // Bits 12..14 Function Bits 08..10 Function
35 // Bits 15..19 Device Bits 11..15 Device
36 // Bits 20..27 Bus Bits 16..23 Bus
37 // Bits 28..31 Reserved(MBZ) Bits 24..30 Reserved(MBZ)
38 // Bits 31..31 Must be 1
42 Assert the validity of a PCI address. A valid PCI address should contain 1's
43 only in the low 28 bits.
45 @param A The address to validate.
46 @param M Additional bits to assert to be zero.
49 #define ASSERT_INVALID_PCI_ADDRESS(A,M) \
50 ASSERT (((A) & (~0xffff0ff | (M))) == 0)
53 Convert a PCI Express address to PCI CF8 address.
55 @param A The address to convert.
57 @retval The coverted address.
60 #define PCI_TO_CF8_ADDRESS(A) \
61 ((UINT32) ((((A) >> 4) & 0x00ffff00) | ((A) & 0xfc) | 0x80000000))
64 Reads an 8-bit PCI configuration register.
66 Reads and returns the 8-bit PCI configuration register specified by Address.
67 This function must guarantee that all PCI read and write operations are
70 If Address > 0x0FFFFFFF, then ASSERT().
71 If the register specified by Address >= 0x100, then ASSERT().
73 @param Address Address that encodes the PCI Bus, Device, Function and
76 @return The read value from the PCI configuration register.
85 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
86 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
87 return IoRead8 (PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3));
91 Writes an 8-bit PCI configuration register.
93 Writes the 8-bit PCI configuration register specified by Address with the
94 value specified by Value. Value is returned. This function must guarantee
95 that all PCI read and write operations are serialized.
97 If Address > 0x0FFFFFFF, then ASSERT().
98 If the register specified by Address >= 0x100, then ASSERT().
100 @param Address Address that encodes the PCI Bus, Device, Function and
102 @param Value The value to write.
104 @return The value written to the PCI configuration register.
114 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
115 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
117 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
123 Performs a bitwise inclusive OR of an 8-bit PCI configuration register with
126 Reads the 8-bit PCI configuration register specified by Address, performs a
127 bitwise inclusive OR between the read result and the value specified by
128 OrData, and writes the result to the 8-bit PCI configuration register
129 specified by Address. The value written to the PCI configuration register is
130 returned. This function must guarantee that all PCI read and write operations
133 If Address > 0x0FFFFFFF, then ASSERT().
134 If the register specified by Address >= 0x100, then ASSERT().
136 @param Address Address that encodes the PCI Bus, Device, Function and
138 @param OrData The value to OR with the PCI configuration register.
140 @return The value written back to the PCI configuration register.
150 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
151 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
153 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
159 Performs a bitwise AND of an 8-bit PCI configuration register with an 8-bit
162 Reads the 8-bit PCI configuration register specified by Address, performs a
163 bitwise AND between the read result and the value specified by AndData, and
164 writes the result to the 8-bit PCI configuration register specified by
165 Address. The value written to the PCI configuration register is returned.
166 This function must guarantee that all PCI read and write operations are
169 If Address > 0x0FFFFFFF, then ASSERT().
170 If the register specified by Address >= 0x100, then ASSERT().
172 @param Address Address that encodes the PCI Bus, Device, Function and
174 @param AndData The value to AND with the PCI configuration register.
176 @return The value written back to the PCI configuration register.
186 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
187 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
189 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
195 Performs a bitwise AND of an 8-bit PCI configuration register with an 8-bit
196 value, followed a bitwise inclusive OR with another 8-bit value.
198 Reads the 8-bit PCI configuration register specified by Address, performs a
199 bitwise AND between the read result and the value specified by AndData,
200 performs a bitwise inclusive OR between the result of the AND operation and
201 the value specified by OrData, and writes the result to the 8-bit PCI
202 configuration register specified by Address. The value written to the PCI
203 configuration register is returned. This function must guarantee that all PCI
204 read and write operations are serialized.
206 If Address > 0x0FFFFFFF, then ASSERT().
207 If the register specified by Address >= 0x100, then ASSERT().
209 @param Address Address that encodes the PCI Bus, Device, Function and
211 @param AndData The value to AND with the PCI configuration register.
212 @param OrData The value to OR with the result of the AND operation.
214 @return The value written back to the PCI configuration register.
225 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
226 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
227 return IoAndThenOr8 (
228 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
235 Reads a bit field of a PCI configuration register.
237 Reads the bit field in an 8-bit PCI configuration register. The bit field is
238 specified by the StartBit and the EndBit. The value of the bit field is
241 If Address > 0x0FFFFFFF, then ASSERT().
242 If the register specified by Address >= 0x100, then ASSERT().
243 If StartBit is greater than 7, then ASSERT().
244 If EndBit is greater than 7, then ASSERT().
245 If EndBit is less than StartBit, then ASSERT().
247 @param Address PCI configuration register to read.
248 @param StartBit The ordinal of the least significant bit in the bit field.
250 @param EndBit The ordinal of the most significant bit in the bit field.
253 @return The value of the bit field read from the PCI configuration register.
258 PciCf8BitFieldRead8 (
264 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
265 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
266 return IoBitFieldRead8 (
267 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
274 Writes a bit field to a PCI configuration register.
276 Writes Value to the bit field of the PCI configuration register. The bit
277 field is specified by the StartBit and the EndBit. All other bits in the
278 destination PCI configuration register are preserved. The new value of the
279 8-bit register is returned.
281 If Address > 0x0FFFFFFF, then ASSERT().
282 If the register specified by Address >= 0x100, then ASSERT().
283 If StartBit is greater than 7, then ASSERT().
284 If EndBit is greater than 7, then ASSERT().
285 If EndBit is less than StartBit, then ASSERT().
287 @param Address PCI configuration register to write.
288 @param StartBit The ordinal of the least significant bit in the bit field.
290 @param EndBit The ordinal of the most significant bit in the bit field.
292 @param Value New value of the bit field.
294 @return The value written back to the PCI configuration register.
299 PciCf8BitFieldWrite8 (
306 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
307 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
308 return IoBitFieldWrite8 (
309 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
317 Reads a bit field in an 8-bit PCI configuration, performs a bitwise OR, and
318 writes the result back to the bit field in the 8-bit port.
320 Reads the 8-bit PCI configuration register specified by Address, performs a
321 bitwise inclusive OR between the read result and the value specified by
322 OrData, and writes the result to the 8-bit PCI configuration register
323 specified by Address. The value written to the PCI configuration register is
324 returned. This function must guarantee that all PCI read and write operations
325 are serialized. Extra left bits in OrData are stripped.
327 If Address > 0x0FFFFFFF, then ASSERT().
328 If the register specified by Address >= 0x100, then ASSERT().
329 If StartBit is greater than 7, then ASSERT().
330 If EndBit is greater than 7, then ASSERT().
331 If EndBit is less than StartBit, then ASSERT().
333 @param Address PCI configuration register to write.
334 @param StartBit The ordinal of the least significant bit in the bit field.
336 @param EndBit The ordinal of the most significant bit in the bit field.
338 @param OrData The value to OR with the PCI configuration register.
340 @return The value written back to the PCI configuration register.
352 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
353 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
354 return IoBitFieldOr8 (
355 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
363 Reads a bit field in an 8-bit PCI configuration register, performs a bitwise
364 AND, and writes the result back to the bit field in the 8-bit register.
366 Reads the 8-bit PCI configuration register specified by Address, performs a
367 bitwise AND between the read result and the value specified by AndData, and
368 writes the result to the 8-bit PCI configuration register specified by
369 Address. The value written to the PCI configuration register is returned.
370 This function must guarantee that all PCI read and write operations are
371 serialized. Extra left bits in AndData are stripped.
373 If Address > 0x0FFFFFFF, then ASSERT().
374 If the register specified by Address >= 0x100, then ASSERT().
375 If StartBit is greater than 7, then ASSERT().
376 If EndBit is greater than 7, then ASSERT().
377 If EndBit is less than StartBit, then ASSERT().
379 @param Address PCI configuration register to write.
380 @param StartBit The ordinal of the least significant bit in the bit field.
382 @param EndBit The ordinal of the most significant bit in the bit field.
384 @param AndData The value to AND with the PCI configuration register.
386 @return The value written back to the PCI configuration register.
398 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
399 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
400 return IoBitFieldAnd8 (
401 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
409 Reads a bit field in an 8-bit port, performs a bitwise AND followed by a
410 bitwise inclusive OR, and writes the result back to the bit field in the
413 Reads the 8-bit PCI configuration register specified by Address, performs a
414 bitwise AND followed by a bitwise inclusive OR between the read result and
415 the value specified by AndData, and writes the result to the 8-bit PCI
416 configuration register specified by Address. The value written to the PCI
417 configuration register is returned. This function must guarantee that all PCI
418 read and write operations are serialized. Extra left bits in both AndData and
421 If Address > 0x0FFFFFFF, then ASSERT().
422 If the register specified by Address >= 0x100, then ASSERT().
423 If StartBit is greater than 7, then ASSERT().
424 If EndBit is greater than 7, then ASSERT().
425 If EndBit is less than StartBit, then ASSERT().
427 @param Address PCI configuration register to write.
428 @param StartBit The ordinal of the least significant bit in the bit field.
430 @param EndBit The ordinal of the most significant bit in the bit field.
432 @param AndData The value to AND with the PCI configuration register.
433 @param OrData The value to OR with the result of the AND operation.
435 @return The value written back to the PCI configuration register.
440 PciCf8BitFieldAndThenOr8(
448 ASSERT_INVALID_PCI_ADDRESS (Address
, 0);
449 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
450 return IoBitFieldAndThenOr8 (
451 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 3),
460 Reads a 16-bit PCI configuration register.
462 Reads and returns the 16-bit PCI configuration register specified by Address.
463 This function must guarantee that all PCI read and write operations are
466 If Address > 0x0FFFFFFF, then ASSERT().
467 If Address is not aligned on a 16-bit boundary, then ASSERT().
468 If the register specified by Address >= 0x100, then ASSERT().
470 @param Address Address that encodes the PCI Bus, Device, Function and
473 @return The read value from the PCI configuration register.
482 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
483 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
484 return IoRead16 (PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2));
488 Writes a 16-bit PCI configuration register.
490 Writes the 16-bit PCI configuration register specified by Address with the
491 value specified by Value. Value is returned. This function must guarantee
492 that all PCI read and write operations are serialized.
494 If Address > 0x0FFFFFFF, then ASSERT().
495 If Address is not aligned on a 16-bit boundary, then ASSERT().
496 If the register specified by Address >= 0x100, then ASSERT().
498 @param Address Address that encodes the PCI Bus, Device, Function and
500 @param Value The value to write.
502 @return The value written to the PCI configuration register.
512 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
513 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
515 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
521 Performs a bitwise inclusive OR of a 16-bit PCI configuration register with
524 Reads the 16-bit PCI configuration register specified by Address, performs a
525 bitwise inclusive OR between the read result and the value specified by
526 OrData, and writes the result to the 16-bit PCI configuration register
527 specified by Address. The value written to the PCI configuration register is
528 returned. This function must guarantee that all PCI read and write operations
531 If Address > 0x0FFFFFFF, then ASSERT().
532 If Address is not aligned on a 16-bit boundary, then ASSERT().
533 If the register specified by Address >= 0x100, then ASSERT().
535 @param Address Address that encodes the PCI Bus, Device, Function and
537 @param OrData The value to OR with the PCI configuration register.
539 @return The value written back to the PCI configuration register.
549 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
550 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
552 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
558 Performs a bitwise AND of a 16-bit PCI configuration register with a 16-bit
561 Reads the 16-bit PCI configuration register specified by Address, performs a
562 bitwise AND between the read result and the value specified by AndData, and
563 writes the result to the 16-bit PCI configuration register specified by
564 Address. The value written to the PCI configuration register is returned.
565 This function must guarantee that all PCI read and write operations are
568 If Address > 0x0FFFFFFF, then ASSERT().
569 If Address is not aligned on a 16-bit boundary, then ASSERT().
570 If the register specified by Address >= 0x100, then ASSERT().
572 @param Address Address that encodes the PCI Bus, Device, Function and
574 @param AndData The value to AND with the PCI configuration register.
576 @return The value written back to the PCI configuration register.
586 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
587 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
589 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
595 Performs a bitwise AND of a 16-bit PCI configuration register with a 16-bit
596 value, followed a bitwise inclusive OR with another 16-bit value.
598 Reads the 16-bit PCI configuration register specified by Address, performs a
599 bitwise AND between the read result and the value specified by AndData,
600 performs a bitwise inclusive OR between the result of the AND operation and
601 the value specified by OrData, and writes the result to the 16-bit PCI
602 configuration register specified by Address. The value written to the PCI
603 configuration register is returned. This function must guarantee that all PCI
604 read and write operations are serialized.
606 If Address > 0x0FFFFFFF, then ASSERT().
607 If Address is not aligned on a 16-bit boundary, then ASSERT().
608 If the register specified by Address >= 0x100, then ASSERT().
610 @param Address Address that encodes the PCI Bus, Device, Function and
612 @param AndData The value to AND with the PCI configuration register.
613 @param OrData The value to OR with the result of the AND operation.
615 @return The value written back to the PCI configuration register.
626 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
627 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
628 return IoAndThenOr16 (
629 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
636 Reads a bit field of a PCI configuration register.
638 Reads the bit field in a 16-bit PCI configuration register. The bit field is
639 specified by the StartBit and the EndBit. The value of the bit field is
642 If Address > 0x0FFFFFFF, then ASSERT().
643 If Address is not aligned on a 16-bit boundary, then ASSERT().
644 If the register specified by Address >= 0x100, then ASSERT().
645 If StartBit is greater than 15, then ASSERT().
646 If EndBit is greater than 15, then ASSERT().
647 If EndBit is less than StartBit, then ASSERT().
649 @param Address PCI configuration register to read.
650 @param StartBit The ordinal of the least significant bit in the bit field.
652 @param EndBit The ordinal of the most significant bit in the bit field.
655 @return The value of the bit field read from the PCI configuration register.
660 PciCf8BitFieldRead16 (
666 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
667 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
668 return IoBitFieldRead16 (
669 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
676 Writes a bit field to a PCI configuration register.
678 Writes Value to the bit field of the PCI configuration register. The bit
679 field is specified by the StartBit and the EndBit. All other bits in the
680 destination PCI configuration register are preserved. The new value of the
681 16-bit register is returned.
683 If Address > 0x0FFFFFFF, then ASSERT().
684 If Address is not aligned on a 16-bit boundary, then ASSERT().
685 If the register specified by Address >= 0x100, then ASSERT().
686 If StartBit is greater than 15, then ASSERT().
687 If EndBit is greater than 15, then ASSERT().
688 If EndBit is less than StartBit, then ASSERT().
690 @param Address PCI configuration register to write.
691 @param StartBit The ordinal of the least significant bit in the bit field.
693 @param EndBit The ordinal of the most significant bit in the bit field.
695 @param Value New value of the bit field.
697 @return The value written back to the PCI configuration register.
702 PciCf8BitFieldWrite16 (
709 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
710 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
711 return IoBitFieldWrite16 (
712 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
720 Reads a bit field in a 16-bit PCI configuration, performs a bitwise OR, and
721 writes the result back to the bit field in the 16-bit port.
723 Reads the 16-bit PCI configuration register specified by Address, performs a
724 bitwise inclusive OR between the read result and the value specified by
725 OrData, and writes the result to the 16-bit PCI configuration register
726 specified by Address. The value written to the PCI configuration register is
727 returned. This function must guarantee that all PCI read and write operations
728 are serialized. Extra left bits in OrData are stripped.
730 If Address > 0x0FFFFFFF, then ASSERT().
731 If Address is not aligned on a 16-bit boundary, then ASSERT().
732 If the register specified by Address >= 0x100, then ASSERT().
733 If StartBit is greater than 15, then ASSERT().
734 If EndBit is greater than 15, then ASSERT().
735 If EndBit is less than StartBit, then ASSERT().
737 @param Address PCI configuration register to write.
738 @param StartBit The ordinal of the least significant bit in the bit field.
740 @param EndBit The ordinal of the most significant bit in the bit field.
742 @param OrData The value to OR with the PCI configuration register.
744 @return The value written back to the PCI configuration register.
756 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
757 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
758 return IoBitFieldOr16 (
759 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
767 Reads a bit field in a 16-bit PCI configuration register, performs a bitwise
768 AND, and writes the result back to the bit field in the 16-bit register.
770 Reads the 16-bit PCI configuration register specified by Address, performs a
771 bitwise AND between the read result and the value specified by AndData, and
772 writes the result to the 16-bit PCI configuration register specified by
773 Address. The value written to the PCI configuration register is returned.
774 This function must guarantee that all PCI read and write operations are
775 serialized. Extra left bits in AndData are stripped.
777 If Address > 0x0FFFFFFF, then ASSERT().
778 If Address is not aligned on a 16-bit boundary, then ASSERT().
779 If the register specified by Address >= 0x100, then ASSERT().
780 If StartBit is greater than 15, then ASSERT().
781 If EndBit is greater than 15, then ASSERT().
782 If EndBit is less than StartBit, then ASSERT().
784 @param Address PCI configuration register to write.
785 @param StartBit The ordinal of the least significant bit in the bit field.
787 @param EndBit The ordinal of the most significant bit in the bit field.
789 @param AndData The value to AND with the PCI configuration register.
791 @return The value written back to the PCI configuration register.
796 PciCf8BitFieldAnd16 (
803 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
804 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
805 return IoBitFieldAnd16 (
806 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
814 Reads a bit field in a 16-bit port, performs a bitwise AND followed by a
815 bitwise inclusive OR, and writes the result back to the bit field in the
818 Reads the 16-bit PCI configuration register specified by Address, performs a
819 bitwise AND followed by a bitwise inclusive OR between the read result and
820 the value specified by AndData, and writes the result to the 16-bit PCI
821 configuration register specified by Address. The value written to the PCI
822 configuration register is returned. This function must guarantee that all PCI
823 read and write operations are serialized. Extra left bits in both AndData and
826 If Address > 0x0FFFFFFF, then ASSERT().
827 If Address is not aligned on a 16-bit boundary, then ASSERT().
828 If the register specified by Address >= 0x100, then ASSERT().
829 If StartBit is greater than 15, then ASSERT().
830 If EndBit is greater than 15, then ASSERT().
831 If EndBit is less than StartBit, then ASSERT().
833 @param Address PCI configuration register to write.
834 @param StartBit The ordinal of the least significant bit in the bit field.
836 @param EndBit The ordinal of the most significant bit in the bit field.
838 @param AndData The value to AND with the PCI configuration register.
839 @param OrData The value to OR with the result of the AND operation.
841 @return The value written back to the PCI configuration register.
846 PciCf8BitFieldAndThenOr16(
854 ASSERT_INVALID_PCI_ADDRESS (Address
, 1);
855 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
856 return IoBitFieldAndThenOr16 (
857 PCI_CONFIGURATION_DATA_PORT
+ (UINT16
)(Address
& 2),
866 Reads a 32-bit PCI configuration register.
868 Reads and returns the 32-bit PCI configuration register specified by Address.
869 This function must guarantee that all PCI read and write operations are
872 If Address > 0x0FFFFFFF, then ASSERT().
873 If Address is not aligned on a 32-bit boundary, then ASSERT().
874 If the register specified by Address >= 0x100, then ASSERT().
876 @param Address Address that encodes the PCI Bus, Device, Function and
879 @return The read value from the PCI configuration register.
888 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
889 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
890 return IoRead32 (PCI_CONFIGURATION_DATA_PORT
);
894 Writes a 32-bit PCI configuration register.
896 Writes the 32-bit PCI configuration register specified by Address with the
897 value specified by Value. Value is returned. This function must guarantee
898 that all PCI read and write operations are serialized.
900 If Address > 0x0FFFFFFF, then ASSERT().
901 If Address is not aligned on a 32-bit boundary, then ASSERT().
902 If the register specified by Address >= 0x100, then ASSERT().
904 @param Address Address that encodes the PCI Bus, Device, Function and
906 @param Value The value to write.
908 @return The value written to the PCI configuration register.
918 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
919 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
921 PCI_CONFIGURATION_DATA_PORT
,
927 Performs a bitwise inclusive OR of a 32-bit PCI configuration register with
930 Reads the 32-bit PCI configuration register specified by Address, performs a
931 bitwise inclusive OR between the read result and the value specified by
932 OrData, and writes the result to the 32-bit PCI configuration register
933 specified by Address. The value written to the PCI configuration register is
934 returned. This function must guarantee that all PCI read and write operations
937 If Address > 0x0FFFFFFF, then ASSERT().
938 If Address is not aligned on a 32-bit boundary, then ASSERT().
939 If the register specified by Address >= 0x100, then ASSERT().
941 @param Address Address that encodes the PCI Bus, Device, Function and
943 @param OrData The value to OR with the PCI configuration register.
945 @return The value written back to the PCI configuration register.
955 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
956 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
958 PCI_CONFIGURATION_DATA_PORT
,
964 Performs a bitwise AND of a 32-bit PCI configuration register with a 32-bit
967 Reads the 32-bit PCI configuration register specified by Address, performs a
968 bitwise AND between the read result and the value specified by AndData, and
969 writes the result to the 32-bit PCI configuration register specified by
970 Address. The value written to the PCI configuration register is returned.
971 This function must guarantee that all PCI read and write operations are
974 If Address > 0x0FFFFFFF, then ASSERT().
975 If Address is not aligned on a 32-bit boundary, then ASSERT().
976 If the register specified by Address >= 0x100, then ASSERT().
978 @param Address Address that encodes the PCI Bus, Device, Function and
980 @param AndData The value to AND with the PCI configuration register.
982 @return The value written back to the PCI configuration register.
992 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
993 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
995 PCI_CONFIGURATION_DATA_PORT
,
1001 Performs a bitwise AND of a 32-bit PCI configuration register with a 32-bit
1002 value, followed a bitwise inclusive OR with another 32-bit value.
1004 Reads the 32-bit PCI configuration register specified by Address, performs a
1005 bitwise AND between the read result and the value specified by AndData,
1006 performs a bitwise inclusive OR between the result of the AND operation and
1007 the value specified by OrData, and writes the result to the 32-bit PCI
1008 configuration register specified by Address. The value written to the PCI
1009 configuration register is returned. This function must guarantee that all PCI
1010 read and write operations are serialized.
1012 If Address > 0x0FFFFFFF, then ASSERT().
1013 If Address is not aligned on a 32-bit boundary, then ASSERT().
1014 If the register specified by Address >= 0x100, then ASSERT().
1016 @param Address Address that encodes the PCI Bus, Device, Function and
1018 @param AndData The value to AND with the PCI configuration register.
1019 @param OrData The value to OR with the result of the AND operation.
1021 @return The value written back to the PCI configuration register.
1032 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1033 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1034 return IoAndThenOr32 (
1035 PCI_CONFIGURATION_DATA_PORT
,
1042 Reads a bit field of a PCI configuration register.
1044 Reads the bit field in a 32-bit PCI configuration register. The bit field is
1045 specified by the StartBit and the EndBit. The value of the bit field is
1048 If Address > 0x0FFFFFFF, then ASSERT().
1049 If Address is not aligned on a 32-bit boundary, then ASSERT().
1050 If the register specified by Address >= 0x100, then ASSERT().
1051 If StartBit is greater than 31, then ASSERT().
1052 If EndBit is greater than 31, then ASSERT().
1053 If EndBit is less than StartBit, then ASSERT().
1055 @param Address PCI configuration register to read.
1056 @param StartBit The ordinal of the least significant bit in the bit field.
1058 @param EndBit The ordinal of the most significant bit in the bit field.
1061 @return The value of the bit field read from the PCI configuration register.
1066 PciCf8BitFieldRead32 (
1072 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1073 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1074 return IoBitFieldRead32 (
1075 PCI_CONFIGURATION_DATA_PORT
,
1082 Writes a bit field to a PCI configuration register.
1084 Writes Value to the bit field of the PCI configuration register. The bit
1085 field is specified by the StartBit and the EndBit. All other bits in the
1086 destination PCI configuration register are preserved. The new value of the
1087 32-bit register is returned.
1089 If Address > 0x0FFFFFFF, then ASSERT().
1090 If Address is not aligned on a 32-bit boundary, then ASSERT().
1091 If the register specified by Address >= 0x100, then ASSERT().
1092 If StartBit is greater than 31, then ASSERT().
1093 If EndBit is greater than 31, then ASSERT().
1094 If EndBit is less than StartBit, then ASSERT().
1096 @param Address PCI configuration register to write.
1097 @param StartBit The ordinal of the least significant bit in the bit field.
1099 @param EndBit The ordinal of the most significant bit in the bit field.
1101 @param Value New value of the bit field.
1103 @return The value written back to the PCI configuration register.
1108 PciCf8BitFieldWrite32 (
1115 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1116 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1117 return IoBitFieldWrite32 (
1118 PCI_CONFIGURATION_DATA_PORT
,
1126 Reads a bit field in a 32-bit PCI configuration, performs a bitwise OR, and
1127 writes the result back to the bit field in the 32-bit port.
1129 Reads the 32-bit PCI configuration register specified by Address, performs a
1130 bitwise inclusive OR between the read result and the value specified by
1131 OrData, and writes the result to the 32-bit PCI configuration register
1132 specified by Address. The value written to the PCI configuration register is
1133 returned. This function must guarantee that all PCI read and write operations
1134 are serialized. Extra left bits in OrData are stripped.
1136 If Address > 0x0FFFFFFF, then ASSERT().
1137 If Address is not aligned on a 32-bit boundary, then ASSERT().
1138 If the register specified by Address >= 0x100, then ASSERT().
1139 If StartBit is greater than 31, then ASSERT().
1140 If EndBit is greater than 31, then ASSERT().
1141 If EndBit is less than StartBit, then ASSERT().
1143 @param Address PCI configuration register to write.
1144 @param StartBit The ordinal of the least significant bit in the bit field.
1146 @param EndBit The ordinal of the most significant bit in the bit field.
1148 @param OrData The value to OR with the PCI configuration register.
1150 @return The value written back to the PCI configuration register.
1155 PciCf8BitFieldOr32 (
1162 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1163 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1164 return IoBitFieldOr32 (
1165 PCI_CONFIGURATION_DATA_PORT
,
1173 Reads a bit field in a 32-bit PCI configuration register, performs a bitwise
1174 AND, and writes the result back to the bit field in the 32-bit register.
1176 Reads the 32-bit PCI configuration register specified by Address, performs a
1177 bitwise AND between the read result and the value specified by AndData, and
1178 writes the result to the 32-bit PCI configuration register specified by
1179 Address. The value written to the PCI configuration register is returned.
1180 This function must guarantee that all PCI read and write operations are
1181 serialized. Extra left bits in AndData are stripped.
1183 If Address > 0x0FFFFFFF, then ASSERT().
1184 If Address is not aligned on a 32-bit boundary, then ASSERT().
1185 If the register specified by Address >= 0x100, then ASSERT().
1186 If StartBit is greater than 31, then ASSERT().
1187 If EndBit is greater than 31, then ASSERT().
1188 If EndBit is less than StartBit, then ASSERT().
1190 @param Address PCI configuration register to write.
1191 @param StartBit The ordinal of the least significant bit in the bit field.
1193 @param EndBit The ordinal of the most significant bit in the bit field.
1195 @param AndData The value to AND with the PCI configuration register.
1197 @return The value written back to the PCI configuration register.
1202 PciCf8BitFieldAnd32 (
1209 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1210 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1211 return IoBitFieldAnd32 (
1212 PCI_CONFIGURATION_DATA_PORT
,
1220 Reads a bit field in a 32-bit port, performs a bitwise AND followed by a
1221 bitwise inclusive OR, and writes the result back to the bit field in the
1224 Reads the 32-bit PCI configuration register specified by Address, performs a
1225 bitwise AND followed by a bitwise inclusive OR between the read result and
1226 the value specified by AndData, and writes the result to the 32-bit PCI
1227 configuration register specified by Address. The value written to the PCI
1228 configuration register is returned. This function must guarantee that all PCI
1229 read and write operations are serialized. Extra left bits in both AndData and
1230 OrData are stripped.
1232 If Address > 0x0FFFFFFF, then ASSERT().
1233 If Address is not aligned on a 32-bit boundary, then ASSERT().
1234 If the register specified by Address >= 0x100, then ASSERT().
1235 If StartBit is greater than 31, then ASSERT().
1236 If EndBit is greater than 31, then ASSERT().
1237 If EndBit is less than StartBit, then ASSERT().
1239 @param Address PCI configuration register to write.
1240 @param StartBit The ordinal of the least significant bit in the bit field.
1242 @param EndBit The ordinal of the most significant bit in the bit field.
1244 @param AndData The value to AND with the PCI configuration register.
1245 @param OrData The value to OR with the result of the AND operation.
1247 @return The value written back to the PCI configuration register.
1252 PciCf8BitFieldAndThenOr32(
1260 ASSERT_INVALID_PCI_ADDRESS (Address
, 3);
1261 IoWrite32 (PCI_CONFIGURATION_ADDRESS_PORT
, PCI_TO_CF8_ADDRESS (Address
));
1262 return IoBitFieldAndThenOr32 (
1263 PCI_CONFIGURATION_DATA_PORT
,
1272 Reads a range of PCI configuration registers into a caller supplied buffer.
1274 Reads the range of PCI configuration registers specified by StartAddress and
1275 Size into the buffer specified by Buffer. This function only allows the PCI
1276 configuration registers from a single PCI function to be read. Size is
1277 returned. When possible 32-bit PCI configuration read cycles are used to read
1278 from StartAdress to StartAddress + Size. Due to alignment restrictions, 8-bit
1279 and 16-bit PCI configuration read cycles may be used at the beginning and the
1282 If StartAddress > 0x0FFFFFFF, then ASSERT().
1283 If the register specified by StartAddress >= 0x100, then ASSERT().
1284 If ((StartAddress & 0xFFF) + Size) > 0x100, then ASSERT().
1285 If Size > 0 and Buffer is NULL, then ASSERT().
1287 @param StartAddress Starting address that encodes the PCI Bus, Device,
1288 Function and Register.
1289 @param Size Size in bytes of the transfer.
1290 @param Buffer Pointer to a buffer receiving the data read.
1298 IN UINTN StartAddress
,
1305 ASSERT_INVALID_PCI_ADDRESS (StartAddress
, 0);
1306 ASSERT (((StartAddress
& 0xFFF) + Size
) <= 0x100);
1312 ASSERT (Buffer
!= NULL
);
1315 // Save Size for return
1319 if ((StartAddress
& 1) != 0) {
1321 // Read a byte if StartAddress is byte aligned
1323 *(volatile UINT8
*)Buffer
= PciCf8Read8 (StartAddress
);
1324 StartAddress
+= sizeof (UINT8
);
1325 Size
-= sizeof (UINT8
);
1326 Buffer
= (UINT8
*)Buffer
+ 1;
1329 if (Size
>= sizeof (UINT16
) && (StartAddress
& 2) != 0) {
1331 // Read a word if StartAddress is word aligned
1333 *(volatile UINT16
*)Buffer
= PciCf8Read16 (StartAddress
);
1334 StartAddress
+= sizeof (UINT16
);
1335 Size
-= sizeof (UINT16
);
1336 Buffer
= (UINT16
*)Buffer
+ 1;
1339 while (Size
>= sizeof (UINT32
)) {
1341 // Read as many double words as possible
1343 *(volatile UINT32
*)Buffer
= PciCf8Read32 (StartAddress
);
1344 StartAddress
+= sizeof (UINT32
);
1345 Size
-= sizeof (UINT32
);
1346 Buffer
= (UINT32
*)Buffer
+ 1;
1349 if (Size
>= sizeof (UINT16
)) {
1351 // Read the last remaining word if exist
1353 *(volatile UINT16
*)Buffer
= PciCf8Read16 (StartAddress
);
1354 StartAddress
+= sizeof (UINT16
);
1355 Size
-= sizeof (UINT16
);
1356 Buffer
= (UINT16
*)Buffer
+ 1;
1359 if (Size
>= sizeof (UINT8
)) {
1361 // Read the last remaining byte if exist
1363 *(volatile UINT8
*)Buffer
= PciCf8Read8 (StartAddress
);
1370 Copies the data in a caller supplied buffer to a specified range of PCI
1371 configuration space.
1373 Writes the range of PCI configuration registers specified by StartAddress and
1374 Size from the buffer specified by Buffer. This function only allows the PCI
1375 configuration registers from a single PCI function to be written. Size is
1376 returned. When possible 32-bit PCI configuration write cycles are used to
1377 write from StartAdress to StartAddress + Size. Due to alignment restrictions,
1378 8-bit and 16-bit PCI configuration write cycles may be used at the beginning
1379 and the end of the range.
1381 If StartAddress > 0x0FFFFFFF, then ASSERT().
1382 If the register specified by StartAddress >= 0x100, then ASSERT().
1383 If ((StartAddress & 0xFFF) + Size) > 0x100, then ASSERT().
1384 If Size > 0 and Buffer is NULL, then ASSERT().
1386 @param StartAddress Starting address that encodes the PCI Bus, Device,
1387 Function and Register.
1388 @param Size Size in bytes of the transfer.
1389 @param Buffer Pointer to a buffer containing the data to write.
1397 IN UINTN StartAddress
,
1404 ASSERT_INVALID_PCI_ADDRESS (StartAddress
, 0);
1405 ASSERT (((StartAddress
& 0xFFF) + Size
) <= 0x100);
1411 ASSERT (Buffer
!= NULL
);
1414 // Save Size for return
1418 if ((StartAddress
& 1) != 0) {
1420 // Write a byte if StartAddress is byte aligned
1422 PciCf8Write8 (StartAddress
, *(UINT8
*)Buffer
);
1423 StartAddress
+= sizeof (UINT8
);
1424 Size
-= sizeof (UINT8
);
1425 Buffer
= (UINT8
*)Buffer
+ 1;
1428 if (Size
>= sizeof (UINT16
) && (StartAddress
& 2) != 0) {
1430 // Write a word if StartAddress is word aligned
1432 PciCf8Write16 (StartAddress
, *(UINT16
*)Buffer
);
1433 StartAddress
+= sizeof (UINT16
);
1434 Size
-= sizeof (UINT16
);
1435 Buffer
= (UINT16
*)Buffer
+ 1;
1438 while (Size
>= sizeof (UINT32
)) {
1440 // Write as many double words as possible
1442 PciCf8Write32 (StartAddress
, *(UINT32
*)Buffer
);
1443 StartAddress
+= sizeof (UINT32
);
1444 Size
-= sizeof (UINT32
);
1445 Buffer
= (UINT32
*)Buffer
+ 1;
1448 if (Size
>= sizeof (UINT16
)) {
1450 // Write the last remaining word if exist
1452 PciCf8Write16 (StartAddress
, *(UINT16
*)Buffer
);
1453 StartAddress
+= sizeof (UINT16
);
1454 Size
-= sizeof (UINT16
);
1455 Buffer
= (UINT16
*)Buffer
+ 1;
1458 if (Size
>= sizeof (UINT8
)) {
1460 // Write the last remaining byte if exist
1462 PciCf8Write8 (StartAddress
, *(UINT8
*)Buffer
);