VirtualBox

source: vbox/trunk/src/VBox/Devices/EFI/Firmware/MdePkg/Library/BasePciExpressLib/PciExpressLib.c

最後變更 在這個檔案是 99404,由 vboxsync 提交於 2 年 前

Devices/EFI/FirmwareNew: Update to edk2-stable202302 and make it build, bugref:4643

  • 屬性 svn:eol-style 設為 native
檔案大小: 49.8 KB
 
1/** @file
2 Functions in this library instance make use of MMIO functions in IoLib to
3 access memory mapped PCI configuration space.
4
5 All assertions for I/O operations are handled in MMIO functions in the IoLib
6 Library.
7
8 Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
9 SPDX-License-Identifier: BSD-2-Clause-Patent
10
11**/
12
13#include <Base.h>
14
15#include <Library/BaseLib.h>
16#include <Library/PciExpressLib.h>
17#include <Library/IoLib.h>
18#include <Library/DebugLib.h>
19#include <Library/PcdLib.h>
20
21/**
22 Assert the validity of a PCI address. A valid PCI address should contain 1's
23 only in the low 28 bits. PcdPciExpressBaseSize limits the size to the real
24 number of PCI busses in this segment.
25
26 @param A The address to validate.
27
28**/
29#define ASSERT_INVALID_PCI_ADDRESS(A) \
30 ASSERT (((A) & ~0xfffffff) == 0)
31
32#ifdef VBOX
33
34STATIC UINT64 mPciExpressBaseAddress;
35
36RETURN_STATUS
37EFIAPI
38PciExpressLibConstructor (
39 VOID
40 )
41{
42 //
43 // Accessing PciExpressBaseAddress as a dynamic PCD does not work
44 // because LibPcdGet64() worker tries to raise the TPL to 16 when
45 // it was already set to 31 by caller further up the chain. We need
46 // to read the value (which won't change) and cache it here.
47 //
48 mPciExpressBaseAddress = PcdGet64 (PcdPciExpressBaseAddress);
49 if (!mPciExpressBaseAddress)
50 return RETURN_LOAD_ERROR;
51
52 return RETURN_SUCCESS;
53}
54#endif
55
56
57/**
58 Registers a PCI device so PCI configuration registers may be accessed after
59 SetVirtualAddressMap().
60
61 Registers the PCI device specified by Address so all the PCI configuration
62 registers associated with that PCI device may be accessed after SetVirtualAddressMap()
63 is called.
64
65 If Address > 0x0FFFFFFF, then ASSERT().
66
67 @param Address The address that encodes the PCI Bus, Device, Function and
68 Register.
69
70 @retval RETURN_SUCCESS The PCI device was registered for runtime access.
71 @retval RETURN_UNSUPPORTED An attempt was made to call this function
72 after ExitBootServices().
73 @retval RETURN_UNSUPPORTED The resources required to access the PCI device
74 at runtime could not be mapped.
75 @retval RETURN_OUT_OF_RESOURCES There are not enough resources available to
76 complete the registration.
77
78**/
79RETURN_STATUS
80EFIAPI
81PciExpressRegisterForRuntimeAccess (
82 IN UINTN Address
83 )
84{
85 ASSERT_INVALID_PCI_ADDRESS (Address);
86 return RETURN_UNSUPPORTED;
87}
88
89/**
90 Gets the base address of PCI Express.
91
92 This internal functions retrieves PCI Express Base Address via a PCD entry
93 PcdPciExpressBaseAddress.
94
95 @return The base address of PCI Express.
96
97**/
98VOID *
99GetPciExpressBaseAddress (
100 VOID
101 )
102{
103#ifdef VBOX
104 return (VOID*)(UINTN) mPciExpressBaseAddress;
105#else
106 return (VOID *)(UINTN)PcdGet64 (PcdPciExpressBaseAddress);
107#endif
108}
109
110/**
111 Gets the size of PCI Express.
112
113 This internal functions retrieves PCI Express Base Size via a PCD entry
114 PcdPciExpressBaseSize.
115
116 @return The base size of PCI Express.
117
118**/
119STATIC
120UINTN
121PcdPciExpressBaseSize (
122 VOID
123 )
124{
125 return (UINTN)PcdGet64 (PcdPciExpressBaseSize);
126}
127
128/**
129 Reads an 8-bit PCI configuration register.
130
131 Reads and returns the 8-bit PCI configuration register specified by Address.
132 This function must guarantee that all PCI read and write operations are
133 serialized.
134
135 If Address > 0x0FFFFFFF, then ASSERT().
136
137 @param Address The address that encodes the PCI Bus, Device, Function and
138 Register.
139
140 @retval 0xFF Invalid PCI address.
141 @retval other The read value from the PCI configuration register.
142
143**/
144UINT8
145EFIAPI
146PciExpressRead8 (
147 IN UINTN Address
148 )
149{
150 ASSERT_INVALID_PCI_ADDRESS (Address);
151 if (Address >= PcdPciExpressBaseSize ()) {
152 return (UINT8)-1;
153 }
154
155 return MmioRead8 ((UINTN)GetPciExpressBaseAddress () + Address);
156}
157
158/**
159 Writes an 8-bit PCI configuration register.
160
161 Writes the 8-bit PCI configuration register specified by Address with the
162 value specified by Value. Value is returned. This function must guarantee
163 that all PCI read and write operations are serialized.
164
165 If Address > 0x0FFFFFFF, then ASSERT().
166
167 @param Address The address that encodes the PCI Bus, Device, Function and
168 Register.
169 @param Value The value to write.
170
171 @retval 0xFF Invalid PCI address.
172 @retval other The value written to the PCI configuration register.
173
174**/
175UINT8
176EFIAPI
177PciExpressWrite8 (
178 IN UINTN Address,
179 IN UINT8 Value
180 )
181{
182 ASSERT_INVALID_PCI_ADDRESS (Address);
183 if (Address >= PcdPciExpressBaseSize ()) {
184 return (UINT8)-1;
185 }
186
187 return MmioWrite8 ((UINTN)GetPciExpressBaseAddress () + Address, Value);
188}
189
190/**
191 Performs a bitwise OR of an 8-bit PCI configuration register with
192 an 8-bit value.
193
194 Reads the 8-bit PCI configuration register specified by Address, performs a
195 bitwise OR between the read result and the value specified by
196 OrData, and writes the result to the 8-bit PCI configuration register
197 specified by Address. The value written to the PCI configuration register is
198 returned. This function must guarantee that all PCI read and write operations
199 are serialized.
200
201 If Address > 0x0FFFFFFF, then ASSERT().
202
203 @param Address The address that encodes the PCI Bus, Device, Function and
204 Register.
205 @param OrData The value to OR with the PCI configuration register.
206
207 @retval 0xFF Invalid PCI address.
208 @retval other The value written to the PCI configuration register.
209
210**/
211UINT8
212EFIAPI
213PciExpressOr8 (
214 IN UINTN Address,
215 IN UINT8 OrData
216 )
217{
218 ASSERT_INVALID_PCI_ADDRESS (Address);
219 if (Address >= PcdPciExpressBaseSize ()) {
220 return (UINT8)-1;
221 }
222
223 return MmioOr8 ((UINTN)GetPciExpressBaseAddress () + Address, OrData);
224}
225
226/**
227 Performs a bitwise AND of an 8-bit PCI configuration register with an 8-bit
228 value.
229
230 Reads the 8-bit PCI configuration register specified by Address, performs a
231 bitwise AND between the read result and the value specified by AndData, and
232 writes the result to the 8-bit PCI configuration register specified by
233 Address. The value written to the PCI configuration register is returned.
234 This function must guarantee that all PCI read and write operations are
235 serialized.
236
237 If Address > 0x0FFFFFFF, then ASSERT().
238
239 @param Address The address that encodes the PCI Bus, Device, Function and
240 Register.
241 @param AndData The value to AND with the PCI configuration register.
242
243 @retval 0xFF Invalid PCI address.
244 @retval other The value written back to the PCI configuration register.
245
246**/
247UINT8
248EFIAPI
249PciExpressAnd8 (
250 IN UINTN Address,
251 IN UINT8 AndData
252 )
253{
254 ASSERT_INVALID_PCI_ADDRESS (Address);
255 if (Address >= PcdPciExpressBaseSize ()) {
256 return (UINT8)-1;
257 }
258
259 return MmioAnd8 ((UINTN)GetPciExpressBaseAddress () + Address, AndData);
260}
261
262/**
263 Performs a bitwise AND of an 8-bit PCI configuration register with an 8-bit
264 value, followed a bitwise OR with another 8-bit value.
265
266 Reads the 8-bit PCI configuration register specified by Address, performs a
267 bitwise AND between the read result and the value specified by AndData,
268 performs a bitwise OR between the result of the AND operation and
269 the value specified by OrData, and writes the result to the 8-bit PCI
270 configuration register specified by Address. The value written to the PCI
271 configuration register is returned. This function must guarantee that all PCI
272 read and write operations are serialized.
273
274 If Address > 0x0FFFFFFF, then ASSERT().
275
276 @param Address The address that encodes the PCI Bus, Device, Function and
277 Register.
278 @param AndData The value to AND with the PCI configuration register.
279 @param OrData The value to OR with the result of the AND operation.
280
281 @retval 0xFF Invalid PCI address.
282 @retval other The value written back to the PCI configuration register.
283
284**/
285UINT8
286EFIAPI
287PciExpressAndThenOr8 (
288 IN UINTN Address,
289 IN UINT8 AndData,
290 IN UINT8 OrData
291 )
292{
293 ASSERT_INVALID_PCI_ADDRESS (Address);
294 if (Address >= PcdPciExpressBaseSize ()) {
295 return (UINT8)-1;
296 }
297
298 return MmioAndThenOr8 (
299 (UINTN)GetPciExpressBaseAddress () + Address,
300 AndData,
301 OrData
302 );
303}
304
305/**
306 Reads a bit field of a PCI configuration register.
307
308 Reads the bit field in an 8-bit PCI configuration register. The bit field is
309 specified by the StartBit and the EndBit. The value of the bit field is
310 returned.
311
312 If Address > 0x0FFFFFFF, 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().
316
317 @param Address The PCI configuration register to read.
318 @param StartBit The ordinal of the least significant bit in the bit field.
319 Range 0..7.
320 @param EndBit The ordinal of the most significant bit in the bit field.
321 Range 0..7.
322
323 @retval 0xFF Invalid PCI address.
324 @retval other The value of the bit field read from the PCI configuration
325 register.
326
327**/
328UINT8
329EFIAPI
330PciExpressBitFieldRead8 (
331 IN UINTN Address,
332 IN UINTN StartBit,
333 IN UINTN EndBit
334 )
335{
336 ASSERT_INVALID_PCI_ADDRESS (Address);
337 if (Address >= PcdPciExpressBaseSize ()) {
338 return (UINT8)-1;
339 }
340
341 return MmioBitFieldRead8 (
342 (UINTN)GetPciExpressBaseAddress () + Address,
343 StartBit,
344 EndBit
345 );
346}
347
348/**
349 Writes a bit field to a PCI configuration register.
350
351 Writes Value to the bit field of the PCI configuration register. The bit
352 field is specified by the StartBit and the EndBit. All other bits in the
353 destination PCI configuration register are preserved. The new value of the
354 8-bit register is returned.
355
356 If Address > 0x0FFFFFFF, then ASSERT().
357 If StartBit is greater than 7, then ASSERT().
358 If EndBit is greater than 7, then ASSERT().
359 If EndBit is less than StartBit, then ASSERT().
360 If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
361
362 @param Address The PCI configuration register to write.
363 @param StartBit The ordinal of the least significant bit in the bit field.
364 Range 0..7.
365 @param EndBit The ordinal of the most significant bit in the bit field.
366 Range 0..7.
367 @param Value The new value of the bit field.
368
369 @retval 0xFF Invalid PCI address.
370 @retval other The value written back to the PCI configuration register.
371
372**/
373UINT8
374EFIAPI
375PciExpressBitFieldWrite8 (
376 IN UINTN Address,
377 IN UINTN StartBit,
378 IN UINTN EndBit,
379 IN UINT8 Value
380 )
381{
382 ASSERT_INVALID_PCI_ADDRESS (Address);
383 if (Address >= PcdPciExpressBaseSize ()) {
384 return (UINT8)-1;
385 }
386
387 return MmioBitFieldWrite8 (
388 (UINTN)GetPciExpressBaseAddress () + Address,
389 StartBit,
390 EndBit,
391 Value
392 );
393}
394
395/**
396 Reads a bit field in an 8-bit PCI configuration, performs a bitwise OR, and
397 writes the result back to the bit field in the 8-bit port.
398
399 Reads the 8-bit PCI configuration register specified by Address, performs a
400 bitwise OR between the read result and the value specified by
401 OrData, and writes the result to the 8-bit PCI configuration register
402 specified by Address. The value written to the PCI configuration register is
403 returned. This function must guarantee that all PCI read and write operations
404 are serialized. Extra left bits in OrData are stripped.
405
406 If Address > 0x0FFFFFFF, then ASSERT().
407 If StartBit is greater than 7, then ASSERT().
408 If EndBit is greater than 7, then ASSERT().
409 If EndBit is less than StartBit, then ASSERT().
410 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
411
412 @param Address The PCI configuration register to write.
413 @param StartBit The ordinal of the least significant bit in the bit field.
414 Range 0..7.
415 @param EndBit The ordinal of the most significant bit in the bit field.
416 Range 0..7.
417 @param OrData The value to OR with the PCI configuration register.
418
419 @retval 0xFF Invalid PCI address.
420 @retval other The value written back to the PCI configuration register.
421
422**/
423UINT8
424EFIAPI
425PciExpressBitFieldOr8 (
426 IN UINTN Address,
427 IN UINTN StartBit,
428 IN UINTN EndBit,
429 IN UINT8 OrData
430 )
431{
432 ASSERT_INVALID_PCI_ADDRESS (Address);
433 if (Address >= PcdPciExpressBaseSize ()) {
434 return (UINT8)-1;
435 }
436
437 return MmioBitFieldOr8 (
438 (UINTN)GetPciExpressBaseAddress () + Address,
439 StartBit,
440 EndBit,
441 OrData
442 );
443}
444
445/**
446 Reads a bit field in an 8-bit PCI configuration register, performs a bitwise
447 AND, and writes the result back to the bit field in the 8-bit register.
448
449 Reads the 8-bit PCI configuration register specified by Address, performs a
450 bitwise AND between the read result and the value specified by AndData, and
451 writes the result to the 8-bit PCI configuration register specified by
452 Address. The value written to the PCI configuration register is returned.
453 This function must guarantee that all PCI read and write operations are
454 serialized. Extra left bits in AndData are stripped.
455
456 If Address > 0x0FFFFFFF, then ASSERT().
457 If StartBit is greater than 7, then ASSERT().
458 If EndBit is greater than 7, then ASSERT().
459 If EndBit is less than StartBit, then ASSERT().
460 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
461
462 @param Address The PCI configuration register to write.
463 @param StartBit The ordinal of the least significant bit in the bit field.
464 Range 0..7.
465 @param EndBit The ordinal of the most significant bit in the bit field.
466 Range 0..7.
467 @param AndData The value to AND with the PCI configuration register.
468
469 @retval 0xFF Invalid PCI address.
470 @retval other The value written back to the PCI configuration register.
471
472**/
473UINT8
474EFIAPI
475PciExpressBitFieldAnd8 (
476 IN UINTN Address,
477 IN UINTN StartBit,
478 IN UINTN EndBit,
479 IN UINT8 AndData
480 )
481{
482 ASSERT_INVALID_PCI_ADDRESS (Address);
483 if (Address >= PcdPciExpressBaseSize ()) {
484 return (UINT8)-1;
485 }
486
487 return MmioBitFieldAnd8 (
488 (UINTN)GetPciExpressBaseAddress () + Address,
489 StartBit,
490 EndBit,
491 AndData
492 );
493}
494
495/**
496 Reads a bit field in an 8-bit port, performs a bitwise AND followed by a
497 bitwise OR, and writes the result back to the bit field in the
498 8-bit port.
499
500 Reads the 8-bit PCI configuration register specified by Address, performs a
501 bitwise AND followed by a bitwise OR between the read result and
502 the value specified by AndData, and writes the result to the 8-bit PCI
503 configuration register specified by Address. The value written to the PCI
504 configuration register is returned. This function must guarantee that all PCI
505 read and write operations are serialized. Extra left bits in both AndData and
506 OrData are stripped.
507
508 If Address > 0x0FFFFFFF, then ASSERT().
509 If StartBit is greater than 7, then ASSERT().
510 If EndBit is greater than 7, then ASSERT().
511 If EndBit is less than StartBit, then ASSERT().
512 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
513 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
514
515 @param Address The PCI configuration register to write.
516 @param StartBit The ordinal of the least significant bit in the bit field.
517 Range 0..7.
518 @param EndBit The ordinal of the most significant bit in the bit field.
519 Range 0..7.
520 @param AndData The value to AND with the PCI configuration register.
521 @param OrData The value to OR with the result of the AND operation.
522
523 @retval 0xFF Invalid PCI address.
524 @retval other The value written back to the PCI configuration register.
525
526**/
527UINT8
528EFIAPI
529PciExpressBitFieldAndThenOr8 (
530 IN UINTN Address,
531 IN UINTN StartBit,
532 IN UINTN EndBit,
533 IN UINT8 AndData,
534 IN UINT8 OrData
535 )
536{
537 ASSERT_INVALID_PCI_ADDRESS (Address);
538 if (Address >= PcdPciExpressBaseSize ()) {
539 return (UINT8)-1;
540 }
541
542 return MmioBitFieldAndThenOr8 (
543 (UINTN)GetPciExpressBaseAddress () + Address,
544 StartBit,
545 EndBit,
546 AndData,
547 OrData
548 );
549}
550
551/**
552 Reads a 16-bit PCI configuration register.
553
554 Reads and returns the 16-bit PCI configuration register specified by Address.
555 This function must guarantee that all PCI read and write operations are
556 serialized.
557
558 If Address > 0x0FFFFFFF, then ASSERT().
559 If Address is not aligned on a 16-bit boundary, then ASSERT().
560
561 @param Address The address that encodes the PCI Bus, Device, Function and
562 Register.
563
564 @retval 0xFF Invalid PCI address.
565 @retval other The read value from the PCI configuration register.
566
567**/
568UINT16
569EFIAPI
570PciExpressRead16 (
571 IN UINTN Address
572 )
573{
574 ASSERT_INVALID_PCI_ADDRESS (Address);
575 if (Address >= PcdPciExpressBaseSize ()) {
576 return (UINT16)-1;
577 }
578
579 return MmioRead16 ((UINTN)GetPciExpressBaseAddress () + Address);
580}
581
582/**
583 Writes a 16-bit PCI configuration register.
584
585 Writes the 16-bit PCI configuration register specified by Address with the
586 value specified by Value. Value is returned. This function must guarantee
587 that all PCI read and write operations are serialized.
588
589 If Address > 0x0FFFFFFF, then ASSERT().
590 If Address is not aligned on a 16-bit boundary, then ASSERT().
591
592 @param Address The address that encodes the PCI Bus, Device, Function and
593 Register.
594 @param Value The value to write.
595
596 @retval 0xFFFF Invalid PCI address.
597 @retval other The value written to the PCI configuration register.
598
599**/
600UINT16
601EFIAPI
602PciExpressWrite16 (
603 IN UINTN Address,
604 IN UINT16 Value
605 )
606{
607 ASSERT_INVALID_PCI_ADDRESS (Address);
608 if (Address >= PcdPciExpressBaseSize ()) {
609 return (UINT16)-1;
610 }
611
612 return MmioWrite16 ((UINTN)GetPciExpressBaseAddress () + Address, Value);
613}
614
615/**
616 Performs a bitwise OR of a 16-bit PCI configuration register with
617 a 16-bit value.
618
619 Reads the 16-bit PCI configuration register specified by Address, performs a
620 bitwise OR between the read result and the value specified by
621 OrData, and writes the result to the 16-bit PCI configuration register
622 specified by Address. The value written to the PCI configuration register is
623 returned. This function must guarantee that all PCI read and write operations
624 are serialized.
625
626 If Address > 0x0FFFFFFF, then ASSERT().
627 If Address is not aligned on a 16-bit boundary, then ASSERT().
628
629 @param Address The address that encodes the PCI Bus, Device, Function and
630 Register.
631 @param OrData The value to OR with the PCI configuration register.
632
633 @retval 0xFFFF Invalid PCI address.
634 @retval other The value written back to the PCI configuration register.
635
636**/
637UINT16
638EFIAPI
639PciExpressOr16 (
640 IN UINTN Address,
641 IN UINT16 OrData
642 )
643{
644 ASSERT_INVALID_PCI_ADDRESS (Address);
645 if (Address >= PcdPciExpressBaseSize ()) {
646 return (UINT16)-1;
647 }
648
649 return MmioOr16 ((UINTN)GetPciExpressBaseAddress () + Address, OrData);
650}
651
652/**
653 Performs a bitwise AND of a 16-bit PCI configuration register with a 16-bit
654 value.
655
656 Reads the 16-bit PCI configuration register specified by Address, performs a
657 bitwise AND between the read result and the value specified by AndData, and
658 writes the result to the 16-bit PCI configuration register specified by
659 Address. The value written to the PCI configuration register is returned.
660 This function must guarantee that all PCI read and write operations are
661 serialized.
662
663 If Address > 0x0FFFFFFF, then ASSERT().
664 If Address is not aligned on a 16-bit boundary, then ASSERT().
665
666 @param Address The address that encodes the PCI Bus, Device, Function and
667 Register.
668 @param AndData The value to AND with the PCI configuration register.
669
670 @retval 0xFFFF Invalid PCI address.
671 @retval other The value written back to the PCI configuration register.
672
673**/
674UINT16
675EFIAPI
676PciExpressAnd16 (
677 IN UINTN Address,
678 IN UINT16 AndData
679 )
680{
681 ASSERT_INVALID_PCI_ADDRESS (Address);
682 if (Address >= PcdPciExpressBaseSize ()) {
683 return (UINT16)-1;
684 }
685
686 return MmioAnd16 ((UINTN)GetPciExpressBaseAddress () + Address, AndData);
687}
688
689/**
690 Performs a bitwise AND of a 16-bit PCI configuration register with a 16-bit
691 value, followed a bitwise OR with another 16-bit value.
692
693 Reads the 16-bit PCI configuration register specified by Address, performs a
694 bitwise AND between the read result and the value specified by AndData,
695 performs a bitwise OR between the result of the AND operation and
696 the value specified by OrData, and writes the result to the 16-bit PCI
697 configuration register specified by Address. The value written to the PCI
698 configuration register is returned. This function must guarantee that all PCI
699 read and write operations are serialized.
700
701 If Address > 0x0FFFFFFF, then ASSERT().
702 If Address is not aligned on a 16-bit boundary, then ASSERT().
703
704 @param Address The address that encodes the PCI Bus, Device, Function and
705 Register.
706 @param AndData The value to AND with the PCI configuration register.
707 @param OrData The value to OR with the result of the AND operation.
708
709 @retval 0xFFFF Invalid PCI address.
710 @retval other The value written back to the PCI configuration register.
711
712**/
713UINT16
714EFIAPI
715PciExpressAndThenOr16 (
716 IN UINTN Address,
717 IN UINT16 AndData,
718 IN UINT16 OrData
719 )
720{
721 ASSERT_INVALID_PCI_ADDRESS (Address);
722 if (Address >= PcdPciExpressBaseSize ()) {
723 return (UINT16)-1;
724 }
725
726 return MmioAndThenOr16 (
727 (UINTN)GetPciExpressBaseAddress () + Address,
728 AndData,
729 OrData
730 );
731}
732
733/**
734 Reads a bit field of a PCI configuration register.
735
736 Reads the bit field in a 16-bit PCI configuration register. The bit field is
737 specified by the StartBit and the EndBit. The value of the bit field is
738 returned.
739
740 If Address > 0x0FFFFFFF, then ASSERT().
741 If Address is not aligned on a 16-bit boundary, then ASSERT().
742 If StartBit is greater than 15, then ASSERT().
743 If EndBit is greater than 15, then ASSERT().
744 If EndBit is less than StartBit, then ASSERT().
745
746 @param Address The PCI configuration register to read.
747 @param StartBit The ordinal of the least significant bit in the bit field.
748 Range 0..15.
749 @param EndBit The ordinal of the most significant bit in the bit field.
750 Range 0..15.
751
752 @retval 0xFFFF Invalid PCI address.
753 @retval other The value of the bit field read from the PCI configuration
754 register.
755
756**/
757UINT16
758EFIAPI
759PciExpressBitFieldRead16 (
760 IN UINTN Address,
761 IN UINTN StartBit,
762 IN UINTN EndBit
763 )
764{
765 ASSERT_INVALID_PCI_ADDRESS (Address);
766 if (Address >= PcdPciExpressBaseSize ()) {
767 return (UINT16)-1;
768 }
769
770 return MmioBitFieldRead16 (
771 (UINTN)GetPciExpressBaseAddress () + Address,
772 StartBit,
773 EndBit
774 );
775}
776
777/**
778 Writes a bit field to a PCI configuration register.
779
780 Writes Value to the bit field of the PCI configuration register. The bit
781 field is specified by the StartBit and the EndBit. All other bits in the
782 destination PCI configuration register are preserved. The new value of the
783 16-bit register is returned.
784
785 If Address > 0x0FFFFFFF, then ASSERT().
786 If Address is not aligned on a 16-bit boundary, then ASSERT().
787 If StartBit is greater than 15, then ASSERT().
788 If EndBit is greater than 15, then ASSERT().
789 If EndBit is less than StartBit, then ASSERT().
790 If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
791
792 @param Address The PCI configuration register to write.
793 @param StartBit The ordinal of the least significant bit in the bit field.
794 Range 0..15.
795 @param EndBit The ordinal of the most significant bit in the bit field.
796 Range 0..15.
797 @param Value The new value of the bit field.
798
799 @retval 0xFFFF Invalid PCI address.
800 @retval other The value written back to the PCI configuration register.
801
802**/
803UINT16
804EFIAPI
805PciExpressBitFieldWrite16 (
806 IN UINTN Address,
807 IN UINTN StartBit,
808 IN UINTN EndBit,
809 IN UINT16 Value
810 )
811{
812 ASSERT_INVALID_PCI_ADDRESS (Address);
813 if (Address >= PcdPciExpressBaseSize ()) {
814 return (UINT16)-1;
815 }
816
817 return MmioBitFieldWrite16 (
818 (UINTN)GetPciExpressBaseAddress () + Address,
819 StartBit,
820 EndBit,
821 Value
822 );
823}
824
825/**
826 Reads a bit field in a 16-bit PCI configuration, performs a bitwise OR, and
827 writes the result back to the bit field in the 16-bit port.
828
829 Reads the 16-bit PCI configuration register specified by Address, performs a
830 bitwise OR between the read result and the value specified by
831 OrData, and writes the result to the 16-bit PCI configuration register
832 specified by Address. The value written to the PCI configuration register is
833 returned. This function must guarantee that all PCI read and write operations
834 are serialized. Extra left bits in OrData are stripped.
835
836 If Address > 0x0FFFFFFF, then ASSERT().
837 If Address is not aligned on a 16-bit boundary, then ASSERT().
838 If StartBit is greater than 15, then ASSERT().
839 If EndBit is greater than 15, then ASSERT().
840 If EndBit is less than StartBit, then ASSERT().
841 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
842
843 @param Address The PCI configuration register to write.
844 @param StartBit The ordinal of the least significant bit in the bit field.
845 Range 0..15.
846 @param EndBit The ordinal of the most significant bit in the bit field.
847 Range 0..15.
848 @param OrData The value to OR with the PCI configuration register.
849
850 @retval 0xFFFF Invalid PCI address.
851 @retval other The value written back to the PCI configuration register.
852
853**/
854UINT16
855EFIAPI
856PciExpressBitFieldOr16 (
857 IN UINTN Address,
858 IN UINTN StartBit,
859 IN UINTN EndBit,
860 IN UINT16 OrData
861 )
862{
863 ASSERT_INVALID_PCI_ADDRESS (Address);
864 if (Address >= PcdPciExpressBaseSize ()) {
865 return (UINT16)-1;
866 }
867
868 return MmioBitFieldOr16 (
869 (UINTN)GetPciExpressBaseAddress () + Address,
870 StartBit,
871 EndBit,
872 OrData
873 );
874}
875
876/**
877 Reads a bit field in a 16-bit PCI configuration register, performs a bitwise
878 AND, and writes the result back to the bit field in the 16-bit register.
879
880 Reads the 16-bit PCI configuration register specified by Address, performs a
881 bitwise AND between the read result and the value specified by AndData, and
882 writes the result to the 16-bit PCI configuration register specified by
883 Address. The value written to the PCI configuration register is returned.
884 This function must guarantee that all PCI read and write operations are
885 serialized. Extra left bits in AndData are stripped.
886
887 If Address > 0x0FFFFFFF, then ASSERT().
888 If Address is not aligned on a 16-bit boundary, then ASSERT().
889 If StartBit is greater than 15, then ASSERT().
890 If EndBit is greater than 15, then ASSERT().
891 If EndBit is less than StartBit, then ASSERT().
892 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
893
894 @param Address The PCI configuration register to write.
895 @param StartBit The ordinal of the least significant bit in the bit field.
896 Range 0..15.
897 @param EndBit The ordinal of the most significant bit in the bit field.
898 Range 0..15.
899 @param AndData The value to AND with the PCI configuration register.
900
901 @retval 0xFFFF Invalid PCI address.
902 @retval other The value written back to the PCI configuration register.
903
904**/
905UINT16
906EFIAPI
907PciExpressBitFieldAnd16 (
908 IN UINTN Address,
909 IN UINTN StartBit,
910 IN UINTN EndBit,
911 IN UINT16 AndData
912 )
913{
914 ASSERT_INVALID_PCI_ADDRESS (Address);
915 if (Address >= PcdPciExpressBaseSize ()) {
916 return (UINT16)-1;
917 }
918
919 return MmioBitFieldAnd16 (
920 (UINTN)GetPciExpressBaseAddress () + Address,
921 StartBit,
922 EndBit,
923 AndData
924 );
925}
926
927/**
928 Reads a bit field in a 16-bit port, performs a bitwise AND followed by a
929 bitwise OR, and writes the result back to the bit field in the
930 16-bit port.
931
932 Reads the 16-bit PCI configuration register specified by Address, performs a
933 bitwise AND followed by a bitwise OR between the read result and
934 the value specified by AndData, and writes the result to the 16-bit PCI
935 configuration register specified by Address. The value written to the PCI
936 configuration register is returned. This function must guarantee that all PCI
937 read and write operations are serialized. Extra left bits in both AndData and
938 OrData are stripped.
939
940 If Address > 0x0FFFFFFF, then ASSERT().
941 If Address is not aligned on a 16-bit boundary, then ASSERT().
942 If StartBit is greater than 15, then ASSERT().
943 If EndBit is greater than 15, then ASSERT().
944 If EndBit is less than StartBit, then ASSERT().
945 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
946 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
947
948 @param Address The PCI configuration register to write.
949 @param StartBit The ordinal of the least significant bit in the bit field.
950 Range 0..15.
951 @param EndBit The ordinal of the most significant bit in the bit field.
952 Range 0..15.
953 @param AndData The value to AND with the PCI configuration register.
954 @param OrData The value to OR with the result of the AND operation.
955
956 @retval 0xFFFF Invalid PCI address.
957 @retval other The value written back to the PCI configuration register.
958
959**/
960UINT16
961EFIAPI
962PciExpressBitFieldAndThenOr16 (
963 IN UINTN Address,
964 IN UINTN StartBit,
965 IN UINTN EndBit,
966 IN UINT16 AndData,
967 IN UINT16 OrData
968 )
969{
970 ASSERT_INVALID_PCI_ADDRESS (Address);
971 if (Address >= PcdPciExpressBaseSize ()) {
972 return (UINT16)-1;
973 }
974
975 return MmioBitFieldAndThenOr16 (
976 (UINTN)GetPciExpressBaseAddress () + Address,
977 StartBit,
978 EndBit,
979 AndData,
980 OrData
981 );
982}
983
984/**
985 Reads a 32-bit PCI configuration register.
986
987 Reads and returns the 32-bit PCI configuration register specified by Address.
988 This function must guarantee that all PCI read and write operations are
989 serialized.
990
991 If Address > 0x0FFFFFFF, then ASSERT().
992 If Address is not aligned on a 32-bit boundary, then ASSERT().
993
994 @param Address The address that encodes the PCI Bus, Device, Function and
995 Register.
996
997 @retval 0xFFFF Invalid PCI address.
998 @retval other The read value from the PCI configuration register.
999
1000**/
1001UINT32
1002EFIAPI
1003PciExpressRead32 (
1004 IN UINTN Address
1005 )
1006{
1007 ASSERT_INVALID_PCI_ADDRESS (Address);
1008 if (Address >= PcdPciExpressBaseSize ()) {
1009 return (UINT32)-1;
1010 }
1011
1012 return MmioRead32 ((UINTN)GetPciExpressBaseAddress () + Address);
1013}
1014
1015/**
1016 Writes a 32-bit PCI configuration register.
1017
1018 Writes the 32-bit PCI configuration register specified by Address with the
1019 value specified by Value. Value is returned. This function must guarantee
1020 that all PCI read and write operations are serialized.
1021
1022 If Address > 0x0FFFFFFF, then ASSERT().
1023 If Address is not aligned on a 32-bit boundary, then ASSERT().
1024
1025 @param Address The address that encodes the PCI Bus, Device, Function and
1026 Register.
1027 @param Value The value to write.
1028
1029 @retval 0xFFFFFFFF Invalid PCI address.
1030 @retval other The value written to the PCI configuration register.
1031
1032**/
1033UINT32
1034EFIAPI
1035PciExpressWrite32 (
1036 IN UINTN Address,
1037 IN UINT32 Value
1038 )
1039{
1040 ASSERT_INVALID_PCI_ADDRESS (Address);
1041 if (Address >= PcdPciExpressBaseSize ()) {
1042 return (UINT32)-1;
1043 }
1044
1045 return MmioWrite32 ((UINTN)GetPciExpressBaseAddress () + Address, Value);
1046}
1047
1048/**
1049 Performs a bitwise OR of a 32-bit PCI configuration register with
1050 a 32-bit value.
1051
1052 Reads the 32-bit PCI configuration register specified by Address, performs a
1053 bitwise OR between the read result and the value specified by
1054 OrData, and writes the result to the 32-bit PCI configuration register
1055 specified by Address. The value written to the PCI configuration register is
1056 returned. This function must guarantee that all PCI read and write operations
1057 are serialized.
1058
1059 If Address > 0x0FFFFFFF, then ASSERT().
1060 If Address is not aligned on a 32-bit boundary, then ASSERT().
1061
1062 @param Address The address that encodes the PCI Bus, Device, Function and
1063 Register.
1064 @param OrData The value to OR with the PCI configuration register.
1065
1066 @retval 0xFFFFFFFF Invalid PCI address.
1067 @retval other The value written back to the PCI configuration register.
1068
1069**/
1070UINT32
1071EFIAPI
1072PciExpressOr32 (
1073 IN UINTN Address,
1074 IN UINT32 OrData
1075 )
1076{
1077 ASSERT_INVALID_PCI_ADDRESS (Address);
1078 if (Address >= PcdPciExpressBaseSize ()) {
1079 return (UINT32)-1;
1080 }
1081
1082 return MmioOr32 ((UINTN)GetPciExpressBaseAddress () + Address, OrData);
1083}
1084
1085/**
1086 Performs a bitwise AND of a 32-bit PCI configuration register with a 32-bit
1087 value.
1088
1089 Reads the 32-bit PCI configuration register specified by Address, performs a
1090 bitwise AND between the read result and the value specified by AndData, and
1091 writes the result to the 32-bit PCI configuration register specified by
1092 Address. The value written to the PCI configuration register is returned.
1093 This function must guarantee that all PCI read and write operations are
1094 serialized.
1095
1096 If Address > 0x0FFFFFFF, then ASSERT().
1097 If Address is not aligned on a 32-bit boundary, then ASSERT().
1098
1099 @param Address The address that encodes the PCI Bus, Device, Function and
1100 Register.
1101 @param AndData The value to AND with the PCI configuration register.
1102
1103 @retval 0xFFFFFFFF Invalid PCI address.
1104 @retval other The value written back to the PCI configuration register.
1105
1106**/
1107UINT32
1108EFIAPI
1109PciExpressAnd32 (
1110 IN UINTN Address,
1111 IN UINT32 AndData
1112 )
1113{
1114 ASSERT_INVALID_PCI_ADDRESS (Address);
1115 if (Address >= PcdPciExpressBaseSize ()) {
1116 return (UINT32)-1;
1117 }
1118
1119 return MmioAnd32 ((UINTN)GetPciExpressBaseAddress () + Address, AndData);
1120}
1121
1122/**
1123 Performs a bitwise AND of a 32-bit PCI configuration register with a 32-bit
1124 value, followed a bitwise OR with another 32-bit value.
1125
1126 Reads the 32-bit PCI configuration register specified by Address, performs a
1127 bitwise AND between the read result and the value specified by AndData,
1128 performs a bitwise OR between the result of the AND operation and
1129 the value specified by OrData, and writes the result to the 32-bit PCI
1130 configuration register specified by Address. The value written to the PCI
1131 configuration register is returned. This function must guarantee that all PCI
1132 read and write operations are serialized.
1133
1134 If Address > 0x0FFFFFFF, then ASSERT().
1135 If Address is not aligned on a 32-bit boundary, then ASSERT().
1136
1137 @param Address The address that encodes the PCI Bus, Device, Function and
1138 Register.
1139 @param AndData The value to AND with the PCI configuration register.
1140 @param OrData The value to OR with the result of the AND operation.
1141
1142 @retval 0xFFFFFFFF Invalid PCI address.
1143 @retval other The value written back to the PCI configuration register.
1144
1145**/
1146UINT32
1147EFIAPI
1148PciExpressAndThenOr32 (
1149 IN UINTN Address,
1150 IN UINT32 AndData,
1151 IN UINT32 OrData
1152 )
1153{
1154 ASSERT_INVALID_PCI_ADDRESS (Address);
1155 if (Address >= PcdPciExpressBaseSize ()) {
1156 return (UINT32)-1;
1157 }
1158
1159 return MmioAndThenOr32 (
1160 (UINTN)GetPciExpressBaseAddress () + Address,
1161 AndData,
1162 OrData
1163 );
1164}
1165
1166/**
1167 Reads a bit field of a PCI configuration register.
1168
1169 Reads the bit field in a 32-bit PCI configuration register. The bit field is
1170 specified by the StartBit and the EndBit. The value of the bit field is
1171 returned.
1172
1173 If Address > 0x0FFFFFFF, then ASSERT().
1174 If Address is not aligned on a 32-bit boundary, then ASSERT().
1175 If StartBit is greater than 31, then ASSERT().
1176 If EndBit is greater than 31, then ASSERT().
1177 If EndBit is less than StartBit, then ASSERT().
1178
1179 @param Address The PCI configuration register to read.
1180 @param StartBit The ordinal of the least significant bit in the bit field.
1181 Range 0..31.
1182 @param EndBit The ordinal of the most significant bit in the bit field.
1183 Range 0..31.
1184
1185 @retval 0xFFFFFFFF Invalid PCI address.
1186 @retval other The value of the bit field read from the PCI
1187 configuration register.
1188
1189**/
1190UINT32
1191EFIAPI
1192PciExpressBitFieldRead32 (
1193 IN UINTN Address,
1194 IN UINTN StartBit,
1195 IN UINTN EndBit
1196 )
1197{
1198 ASSERT_INVALID_PCI_ADDRESS (Address);
1199 if (Address >= PcdPciExpressBaseSize ()) {
1200 return (UINT32)-1;
1201 }
1202
1203 return MmioBitFieldRead32 (
1204 (UINTN)GetPciExpressBaseAddress () + Address,
1205 StartBit,
1206 EndBit
1207 );
1208}
1209
1210/**
1211 Writes a bit field to a PCI configuration register.
1212
1213 Writes Value to the bit field of the PCI configuration register. The bit
1214 field is specified by the StartBit and the EndBit. All other bits in the
1215 destination PCI configuration register are preserved. The new value of the
1216 32-bit register is returned.
1217
1218 If Address > 0x0FFFFFFF, then ASSERT().
1219 If Address is not aligned on a 32-bit boundary, then ASSERT().
1220 If StartBit is greater than 31, then ASSERT().
1221 If EndBit is greater than 31, then ASSERT().
1222 If EndBit is less than StartBit, then ASSERT().
1223 If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1224
1225 @param Address The PCI configuration register to write.
1226 @param StartBit The ordinal of the least significant bit in the bit field.
1227 Range 0..31.
1228 @param EndBit The ordinal of the most significant bit in the bit field.
1229 Range 0..31.
1230 @param Value The new value of the bit field.
1231
1232 @retval 0xFFFFFFFF Invalid PCI address.
1233 @retval other The value written back to the PCI configuration register.
1234
1235**/
1236UINT32
1237EFIAPI
1238PciExpressBitFieldWrite32 (
1239 IN UINTN Address,
1240 IN UINTN StartBit,
1241 IN UINTN EndBit,
1242 IN UINT32 Value
1243 )
1244{
1245 ASSERT_INVALID_PCI_ADDRESS (Address);
1246 if (Address >= PcdPciExpressBaseSize ()) {
1247 return (UINT32)-1;
1248 }
1249
1250 return MmioBitFieldWrite32 (
1251 (UINTN)GetPciExpressBaseAddress () + Address,
1252 StartBit,
1253 EndBit,
1254 Value
1255 );
1256}
1257
1258/**
1259 Reads a bit field in a 32-bit PCI configuration, performs a bitwise OR, and
1260 writes the result back to the bit field in the 32-bit port.
1261
1262 Reads the 32-bit PCI configuration register specified by Address, performs a
1263 bitwise OR between the read result and the value specified by
1264 OrData, and writes the result to the 32-bit PCI configuration register
1265 specified by Address. The value written to the PCI configuration register is
1266 returned. This function must guarantee that all PCI read and write operations
1267 are serialized. Extra left bits in OrData are stripped.
1268
1269 If Address > 0x0FFFFFFF, then ASSERT().
1270 If Address is not aligned on a 32-bit boundary, then ASSERT().
1271 If StartBit is greater than 31, then ASSERT().
1272 If EndBit is greater than 31, then ASSERT().
1273 If EndBit is less than StartBit, then ASSERT().
1274 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1275
1276 @param Address The PCI configuration register to write.
1277 @param StartBit The ordinal of the least significant bit in the bit field.
1278 Range 0..31.
1279 @param EndBit The ordinal of the most significant bit in the bit field.
1280 Range 0..31.
1281 @param OrData The value to OR with the PCI configuration register.
1282
1283 @retval 0xFFFFFFFF Invalid PCI address.
1284 @retval other The value written back to the PCI configuration register.
1285
1286**/
1287UINT32
1288EFIAPI
1289PciExpressBitFieldOr32 (
1290 IN UINTN Address,
1291 IN UINTN StartBit,
1292 IN UINTN EndBit,
1293 IN UINT32 OrData
1294 )
1295{
1296 ASSERT_INVALID_PCI_ADDRESS (Address);
1297 if (Address >= PcdPciExpressBaseSize ()) {
1298 return (UINT32)-1;
1299 }
1300
1301 return MmioBitFieldOr32 (
1302 (UINTN)GetPciExpressBaseAddress () + Address,
1303 StartBit,
1304 EndBit,
1305 OrData
1306 );
1307}
1308
1309/**
1310 Reads a bit field in a 32-bit PCI configuration register, performs a bitwise
1311 AND, and writes the result back to the bit field in the 32-bit register.
1312
1313 Reads the 32-bit PCI configuration register specified by Address, performs a
1314 bitwise AND between the read result and the value specified by AndData, and
1315 writes the result to the 32-bit PCI configuration register specified by
1316 Address. The value written to the PCI configuration register is returned.
1317 This function must guarantee that all PCI read and write operations are
1318 serialized. Extra left bits in AndData are stripped.
1319
1320 If Address > 0x0FFFFFFF, then ASSERT().
1321 If Address is not aligned on a 32-bit boundary, then ASSERT().
1322 If StartBit is greater than 31, then ASSERT().
1323 If EndBit is greater than 31, then ASSERT().
1324 If EndBit is less than StartBit, then ASSERT().
1325 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1326
1327 @param Address The PCI configuration register to write.
1328 @param StartBit The ordinal of the least significant bit in the bit field.
1329 Range 0..31.
1330 @param EndBit The ordinal of the most significant bit in the bit field.
1331 Range 0..31.
1332 @param AndData The value to AND with the PCI configuration register.
1333
1334 @retval 0xFFFFFFFF Invalid PCI address.
1335 @retval other The value written back to the PCI configuration register.
1336
1337**/
1338UINT32
1339EFIAPI
1340PciExpressBitFieldAnd32 (
1341 IN UINTN Address,
1342 IN UINTN StartBit,
1343 IN UINTN EndBit,
1344 IN UINT32 AndData
1345 )
1346{
1347 ASSERT_INVALID_PCI_ADDRESS (Address);
1348 if (Address >= PcdPciExpressBaseSize ()) {
1349 return (UINT32)-1;
1350 }
1351
1352 return MmioBitFieldAnd32 (
1353 (UINTN)GetPciExpressBaseAddress () + Address,
1354 StartBit,
1355 EndBit,
1356 AndData
1357 );
1358}
1359
1360/**
1361 Reads a bit field in a 32-bit port, performs a bitwise AND followed by a
1362 bitwise OR, and writes the result back to the bit field in the
1363 32-bit port.
1364
1365 Reads the 32-bit PCI configuration register specified by Address, performs a
1366 bitwise AND followed by a bitwise OR between the read result and
1367 the value specified by AndData, and writes the result to the 32-bit PCI
1368 configuration register specified by Address. The value written to the PCI
1369 configuration register is returned. This function must guarantee that all PCI
1370 read and write operations are serialized. Extra left bits in both AndData and
1371 OrData are stripped.
1372
1373 If Address > 0x0FFFFFFF, then ASSERT().
1374 If Address is not aligned on a 32-bit boundary, then ASSERT().
1375 If StartBit is greater than 31, then ASSERT().
1376 If EndBit is greater than 31, then ASSERT().
1377 If EndBit is less than StartBit, then ASSERT().
1378 If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1379 If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
1380
1381 @param Address The PCI configuration register to write.
1382 @param StartBit The ordinal of the least significant bit in the bit field.
1383 Range 0..31.
1384 @param EndBit The ordinal of the most significant bit in the bit field.
1385 Range 0..31.
1386 @param AndData The value to AND with the PCI configuration register.
1387 @param OrData The value to OR with the result of the AND operation.
1388
1389 @retval 0xFFFFFFFF Invalid PCI address.
1390 @retval other The value written back to the PCI configuration register.
1391
1392**/
1393UINT32
1394EFIAPI
1395PciExpressBitFieldAndThenOr32 (
1396 IN UINTN Address,
1397 IN UINTN StartBit,
1398 IN UINTN EndBit,
1399 IN UINT32 AndData,
1400 IN UINT32 OrData
1401 )
1402{
1403 ASSERT_INVALID_PCI_ADDRESS (Address);
1404 if (Address >= PcdPciExpressBaseSize ()) {
1405 return (UINT32)-1;
1406 }
1407
1408 return MmioBitFieldAndThenOr32 (
1409 (UINTN)GetPciExpressBaseAddress () + Address,
1410 StartBit,
1411 EndBit,
1412 AndData,
1413 OrData
1414 );
1415}
1416
1417/**
1418 Reads a range of PCI configuration registers into a caller supplied buffer.
1419
1420 Reads the range of PCI configuration registers specified by StartAddress and
1421 Size into the buffer specified by Buffer. This function only allows the PCI
1422 configuration registers from a single PCI function to be read. Size is
1423 returned. When possible 32-bit PCI configuration read cycles are used to read
1424 from StartAdress to StartAddress + Size. Due to alignment restrictions, 8-bit
1425 and 16-bit PCI configuration read cycles may be used at the beginning and the
1426 end of the range.
1427
1428 If StartAddress > 0x0FFFFFFF, then ASSERT().
1429 If ((StartAddress & 0xFFF) + Size) > 0x1000, then ASSERT().
1430 If Size > 0 and Buffer is NULL, then ASSERT().
1431
1432 @param StartAddress The starting address that encodes the PCI Bus, Device,
1433 Function and Register.
1434 @param Size The size in bytes of the transfer.
1435 @param Buffer The pointer to a buffer receiving the data read.
1436
1437 @retval (UINTN)-1 Invalid PCI address.
1438 @retval other Size read data from StartAddress.
1439
1440**/
1441UINTN
1442EFIAPI
1443PciExpressReadBuffer (
1444 IN UINTN StartAddress,
1445 IN UINTN Size,
1446 OUT VOID *Buffer
1447 )
1448{
1449 UINTN ReturnValue;
1450
1451 ASSERT_INVALID_PCI_ADDRESS (StartAddress);
1452 if (StartAddress >= PcdPciExpressBaseSize ()) {
1453 return (UINTN)-1;
1454 }
1455
1456 ASSERT (((StartAddress & 0xFFF) + Size) <= 0x1000);
1457
1458 if (Size == 0) {
1459 return Size;
1460 }
1461
1462 ASSERT (Buffer != NULL);
1463
1464 //
1465 // Save Size for return
1466 //
1467 ReturnValue = Size;
1468
1469 if ((StartAddress & 1) != 0) {
1470 //
1471 // Read a byte if StartAddress is byte aligned
1472 //
1473 *(volatile UINT8 *)Buffer = PciExpressRead8 (StartAddress);
1474 StartAddress += sizeof (UINT8);
1475 Size -= sizeof (UINT8);
1476 Buffer = (UINT8 *)Buffer + 1;
1477 }
1478
1479 if ((Size >= sizeof (UINT16)) && ((StartAddress & 2) != 0)) {
1480 //
1481 // Read a word if StartAddress is word aligned
1482 //
1483 WriteUnaligned16 ((UINT16 *)Buffer, (UINT16)PciExpressRead16 (StartAddress));
1484
1485 StartAddress += sizeof (UINT16);
1486 Size -= sizeof (UINT16);
1487 Buffer = (UINT16 *)Buffer + 1;
1488 }
1489
1490 while (Size >= sizeof (UINT32)) {
1491 //
1492 // Read as many double words as possible
1493 //
1494 WriteUnaligned32 ((UINT32 *)Buffer, (UINT32)PciExpressRead32 (StartAddress));
1495
1496 StartAddress += sizeof (UINT32);
1497 Size -= sizeof (UINT32);
1498 Buffer = (UINT32 *)Buffer + 1;
1499 }
1500
1501 if (Size >= sizeof (UINT16)) {
1502 //
1503 // Read the last remaining word if exist
1504 //
1505 WriteUnaligned16 ((UINT16 *)Buffer, (UINT16)PciExpressRead16 (StartAddress));
1506 StartAddress += sizeof (UINT16);
1507 Size -= sizeof (UINT16);
1508 Buffer = (UINT16 *)Buffer + 1;
1509 }
1510
1511 if (Size >= sizeof (UINT8)) {
1512 //
1513 // Read the last remaining byte if exist
1514 //
1515 *(volatile UINT8 *)Buffer = PciExpressRead8 (StartAddress);
1516 }
1517
1518 return ReturnValue;
1519}
1520
1521/**
1522 Copies the data in a caller supplied buffer to a specified range of PCI
1523 configuration space.
1524
1525 Writes the range of PCI configuration registers specified by StartAddress and
1526 Size from the buffer specified by Buffer. This function only allows the PCI
1527 configuration registers from a single PCI function to be written. Size is
1528 returned. When possible 32-bit PCI configuration write cycles are used to
1529 write from StartAdress to StartAddress + Size. Due to alignment restrictions,
1530 8-bit and 16-bit PCI configuration write cycles may be used at the beginning
1531 and the end of the range.
1532
1533 If StartAddress > 0x0FFFFFFF, then ASSERT().
1534 If ((StartAddress & 0xFFF) + Size) > 0x1000, then ASSERT().
1535 If Size > 0 and Buffer is NULL, then ASSERT().
1536
1537 @param StartAddress The starting address that encodes the PCI Bus, Device,
1538 Function and Register.
1539 @param Size The size in bytes of the transfer.
1540 @param Buffer The pointer to a buffer containing the data to write.
1541
1542 @retval (UINTN)-1 Invalid PCI address.
1543 @retval other Size written to StartAddress.
1544
1545**/
1546UINTN
1547EFIAPI
1548PciExpressWriteBuffer (
1549 IN UINTN StartAddress,
1550 IN UINTN Size,
1551 IN VOID *Buffer
1552 )
1553{
1554 UINTN ReturnValue;
1555
1556 ASSERT_INVALID_PCI_ADDRESS (StartAddress);
1557 if (StartAddress >= PcdPciExpressBaseSize ()) {
1558 return (UINTN)-1;
1559 }
1560
1561 ASSERT (((StartAddress & 0xFFF) + Size) <= 0x1000);
1562
1563 if (Size == 0) {
1564 return 0;
1565 }
1566
1567 ASSERT (Buffer != NULL);
1568
1569 //
1570 // Save Size for return
1571 //
1572 ReturnValue = Size;
1573
1574 if ((StartAddress & 1) != 0) {
1575 //
1576 // Write a byte if StartAddress is byte aligned
1577 //
1578 PciExpressWrite8 (StartAddress, *(UINT8 *)Buffer);
1579 StartAddress += sizeof (UINT8);
1580 Size -= sizeof (UINT8);
1581 Buffer = (UINT8 *)Buffer + 1;
1582 }
1583
1584 if ((Size >= sizeof (UINT16)) && ((StartAddress & 2) != 0)) {
1585 //
1586 // Write a word if StartAddress is word aligned
1587 //
1588 PciExpressWrite16 (StartAddress, ReadUnaligned16 ((UINT16 *)Buffer));
1589 StartAddress += sizeof (UINT16);
1590 Size -= sizeof (UINT16);
1591 Buffer = (UINT16 *)Buffer + 1;
1592 }
1593
1594 while (Size >= sizeof (UINT32)) {
1595 //
1596 // Write as many double words as possible
1597 //
1598 PciExpressWrite32 (StartAddress, ReadUnaligned32 ((UINT32 *)Buffer));
1599 StartAddress += sizeof (UINT32);
1600 Size -= sizeof (UINT32);
1601 Buffer = (UINT32 *)Buffer + 1;
1602 }
1603
1604 if (Size >= sizeof (UINT16)) {
1605 //
1606 // Write the last remaining word if exist
1607 //
1608 PciExpressWrite16 (StartAddress, ReadUnaligned16 ((UINT16 *)Buffer));
1609 StartAddress += sizeof (UINT16);
1610 Size -= sizeof (UINT16);
1611 Buffer = (UINT16 *)Buffer + 1;
1612 }
1613
1614 if (Size >= sizeof (UINT8)) {
1615 //
1616 // Write the last remaining byte if exist
1617 //
1618 PciExpressWrite8 (StartAddress, *(UINT8 *)Buffer);
1619 }
1620
1621 return ReturnValue;
1622}
注意: 瀏覽 TracBrowser 來幫助您使用儲存庫瀏覽器

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette