]> git.proxmox.com Git - mirror_edk2.git/blob - ShellPkg/Library/UefiShellDebug1CommandsLib/Pci.c
470f870065531d1159c89ba0cff69346dd66ed57
[mirror_edk2.git] / ShellPkg / Library / UefiShellDebug1CommandsLib / Pci.c
1 /** @file
2 Main file for Pci shell Debug1 function.
3
4 Copyright (c) 2013 Hewlett-Packard Development Company, L.P.
5 Copyright (c) 2005 - 2014, Intel Corporation. All rights reserved.<BR>
6 This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
10
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
13
14 **/
15
16 #include "UefiShellDebug1CommandsLib.h"
17 #include <Protocol/PciRootBridgeIo.h>
18 #include <Library/ShellLib.h>
19 #include <IndustryStandard/Pci.h>
20 #include <IndustryStandard/Acpi.h>
21 #include "Pci.h"
22
23 #define PCI_CLASS_STRING_LIMIT 54
24 //
25 // Printable strings for Pci class code
26 //
27 typedef struct {
28 CHAR16 *BaseClass; // Pointer to the PCI base class string
29 CHAR16 *SubClass; // Pointer to the PCI sub class string
30 CHAR16 *PIFClass; // Pointer to the PCI programming interface string
31 } PCI_CLASS_STRINGS;
32
33 //
34 // a structure holding a single entry, which also points to its lower level
35 // class
36 //
37 typedef struct PCI_CLASS_ENTRY_TAG {
38 UINT8 Code; // Class, subclass or I/F code
39 CHAR16 *DescText; // Description string
40 struct PCI_CLASS_ENTRY_TAG *LowerLevelClass; // Subclass or I/F if any
41 } PCI_CLASS_ENTRY;
42
43 //
44 // Declarations of entries which contain printable strings for class codes
45 // in PCI configuration space
46 //
47 PCI_CLASS_ENTRY PCIBlankEntry[];
48 PCI_CLASS_ENTRY PCISubClass_00[];
49 PCI_CLASS_ENTRY PCISubClass_01[];
50 PCI_CLASS_ENTRY PCISubClass_02[];
51 PCI_CLASS_ENTRY PCISubClass_03[];
52 PCI_CLASS_ENTRY PCISubClass_04[];
53 PCI_CLASS_ENTRY PCISubClass_05[];
54 PCI_CLASS_ENTRY PCISubClass_06[];
55 PCI_CLASS_ENTRY PCISubClass_07[];
56 PCI_CLASS_ENTRY PCISubClass_08[];
57 PCI_CLASS_ENTRY PCISubClass_09[];
58 PCI_CLASS_ENTRY PCISubClass_0a[];
59 PCI_CLASS_ENTRY PCISubClass_0b[];
60 PCI_CLASS_ENTRY PCISubClass_0c[];
61 PCI_CLASS_ENTRY PCISubClass_0d[];
62 PCI_CLASS_ENTRY PCISubClass_0e[];
63 PCI_CLASS_ENTRY PCISubClass_0f[];
64 PCI_CLASS_ENTRY PCISubClass_10[];
65 PCI_CLASS_ENTRY PCISubClass_11[];
66 PCI_CLASS_ENTRY PCIPIFClass_0101[];
67 PCI_CLASS_ENTRY PCIPIFClass_0300[];
68 PCI_CLASS_ENTRY PCIPIFClass_0604[];
69 PCI_CLASS_ENTRY PCIPIFClass_0700[];
70 PCI_CLASS_ENTRY PCIPIFClass_0701[];
71 PCI_CLASS_ENTRY PCIPIFClass_0703[];
72 PCI_CLASS_ENTRY PCIPIFClass_0800[];
73 PCI_CLASS_ENTRY PCIPIFClass_0801[];
74 PCI_CLASS_ENTRY PCIPIFClass_0802[];
75 PCI_CLASS_ENTRY PCIPIFClass_0803[];
76 PCI_CLASS_ENTRY PCIPIFClass_0904[];
77 PCI_CLASS_ENTRY PCIPIFClass_0c00[];
78 PCI_CLASS_ENTRY PCIPIFClass_0c03[];
79 PCI_CLASS_ENTRY PCIPIFClass_0e00[];
80
81 //
82 // Base class strings entries
83 //
84 PCI_CLASS_ENTRY gClassStringList[] = {
85 {
86 0x00,
87 L"Pre 2.0 device",
88 PCISubClass_00
89 },
90 {
91 0x01,
92 L"Mass Storage Controller",
93 PCISubClass_01
94 },
95 {
96 0x02,
97 L"Network Controller",
98 PCISubClass_02
99 },
100 {
101 0x03,
102 L"Display Controller",
103 PCISubClass_03
104 },
105 {
106 0x04,
107 L"Multimedia Device",
108 PCISubClass_04
109 },
110 {
111 0x05,
112 L"Memory Controller",
113 PCISubClass_05
114 },
115 {
116 0x06,
117 L"Bridge Device",
118 PCISubClass_06
119 },
120 {
121 0x07,
122 L"Simple Communications Controllers",
123 PCISubClass_07
124 },
125 {
126 0x08,
127 L"Base System Peripherals",
128 PCISubClass_08
129 },
130 {
131 0x09,
132 L"Input Devices",
133 PCISubClass_09
134 },
135 {
136 0x0a,
137 L"Docking Stations",
138 PCISubClass_0a
139 },
140 {
141 0x0b,
142 L"Processors",
143 PCISubClass_0b
144 },
145 {
146 0x0c,
147 L"Serial Bus Controllers",
148 PCISubClass_0c
149 },
150 {
151 0x0d,
152 L"Wireless Controllers",
153 PCISubClass_0d
154 },
155 {
156 0x0e,
157 L"Intelligent IO Controllers",
158 PCISubClass_0e
159 },
160 {
161 0x0f,
162 L"Satellite Communications Controllers",
163 PCISubClass_0f
164 },
165 {
166 0x10,
167 L"Encryption/Decryption Controllers",
168 PCISubClass_10
169 },
170 {
171 0x11,
172 L"Data Acquisition & Signal Processing Controllers",
173 PCISubClass_11
174 },
175 {
176 0xff,
177 L"Device does not fit in any defined classes",
178 PCIBlankEntry
179 },
180 {
181 0x00,
182 NULL,
183 /* null string ends the list */NULL
184 }
185 };
186
187 //
188 // Subclass strings entries
189 //
190 PCI_CLASS_ENTRY PCIBlankEntry[] = {
191 {
192 0x00,
193 L"",
194 PCIBlankEntry
195 },
196 {
197 0x00,
198 NULL,
199 /* null string ends the list */NULL
200 }
201 };
202
203 PCI_CLASS_ENTRY PCISubClass_00[] = {
204 {
205 0x00,
206 L"All devices other than VGA",
207 PCIBlankEntry
208 },
209 {
210 0x01,
211 L"VGA-compatible devices",
212 PCIBlankEntry
213 },
214 {
215 0x00,
216 NULL,
217 /* null string ends the list */NULL
218 }
219 };
220
221 PCI_CLASS_ENTRY PCISubClass_01[] = {
222 {
223 0x00,
224 L"SCSI controller",
225 PCIBlankEntry
226 },
227 {
228 0x01,
229 L"IDE controller",
230 PCIPIFClass_0101
231 },
232 {
233 0x02,
234 L"Floppy disk controller",
235 PCIBlankEntry
236 },
237 {
238 0x03,
239 L"IPI controller",
240 PCIBlankEntry
241 },
242 {
243 0x04,
244 L"RAID controller",
245 PCIBlankEntry
246 },
247 {
248 0x80,
249 L"Other mass storage controller",
250 PCIBlankEntry
251 },
252 {
253 0x00,
254 NULL,
255 /* null string ends the list */NULL
256 }
257 };
258
259 PCI_CLASS_ENTRY PCISubClass_02[] = {
260 {
261 0x00,
262 L"Ethernet controller",
263 PCIBlankEntry
264 },
265 {
266 0x01,
267 L"Token ring controller",
268 PCIBlankEntry
269 },
270 {
271 0x02,
272 L"FDDI controller",
273 PCIBlankEntry
274 },
275 {
276 0x03,
277 L"ATM controller",
278 PCIBlankEntry
279 },
280 {
281 0x04,
282 L"ISDN controller",
283 PCIBlankEntry
284 },
285 {
286 0x80,
287 L"Other network controller",
288 PCIBlankEntry
289 },
290 {
291 0x00,
292 NULL,
293 /* null string ends the list */NULL
294 }
295 };
296
297 PCI_CLASS_ENTRY PCISubClass_03[] = {
298 {
299 0x00,
300 L"VGA/8514 controller",
301 PCIPIFClass_0300
302 },
303 {
304 0x01,
305 L"XGA controller",
306 PCIBlankEntry
307 },
308 {
309 0x02,
310 L"3D controller",
311 PCIBlankEntry
312 },
313 {
314 0x80,
315 L"Other display controller",
316 PCIBlankEntry
317 },
318 {
319 0x00,
320 NULL,
321 /* null string ends the list */PCIBlankEntry
322 }
323 };
324
325 PCI_CLASS_ENTRY PCISubClass_04[] = {
326 {
327 0x00,
328 L"Video device",
329 PCIBlankEntry
330 },
331 {
332 0x01,
333 L"Audio device",
334 PCIBlankEntry
335 },
336 {
337 0x02,
338 L"Computer Telephony device",
339 PCIBlankEntry
340 },
341 {
342 0x80,
343 L"Other multimedia device",
344 PCIBlankEntry
345 },
346 {
347 0x00,
348 NULL,
349 /* null string ends the list */NULL
350 }
351 };
352
353 PCI_CLASS_ENTRY PCISubClass_05[] = {
354 {
355 0x00,
356 L"RAM memory controller",
357 PCIBlankEntry
358 },
359 {
360 0x01,
361 L"Flash memory controller",
362 PCIBlankEntry
363 },
364 {
365 0x80,
366 L"Other memory controller",
367 PCIBlankEntry
368 },
369 {
370 0x00,
371 NULL,
372 /* null string ends the list */NULL
373 }
374 };
375
376 PCI_CLASS_ENTRY PCISubClass_06[] = {
377 {
378 0x00,
379 L"Host/PCI bridge",
380 PCIBlankEntry
381 },
382 {
383 0x01,
384 L"PCI/ISA bridge",
385 PCIBlankEntry
386 },
387 {
388 0x02,
389 L"PCI/EISA bridge",
390 PCIBlankEntry
391 },
392 {
393 0x03,
394 L"PCI/Micro Channel bridge",
395 PCIBlankEntry
396 },
397 {
398 0x04,
399 L"PCI/PCI bridge",
400 PCIPIFClass_0604
401 },
402 {
403 0x05,
404 L"PCI/PCMCIA bridge",
405 PCIBlankEntry
406 },
407 {
408 0x06,
409 L"NuBus bridge",
410 PCIBlankEntry
411 },
412 {
413 0x07,
414 L"CardBus bridge",
415 PCIBlankEntry
416 },
417 {
418 0x08,
419 L"RACEway bridge",
420 PCIBlankEntry
421 },
422 {
423 0x80,
424 L"Other bridge type",
425 PCIBlankEntry
426 },
427 {
428 0x00,
429 NULL,
430 /* null string ends the list */NULL
431 }
432 };
433
434 PCI_CLASS_ENTRY PCISubClass_07[] = {
435 {
436 0x00,
437 L"Serial controller",
438 PCIPIFClass_0700
439 },
440 {
441 0x01,
442 L"Parallel port",
443 PCIPIFClass_0701
444 },
445 {
446 0x02,
447 L"Multiport serial controller",
448 PCIBlankEntry
449 },
450 {
451 0x03,
452 L"Modem",
453 PCIPIFClass_0703
454 },
455 {
456 0x80,
457 L"Other communication device",
458 PCIBlankEntry
459 },
460 {
461 0x00,
462 NULL,
463 /* null string ends the list */NULL
464 }
465 };
466
467 PCI_CLASS_ENTRY PCISubClass_08[] = {
468 {
469 0x00,
470 L"PIC",
471 PCIPIFClass_0800
472 },
473 {
474 0x01,
475 L"DMA controller",
476 PCIPIFClass_0801
477 },
478 {
479 0x02,
480 L"System timer",
481 PCIPIFClass_0802
482 },
483 {
484 0x03,
485 L"RTC controller",
486 PCIPIFClass_0803
487 },
488 {
489 0x04,
490 L"Generic PCI Hot-Plug controller",
491 PCIBlankEntry
492 },
493 {
494 0x80,
495 L"Other system peripheral",
496 PCIBlankEntry
497 },
498 {
499 0x00,
500 NULL,
501 /* null string ends the list */NULL
502 }
503 };
504
505 PCI_CLASS_ENTRY PCISubClass_09[] = {
506 {
507 0x00,
508 L"Keyboard controller",
509 PCIBlankEntry
510 },
511 {
512 0x01,
513 L"Digitizer (pen)",
514 PCIBlankEntry
515 },
516 {
517 0x02,
518 L"Mouse controller",
519 PCIBlankEntry
520 },
521 {
522 0x03,
523 L"Scanner controller",
524 PCIBlankEntry
525 },
526 {
527 0x04,
528 L"Gameport controller",
529 PCIPIFClass_0904
530 },
531 {
532 0x80,
533 L"Other input controller",
534 PCIBlankEntry
535 },
536 {
537 0x00,
538 NULL,
539 /* null string ends the list */NULL
540 }
541 };
542
543 PCI_CLASS_ENTRY PCISubClass_0a[] = {
544 {
545 0x00,
546 L"Generic docking station",
547 PCIBlankEntry
548 },
549 {
550 0x80,
551 L"Other type of docking station",
552 PCIBlankEntry
553 },
554 {
555 0x00,
556 NULL,
557 /* null string ends the list */NULL
558 }
559 };
560
561 PCI_CLASS_ENTRY PCISubClass_0b[] = {
562 {
563 0x00,
564 L"386",
565 PCIBlankEntry
566 },
567 {
568 0x01,
569 L"486",
570 PCIBlankEntry
571 },
572 {
573 0x02,
574 L"Pentium",
575 PCIBlankEntry
576 },
577 {
578 0x10,
579 L"Alpha",
580 PCIBlankEntry
581 },
582 {
583 0x20,
584 L"PowerPC",
585 PCIBlankEntry
586 },
587 {
588 0x30,
589 L"MIPS",
590 PCIBlankEntry
591 },
592 {
593 0x40,
594 L"Co-processor",
595 PCIBlankEntry
596 },
597 {
598 0x80,
599 L"Other processor",
600 PCIBlankEntry
601 },
602 {
603 0x00,
604 NULL,
605 /* null string ends the list */NULL
606 }
607 };
608
609 PCI_CLASS_ENTRY PCISubClass_0c[] = {
610 {
611 0x00,
612 L"Firewire(IEEE 1394)",
613 PCIPIFClass_0c03
614 },
615 {
616 0x01,
617 L"ACCESS.bus",
618 PCIBlankEntry
619 },
620 {
621 0x02,
622 L"SSA",
623 PCIBlankEntry
624 },
625 {
626 0x03,
627 L"USB",
628 PCIPIFClass_0c00
629 },
630 {
631 0x04,
632 L"Fibre Channel",
633 PCIBlankEntry
634 },
635 {
636 0x05,
637 L"System Management Bus",
638 PCIBlankEntry
639 },
640 {
641 0x80,
642 L"Other bus type",
643 PCIBlankEntry
644 },
645 {
646 0x00,
647 NULL,
648 /* null string ends the list */NULL
649 }
650 };
651
652 PCI_CLASS_ENTRY PCISubClass_0d[] = {
653 {
654 0x00,
655 L"iRDA compatible controller",
656 PCIBlankEntry
657 },
658 {
659 0x01,
660 L"Consumer IR controller",
661 PCIBlankEntry
662 },
663 {
664 0x10,
665 L"RF controller",
666 PCIBlankEntry
667 },
668 {
669 0x80,
670 L"Other type of wireless controller",
671 PCIBlankEntry
672 },
673 {
674 0x00,
675 NULL,
676 /* null string ends the list */NULL
677 }
678 };
679
680 PCI_CLASS_ENTRY PCISubClass_0e[] = {
681 {
682 0x00,
683 L"I2O Architecture",
684 PCIPIFClass_0e00
685 },
686 {
687 0x00,
688 NULL,
689 /* null string ends the list */NULL
690 }
691 };
692
693 PCI_CLASS_ENTRY PCISubClass_0f[] = {
694 {
695 0x00,
696 L"TV",
697 PCIBlankEntry
698 },
699 {
700 0x01,
701 L"Audio",
702 PCIBlankEntry
703 },
704 {
705 0x02,
706 L"Voice",
707 PCIBlankEntry
708 },
709 {
710 0x03,
711 L"Data",
712 PCIBlankEntry
713 },
714 {
715 0x00,
716 NULL,
717 /* null string ends the list */NULL
718 }
719 };
720
721 PCI_CLASS_ENTRY PCISubClass_10[] = {
722 {
723 0x00,
724 L"Network & computing Encrypt/Decrypt",
725 PCIBlankEntry
726 },
727 {
728 0x01,
729 L"Entertainment Encrypt/Decrypt",
730 PCIBlankEntry
731 },
732 {
733 0x80,
734 L"Other Encrypt/Decrypt",
735 PCIBlankEntry
736 },
737 {
738 0x00,
739 NULL,
740 /* null string ends the list */NULL
741 }
742 };
743
744 PCI_CLASS_ENTRY PCISubClass_11[] = {
745 {
746 0x00,
747 L"DPIO modules",
748 PCIBlankEntry
749 },
750 {
751 0x80,
752 L"Other DAQ & SP controllers",
753 PCIBlankEntry
754 },
755 {
756 0x00,
757 NULL,
758 /* null string ends the list */NULL
759 }
760 };
761
762 //
763 // Programming Interface entries
764 //
765 PCI_CLASS_ENTRY PCIPIFClass_0101[] = {
766 {
767 0x00,
768 L"",
769 PCIBlankEntry
770 },
771 {
772 0x01,
773 L"OM-primary",
774 PCIBlankEntry
775 },
776 {
777 0x02,
778 L"PI-primary",
779 PCIBlankEntry
780 },
781 {
782 0x03,
783 L"OM/PI-primary",
784 PCIBlankEntry
785 },
786 {
787 0x04,
788 L"OM-secondary",
789 PCIBlankEntry
790 },
791 {
792 0x05,
793 L"OM-primary, OM-secondary",
794 PCIBlankEntry
795 },
796 {
797 0x06,
798 L"PI-primary, OM-secondary",
799 PCIBlankEntry
800 },
801 {
802 0x07,
803 L"OM/PI-primary, OM-secondary",
804 PCIBlankEntry
805 },
806 {
807 0x08,
808 L"OM-secondary",
809 PCIBlankEntry
810 },
811 {
812 0x09,
813 L"OM-primary, PI-secondary",
814 PCIBlankEntry
815 },
816 {
817 0x0a,
818 L"PI-primary, PI-secondary",
819 PCIBlankEntry
820 },
821 {
822 0x0b,
823 L"OM/PI-primary, PI-secondary",
824 PCIBlankEntry
825 },
826 {
827 0x0c,
828 L"OM-secondary",
829 PCIBlankEntry
830 },
831 {
832 0x0d,
833 L"OM-primary, OM/PI-secondary",
834 PCIBlankEntry
835 },
836 {
837 0x0e,
838 L"PI-primary, OM/PI-secondary",
839 PCIBlankEntry
840 },
841 {
842 0x0f,
843 L"OM/PI-primary, OM/PI-secondary",
844 PCIBlankEntry
845 },
846 {
847 0x80,
848 L"Master",
849 PCIBlankEntry
850 },
851 {
852 0x81,
853 L"Master, OM-primary",
854 PCIBlankEntry
855 },
856 {
857 0x82,
858 L"Master, PI-primary",
859 PCIBlankEntry
860 },
861 {
862 0x83,
863 L"Master, OM/PI-primary",
864 PCIBlankEntry
865 },
866 {
867 0x84,
868 L"Master, OM-secondary",
869 PCIBlankEntry
870 },
871 {
872 0x85,
873 L"Master, OM-primary, OM-secondary",
874 PCIBlankEntry
875 },
876 {
877 0x86,
878 L"Master, PI-primary, OM-secondary",
879 PCIBlankEntry
880 },
881 {
882 0x87,
883 L"Master, OM/PI-primary, OM-secondary",
884 PCIBlankEntry
885 },
886 {
887 0x88,
888 L"Master, OM-secondary",
889 PCIBlankEntry
890 },
891 {
892 0x89,
893 L"Master, OM-primary, PI-secondary",
894 PCIBlankEntry
895 },
896 {
897 0x8a,
898 L"Master, PI-primary, PI-secondary",
899 PCIBlankEntry
900 },
901 {
902 0x8b,
903 L"Master, OM/PI-primary, PI-secondary",
904 PCIBlankEntry
905 },
906 {
907 0x8c,
908 L"Master, OM-secondary",
909 PCIBlankEntry
910 },
911 {
912 0x8d,
913 L"Master, OM-primary, OM/PI-secondary",
914 PCIBlankEntry
915 },
916 {
917 0x8e,
918 L"Master, PI-primary, OM/PI-secondary",
919 PCIBlankEntry
920 },
921 {
922 0x8f,
923 L"Master, OM/PI-primary, OM/PI-secondary",
924 PCIBlankEntry
925 },
926 {
927 0x00,
928 NULL,
929 /* null string ends the list */NULL
930 }
931 };
932
933 PCI_CLASS_ENTRY PCIPIFClass_0300[] = {
934 {
935 0x00,
936 L"VGA compatible",
937 PCIBlankEntry
938 },
939 {
940 0x01,
941 L"8514 compatible",
942 PCIBlankEntry
943 },
944 {
945 0x00,
946 NULL,
947 /* null string ends the list */NULL
948 }
949 };
950
951 PCI_CLASS_ENTRY PCIPIFClass_0604[] = {
952 {
953 0x00,
954 L"",
955 PCIBlankEntry
956 },
957 {
958 0x01,
959 L"Subtractive decode",
960 PCIBlankEntry
961 },
962 {
963 0x00,
964 NULL,
965 /* null string ends the list */NULL
966 }
967 };
968
969 PCI_CLASS_ENTRY PCIPIFClass_0700[] = {
970 {
971 0x00,
972 L"Generic XT-compatible",
973 PCIBlankEntry
974 },
975 {
976 0x01,
977 L"16450-compatible",
978 PCIBlankEntry
979 },
980 {
981 0x02,
982 L"16550-compatible",
983 PCIBlankEntry
984 },
985 {
986 0x03,
987 L"16650-compatible",
988 PCIBlankEntry
989 },
990 {
991 0x04,
992 L"16750-compatible",
993 PCIBlankEntry
994 },
995 {
996 0x05,
997 L"16850-compatible",
998 PCIBlankEntry
999 },
1000 {
1001 0x06,
1002 L"16950-compatible",
1003 PCIBlankEntry
1004 },
1005 {
1006 0x00,
1007 NULL,
1008 /* null string ends the list */NULL
1009 }
1010 };
1011
1012 PCI_CLASS_ENTRY PCIPIFClass_0701[] = {
1013 {
1014 0x00,
1015 L"",
1016 PCIBlankEntry
1017 },
1018 {
1019 0x01,
1020 L"Bi-directional",
1021 PCIBlankEntry
1022 },
1023 {
1024 0x02,
1025 L"ECP 1.X-compliant",
1026 PCIBlankEntry
1027 },
1028 {
1029 0x03,
1030 L"IEEE 1284",
1031 PCIBlankEntry
1032 },
1033 {
1034 0xfe,
1035 L"IEEE 1284 target (not a controller)",
1036 PCIBlankEntry
1037 },
1038 {
1039 0x00,
1040 NULL,
1041 /* null string ends the list */NULL
1042 }
1043 };
1044
1045 PCI_CLASS_ENTRY PCIPIFClass_0703[] = {
1046 {
1047 0x00,
1048 L"Generic",
1049 PCIBlankEntry
1050 },
1051 {
1052 0x01,
1053 L"Hayes-compatible 16450",
1054 PCIBlankEntry
1055 },
1056 {
1057 0x02,
1058 L"Hayes-compatible 16550",
1059 PCIBlankEntry
1060 },
1061 {
1062 0x03,
1063 L"Hayes-compatible 16650",
1064 PCIBlankEntry
1065 },
1066 {
1067 0x04,
1068 L"Hayes-compatible 16750",
1069 PCIBlankEntry
1070 },
1071 {
1072 0x00,
1073 NULL,
1074 /* null string ends the list */NULL
1075 }
1076 };
1077
1078 PCI_CLASS_ENTRY PCIPIFClass_0800[] = {
1079 {
1080 0x00,
1081 L"Generic 8259",
1082 PCIBlankEntry
1083 },
1084 {
1085 0x01,
1086 L"ISA",
1087 PCIBlankEntry
1088 },
1089 {
1090 0x02,
1091 L"EISA",
1092 PCIBlankEntry
1093 },
1094 {
1095 0x10,
1096 L"IO APIC",
1097 PCIBlankEntry
1098 },
1099 {
1100 0x20,
1101 L"IO(x) APIC interrupt controller",
1102 PCIBlankEntry
1103 },
1104 {
1105 0x00,
1106 NULL,
1107 /* null string ends the list */NULL
1108 }
1109 };
1110
1111 PCI_CLASS_ENTRY PCIPIFClass_0801[] = {
1112 {
1113 0x00,
1114 L"Generic 8237",
1115 PCIBlankEntry
1116 },
1117 {
1118 0x01,
1119 L"ISA",
1120 PCIBlankEntry
1121 },
1122 {
1123 0x02,
1124 L"EISA",
1125 PCIBlankEntry
1126 },
1127 {
1128 0x00,
1129 NULL,
1130 /* null string ends the list */NULL
1131 }
1132 };
1133
1134 PCI_CLASS_ENTRY PCIPIFClass_0802[] = {
1135 {
1136 0x00,
1137 L"Generic 8254",
1138 PCIBlankEntry
1139 },
1140 {
1141 0x01,
1142 L"ISA",
1143 PCIBlankEntry
1144 },
1145 {
1146 0x02,
1147 L"EISA",
1148 PCIBlankEntry
1149 },
1150 {
1151 0x00,
1152 NULL,
1153 /* null string ends the list */NULL
1154 }
1155 };
1156
1157 PCI_CLASS_ENTRY PCIPIFClass_0803[] = {
1158 {
1159 0x00,
1160 L"Generic",
1161 PCIBlankEntry
1162 },
1163 {
1164 0x01,
1165 L"ISA",
1166 PCIBlankEntry
1167 },
1168 {
1169 0x02,
1170 L"EISA",
1171 PCIBlankEntry
1172 },
1173 {
1174 0x00,
1175 NULL,
1176 /* null string ends the list */NULL
1177 }
1178 };
1179
1180 PCI_CLASS_ENTRY PCIPIFClass_0904[] = {
1181 {
1182 0x00,
1183 L"Generic",
1184 PCIBlankEntry
1185 },
1186 {
1187 0x10,
1188 L"",
1189 PCIBlankEntry
1190 },
1191 {
1192 0x00,
1193 NULL,
1194 /* null string ends the list */NULL
1195 }
1196 };
1197
1198 PCI_CLASS_ENTRY PCIPIFClass_0c00[] = {
1199 {
1200 0x00,
1201 L"Universal Host Controller spec",
1202 PCIBlankEntry
1203 },
1204 {
1205 0x10,
1206 L"Open Host Controller spec",
1207 PCIBlankEntry
1208 },
1209 {
1210 0x80,
1211 L"No specific programming interface",
1212 PCIBlankEntry
1213 },
1214 {
1215 0xfe,
1216 L"(Not Host Controller)",
1217 PCIBlankEntry
1218 },
1219 {
1220 0x00,
1221 NULL,
1222 /* null string ends the list */NULL
1223 }
1224 };
1225
1226 PCI_CLASS_ENTRY PCIPIFClass_0c03[] = {
1227 {
1228 0x00,
1229 L"",
1230 PCIBlankEntry
1231 },
1232 {
1233 0x10,
1234 L"Using 1394 OpenHCI spec",
1235 PCIBlankEntry
1236 },
1237 {
1238 0x00,
1239 NULL,
1240 /* null string ends the list */NULL
1241 }
1242 };
1243
1244 PCI_CLASS_ENTRY PCIPIFClass_0e00[] = {
1245 {
1246 0x00,
1247 L"Message FIFO at offset 40h",
1248 PCIBlankEntry
1249 },
1250 {
1251 0x01,
1252 L"",
1253 PCIBlankEntry
1254 },
1255 {
1256 0x00,
1257 NULL,
1258 /* null string ends the list */NULL
1259 }
1260 };
1261
1262
1263 /**
1264 Generates printable Unicode strings that represent PCI device class,
1265 subclass and programmed I/F based on a value passed to the function.
1266
1267 @param[in] ClassCode Value representing the PCI "Class Code" register read from a
1268 PCI device. The encodings are:
1269 bits 23:16 - Base Class Code
1270 bits 15:8 - Sub-Class Code
1271 bits 7:0 - Programming Interface
1272 @param[in, out] ClassStrings Pointer of PCI_CLASS_STRINGS structure, which contains
1273 printable class strings corresponding to ClassCode. The
1274 caller must not modify the strings that are pointed by
1275 the fields in ClassStrings.
1276 **/
1277 VOID
1278 PciGetClassStrings (
1279 IN UINT32 ClassCode,
1280 IN OUT PCI_CLASS_STRINGS *ClassStrings
1281 )
1282 {
1283 INTN Index;
1284 UINT8 Code;
1285 PCI_CLASS_ENTRY *CurrentClass;
1286
1287 //
1288 // Assume no strings found
1289 //
1290 ClassStrings->BaseClass = L"UNDEFINED";
1291 ClassStrings->SubClass = L"UNDEFINED";
1292 ClassStrings->PIFClass = L"UNDEFINED";
1293
1294 CurrentClass = gClassStringList;
1295 Code = (UINT8) (ClassCode >> 16);
1296 Index = 0;
1297
1298 //
1299 // Go through all entries of the base class, until the entry with a matching
1300 // base class code is found. If reaches an entry with a null description
1301 // text, the last entry is met, which means no text for the base class was
1302 // found, so no more action is needed.
1303 //
1304 while (Code != CurrentClass[Index].Code) {
1305 if (NULL == CurrentClass[Index].DescText) {
1306 return ;
1307 }
1308
1309 Index++;
1310 }
1311 //
1312 // A base class was found. Assign description, and check if this class has
1313 // sub-class defined. If sub-class defined, no more action is needed,
1314 // otherwise, continue to find description for the sub-class code.
1315 //
1316 ClassStrings->BaseClass = CurrentClass[Index].DescText;
1317 if (NULL == CurrentClass[Index].LowerLevelClass) {
1318 return ;
1319 }
1320 //
1321 // find Subclass entry
1322 //
1323 CurrentClass = CurrentClass[Index].LowerLevelClass;
1324 Code = (UINT8) (ClassCode >> 8);
1325 Index = 0;
1326
1327 //
1328 // Go through all entries of the sub-class, until the entry with a matching
1329 // sub-class code is found. If reaches an entry with a null description
1330 // text, the last entry is met, which means no text for the sub-class was
1331 // found, so no more action is needed.
1332 //
1333 while (Code != CurrentClass[Index].Code) {
1334 if (NULL == CurrentClass[Index].DescText) {
1335 return ;
1336 }
1337
1338 Index++;
1339 }
1340 //
1341 // A class was found for the sub-class code. Assign description, and check if
1342 // this sub-class has programming interface defined. If no, no more action is
1343 // needed, otherwise, continue to find description for the programming
1344 // interface.
1345 //
1346 ClassStrings->SubClass = CurrentClass[Index].DescText;
1347 if (NULL == CurrentClass[Index].LowerLevelClass) {
1348 return ;
1349 }
1350 //
1351 // Find programming interface entry
1352 //
1353 CurrentClass = CurrentClass[Index].LowerLevelClass;
1354 Code = (UINT8) ClassCode;
1355 Index = 0;
1356
1357 //
1358 // Go through all entries of the I/F entries, until the entry with a
1359 // matching I/F code is found. If reaches an entry with a null description
1360 // text, the last entry is met, which means no text was found, so no more
1361 // action is needed.
1362 //
1363 while (Code != CurrentClass[Index].Code) {
1364 if (NULL == CurrentClass[Index].DescText) {
1365 return ;
1366 }
1367
1368 Index++;
1369 }
1370 //
1371 // A class was found for the I/F code. Assign description, done!
1372 //
1373 ClassStrings->PIFClass = CurrentClass[Index].DescText;
1374 return ;
1375 }
1376
1377 /**
1378 Print strings that represent PCI device class, subclass and programmed I/F.
1379
1380 @param[in] ClassCodePtr Points to the memory which stores register Class Code in PCI
1381 configuation space.
1382 @param[in] IncludePIF If the printed string should include the programming I/F part
1383 **/
1384 VOID
1385 PciPrintClassCode (
1386 IN UINT8 *ClassCodePtr,
1387 IN BOOLEAN IncludePIF
1388 )
1389 {
1390 UINT32 ClassCode;
1391 PCI_CLASS_STRINGS ClassStrings;
1392
1393 ClassCode = 0;
1394 ClassCode |= ClassCodePtr[0];
1395 ClassCode |= (ClassCodePtr[1] << 8);
1396 ClassCode |= (ClassCodePtr[2] << 16);
1397
1398 //
1399 // Get name from class code
1400 //
1401 PciGetClassStrings (ClassCode, &ClassStrings);
1402
1403 if (IncludePIF) {
1404 //
1405 // Print base class, sub class, and programming inferface name
1406 //
1407 ShellPrintEx (-1, -1, L"%s - %s - %s",
1408 ClassStrings.BaseClass,
1409 ClassStrings.SubClass,
1410 ClassStrings.PIFClass
1411 );
1412
1413 } else {
1414 //
1415 // Only print base class and sub class name
1416 //
1417 ShellPrintEx (-1, -1, L"%s - %s",
1418 ClassStrings.BaseClass,
1419 ClassStrings.SubClass
1420 );
1421 }
1422 }
1423
1424 /**
1425 This function finds out the protocol which is in charge of the given
1426 segment, and its bus range covers the current bus number. It lookes
1427 each instances of RootBridgeIoProtocol handle, until the one meets the
1428 criteria is found.
1429
1430 @param[in] HandleBuf Buffer which holds all PCI_ROOT_BRIDIGE_IO_PROTOCOL handles.
1431 @param[in] HandleCount Count of all PCI_ROOT_BRIDIGE_IO_PROTOCOL handles.
1432 @param[in] Segment Segment number of device we are dealing with.
1433 @param[in] Bus Bus number of device we are dealing with.
1434 @param[out] IoDev Handle used to access configuration space of PCI device.
1435
1436 @retval EFI_SUCCESS The command completed successfully.
1437 @retval EFI_INVALID_PARAMETER Invalid parameter.
1438
1439 **/
1440 EFI_STATUS
1441 PciFindProtocolInterface (
1442 IN EFI_HANDLE *HandleBuf,
1443 IN UINTN HandleCount,
1444 IN UINT16 Segment,
1445 IN UINT16 Bus,
1446 OUT EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **IoDev
1447 );
1448
1449 /**
1450 This function gets the protocol interface from the given handle, and
1451 obtains its address space descriptors.
1452
1453 @param[in] Handle The PCI_ROOT_BRIDIGE_IO_PROTOCOL handle.
1454 @param[out] IoDev Handle used to access configuration space of PCI device.
1455 @param[out] Descriptors Points to the address space descriptors.
1456
1457 @retval EFI_SUCCESS The command completed successfully
1458 **/
1459 EFI_STATUS
1460 PciGetProtocolAndResource (
1461 IN EFI_HANDLE Handle,
1462 OUT EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **IoDev,
1463 OUT EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR **Descriptors
1464 );
1465
1466 /**
1467 This function get the next bus range of given address space descriptors.
1468 It also moves the pointer backward a node, to get prepared to be called
1469 again.
1470
1471 @param[in, out] Descriptors Points to current position of a serial of address space
1472 descriptors.
1473 @param[out] MinBus The lower range of bus number.
1474 @param[out] MaxBus The upper range of bus number.
1475 @param[out] IsEnd Meet end of the serial of descriptors.
1476
1477 @retval EFI_SUCCESS The command completed successfully.
1478 **/
1479 EFI_STATUS
1480 PciGetNextBusRange (
1481 IN OUT EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR **Descriptors,
1482 OUT UINT16 *MinBus,
1483 OUT UINT16 *MaxBus,
1484 OUT BOOLEAN *IsEnd
1485 );
1486
1487 /**
1488 Explain the data in PCI configuration space. The part which is common for
1489 PCI device and bridge is interpreted in this function. It calls other
1490 functions to interpret data unique for device or bridge.
1491
1492 @param[in] ConfigSpace Data in PCI configuration space.
1493 @param[in] Address Address used to access configuration space of this PCI device.
1494 @param[in] IoDev Handle used to access configuration space of PCI device.
1495 @param[in] EnhancedDump The print format for the dump data.
1496
1497 @retval EFI_SUCCESS The command completed successfully.
1498 **/
1499 EFI_STATUS
1500 PciExplainData (
1501 IN PCI_CONFIG_SPACE *ConfigSpace,
1502 IN UINT64 Address,
1503 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
1504 IN CONST UINT16 EnhancedDump
1505 );
1506
1507 /**
1508 Explain the device specific part of data in PCI configuration space.
1509
1510 @param[in] Device Data in PCI configuration space.
1511 @param[in] Address Address used to access configuration space of this PCI device.
1512 @param[in] IoDev Handle used to access configuration space of PCI device.
1513
1514 @retval EFI_SUCCESS The command completed successfully.
1515 **/
1516 EFI_STATUS
1517 PciExplainDeviceData (
1518 IN PCI_DEVICE_HEADER *Device,
1519 IN UINT64 Address,
1520 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev
1521 );
1522
1523 /**
1524 Explain the bridge specific part of data in PCI configuration space.
1525
1526 @param[in] Bridge Bridge specific data region in PCI configuration space.
1527 @param[in] Address Address used to access configuration space of this PCI device.
1528 @param[in] IoDev Handle used to access configuration space of PCI device.
1529
1530 @retval EFI_SUCCESS The command completed successfully.
1531 **/
1532 EFI_STATUS
1533 PciExplainBridgeData (
1534 IN PCI_BRIDGE_HEADER *Bridge,
1535 IN UINT64 Address,
1536 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev
1537 );
1538
1539 /**
1540 Explain the Base Address Register(Bar) in PCI configuration space.
1541
1542 @param[in] Bar Points to the Base Address Register intended to interpret.
1543 @param[in] Command Points to the register Command.
1544 @param[in] Address Address used to access configuration space of this PCI device.
1545 @param[in] IoDev Handle used to access configuration space of PCI device.
1546 @param[in, out] Index The Index.
1547
1548 @retval EFI_SUCCESS The command completed successfully.
1549 **/
1550 EFI_STATUS
1551 PciExplainBar (
1552 IN UINT32 *Bar,
1553 IN UINT16 *Command,
1554 IN UINT64 Address,
1555 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
1556 IN OUT UINTN *Index
1557 );
1558
1559 /**
1560 Explain the cardbus specific part of data in PCI configuration space.
1561
1562 @param[in] CardBus CardBus specific region of PCI configuration space.
1563 @param[in] Address Address used to access configuration space of this PCI device.
1564 @param[in] IoDev Handle used to access configuration space of PCI device.
1565
1566 @retval EFI_SUCCESS The command completed successfully.
1567 **/
1568 EFI_STATUS
1569 PciExplainCardBusData (
1570 IN PCI_CARDBUS_HEADER *CardBus,
1571 IN UINT64 Address,
1572 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev
1573 );
1574
1575 /**
1576 Explain each meaningful bit of register Status. The definition of Status is
1577 slightly different depending on the PCI header type.
1578
1579 @param[in] Status Points to the content of register Status.
1580 @param[in] MainStatus Indicates if this register is main status(not secondary
1581 status).
1582 @param[in] HeaderType Header type of this PCI device.
1583
1584 @retval EFI_SUCCESS The command completed successfully.
1585 **/
1586 EFI_STATUS
1587 PciExplainStatus (
1588 IN UINT16 *Status,
1589 IN BOOLEAN MainStatus,
1590 IN PCI_HEADER_TYPE HeaderType
1591 );
1592
1593 /**
1594 Explain each meaningful bit of register Command.
1595
1596 @param[in] Command Points to the content of register Command.
1597
1598 @retval EFI_SUCCESS The command completed successfully.
1599 **/
1600 EFI_STATUS
1601 PciExplainCommand (
1602 IN UINT16 *Command
1603 );
1604
1605 /**
1606 Explain each meaningful bit of register Bridge Control.
1607
1608 @param[in] BridgeControl Points to the content of register Bridge Control.
1609 @param[in] HeaderType The headertype.
1610
1611 @retval EFI_SUCCESS The command completed successfully.
1612 **/
1613 EFI_STATUS
1614 PciExplainBridgeControl (
1615 IN UINT16 *BridgeControl,
1616 IN PCI_HEADER_TYPE HeaderType
1617 );
1618
1619 /**
1620 Print each capability structure.
1621
1622 @param[in] IoDev The pointer to the deivce.
1623 @param[in] Address The address to start at.
1624 @param[in] CapPtr The offset from the address.
1625 @param[in] EnhancedDump The print format for the dump data.
1626
1627 @retval EFI_SUCCESS The operation was successful.
1628 **/
1629 EFI_STATUS
1630 PciExplainCapabilityStruct (
1631 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
1632 IN UINT64 Address,
1633 IN UINT8 CapPtr,
1634 IN CONST UINT16 EnhancedDump
1635 );
1636
1637 /**
1638 Display Pcie device structure.
1639
1640 @param[in] IoDev The pointer to the root pci protocol.
1641 @param[in] Address The Address to start at.
1642 @param[in] CapabilityPtr The offset from the address to start.
1643 @param[in] EnhancedDump The print format for the dump data.
1644
1645 @retval EFI_SUCCESS The command completed successfully.
1646 @retval @retval EFI_SUCCESS Pci express extend space IO is not suppoted.
1647 **/
1648 EFI_STATUS
1649 PciExplainPciExpress (
1650 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
1651 IN UINT64 Address,
1652 IN UINT8 CapabilityPtr,
1653 IN CONST UINT16 EnhancedDump
1654 );
1655
1656 /**
1657 Print out information of the capability information.
1658
1659 @param[in] PciExpressCap The pointer to the structure about the device.
1660
1661 @retval EFI_SUCCESS The operation was successful.
1662 **/
1663 EFI_STATUS
1664 ExplainPcieCapReg (
1665 IN PCIE_CAP_STURCTURE *PciExpressCap
1666 );
1667
1668 /**
1669 Print out information of the device capability information.
1670
1671 @param[in] PciExpressCap The pointer to the structure about the device.
1672
1673 @retval EFI_SUCCESS The operation was successful.
1674 **/
1675 EFI_STATUS
1676 ExplainPcieDeviceCap (
1677 IN PCIE_CAP_STURCTURE *PciExpressCap
1678 );
1679
1680 /**
1681 Print out information of the device control information.
1682
1683 @param[in] PciExpressCap The pointer to the structure about the device.
1684
1685 @retval EFI_SUCCESS The operation was successful.
1686 **/
1687 EFI_STATUS
1688 ExplainPcieDeviceControl (
1689 IN PCIE_CAP_STURCTURE *PciExpressCap
1690 );
1691
1692 /**
1693 Print out information of the device status information.
1694
1695 @param[in] PciExpressCap The pointer to the structure about the device.
1696
1697 @retval EFI_SUCCESS The operation was successful.
1698 **/
1699 EFI_STATUS
1700 ExplainPcieDeviceStatus (
1701 IN PCIE_CAP_STURCTURE *PciExpressCap
1702 );
1703
1704 /**
1705 Print out information of the device link information.
1706
1707 @param[in] PciExpressCap The pointer to the structure about the device.
1708
1709 @retval EFI_SUCCESS The operation was successful.
1710 **/
1711 EFI_STATUS
1712 ExplainPcieLinkCap (
1713 IN PCIE_CAP_STURCTURE *PciExpressCap
1714 );
1715
1716 /**
1717 Print out information of the device link control information.
1718
1719 @param[in] PciExpressCap The pointer to the structure about the device.
1720
1721 @retval EFI_SUCCESS The operation was successful.
1722 **/
1723 EFI_STATUS
1724 ExplainPcieLinkControl (
1725 IN PCIE_CAP_STURCTURE *PciExpressCap
1726 );
1727
1728 /**
1729 Print out information of the device link status information.
1730
1731 @param[in] PciExpressCap The pointer to the structure about the device.
1732
1733 @retval EFI_SUCCESS The operation was successful.
1734 **/
1735 EFI_STATUS
1736 ExplainPcieLinkStatus (
1737 IN PCIE_CAP_STURCTURE *PciExpressCap
1738 );
1739
1740 /**
1741 Print out information of the device slot information.
1742
1743 @param[in] PciExpressCap The pointer to the structure about the device.
1744
1745 @retval EFI_SUCCESS The operation was successful.
1746 **/
1747 EFI_STATUS
1748 ExplainPcieSlotCap (
1749 IN PCIE_CAP_STURCTURE *PciExpressCap
1750 );
1751
1752 /**
1753 Print out information of the device slot control information.
1754
1755 @param[in] PciExpressCap The pointer to the structure about the device.
1756
1757 @retval EFI_SUCCESS The operation was successful.
1758 **/
1759 EFI_STATUS
1760 ExplainPcieSlotControl (
1761 IN PCIE_CAP_STURCTURE *PciExpressCap
1762 );
1763
1764 /**
1765 Print out information of the device slot status information.
1766
1767 @param[in] PciExpressCap The pointer to the structure about the device.
1768
1769 @retval EFI_SUCCESS The operation was successful.
1770 **/
1771 EFI_STATUS
1772 ExplainPcieSlotStatus (
1773 IN PCIE_CAP_STURCTURE *PciExpressCap
1774 );
1775
1776 /**
1777 Print out information of the device root information.
1778
1779 @param[in] PciExpressCap The pointer to the structure about the device.
1780
1781 @retval EFI_SUCCESS The operation was successful.
1782 **/
1783 EFI_STATUS
1784 ExplainPcieRootControl (
1785 IN PCIE_CAP_STURCTURE *PciExpressCap
1786 );
1787
1788 /**
1789 Print out information of the device root capability information.
1790
1791 @param[in] PciExpressCap The pointer to the structure about the device.
1792
1793 @retval EFI_SUCCESS The operation was successful.
1794 **/
1795 EFI_STATUS
1796 ExplainPcieRootCap (
1797 IN PCIE_CAP_STURCTURE *PciExpressCap
1798 );
1799
1800 /**
1801 Print out information of the device root status information.
1802
1803 @param[in] PciExpressCap The pointer to the structure about the device.
1804
1805 @retval EFI_SUCCESS The operation was successful.
1806 **/
1807 EFI_STATUS
1808 ExplainPcieRootStatus (
1809 IN PCIE_CAP_STURCTURE *PciExpressCap
1810 );
1811
1812 typedef EFI_STATUS (*PCIE_EXPLAIN_FUNCTION) (IN PCIE_CAP_STURCTURE *PciExpressCap);
1813
1814 typedef enum {
1815 FieldWidthUINT8,
1816 FieldWidthUINT16,
1817 FieldWidthUINT32
1818 } PCIE_CAPREG_FIELD_WIDTH;
1819
1820 typedef enum {
1821 PcieExplainTypeCommon,
1822 PcieExplainTypeDevice,
1823 PcieExplainTypeLink,
1824 PcieExplainTypeSlot,
1825 PcieExplainTypeRoot,
1826 PcieExplainTypeMax
1827 } PCIE_EXPLAIN_TYPE;
1828
1829 typedef struct
1830 {
1831 UINT16 Token;
1832 UINTN Offset;
1833 PCIE_CAPREG_FIELD_WIDTH Width;
1834 PCIE_EXPLAIN_FUNCTION Func;
1835 PCIE_EXPLAIN_TYPE Type;
1836 } PCIE_EXPLAIN_STRUCT;
1837
1838 PCIE_EXPLAIN_STRUCT PcieExplainList[] = {
1839 {
1840 STRING_TOKEN (STR_PCIEX_CAPABILITY_CAPID),
1841 0x00,
1842 FieldWidthUINT8,
1843 NULL,
1844 PcieExplainTypeCommon
1845 },
1846 {
1847 STRING_TOKEN (STR_PCIEX_NEXTCAP_PTR),
1848 0x01,
1849 FieldWidthUINT8,
1850 NULL,
1851 PcieExplainTypeCommon
1852 },
1853 {
1854 STRING_TOKEN (STR_PCIEX_CAP_REGISTER),
1855 0x02,
1856 FieldWidthUINT16,
1857 ExplainPcieCapReg,
1858 PcieExplainTypeCommon
1859 },
1860 {
1861 STRING_TOKEN (STR_PCIEX_DEVICE_CAP),
1862 0x04,
1863 FieldWidthUINT32,
1864 ExplainPcieDeviceCap,
1865 PcieExplainTypeDevice
1866 },
1867 {
1868 STRING_TOKEN (STR_PCIEX_DEVICE_CONTROL),
1869 0x08,
1870 FieldWidthUINT16,
1871 ExplainPcieDeviceControl,
1872 PcieExplainTypeDevice
1873 },
1874 {
1875 STRING_TOKEN (STR_PCIEX_DEVICE_STATUS),
1876 0x0a,
1877 FieldWidthUINT16,
1878 ExplainPcieDeviceStatus,
1879 PcieExplainTypeDevice
1880 },
1881 {
1882 STRING_TOKEN (STR_PCIEX_LINK_CAPABILITIES),
1883 0x0c,
1884 FieldWidthUINT32,
1885 ExplainPcieLinkCap,
1886 PcieExplainTypeLink
1887 },
1888 {
1889 STRING_TOKEN (STR_PCIEX_LINK_CONTROL),
1890 0x10,
1891 FieldWidthUINT16,
1892 ExplainPcieLinkControl,
1893 PcieExplainTypeLink
1894 },
1895 {
1896 STRING_TOKEN (STR_PCIEX_LINK_STATUS),
1897 0x12,
1898 FieldWidthUINT16,
1899 ExplainPcieLinkStatus,
1900 PcieExplainTypeLink
1901 },
1902 {
1903 STRING_TOKEN (STR_PCIEX_SLOT_CAPABILITIES),
1904 0x14,
1905 FieldWidthUINT32,
1906 ExplainPcieSlotCap,
1907 PcieExplainTypeSlot
1908 },
1909 {
1910 STRING_TOKEN (STR_PCIEX_SLOT_CONTROL),
1911 0x18,
1912 FieldWidthUINT16,
1913 ExplainPcieSlotControl,
1914 PcieExplainTypeSlot
1915 },
1916 {
1917 STRING_TOKEN (STR_PCIEX_SLOT_STATUS),
1918 0x1a,
1919 FieldWidthUINT16,
1920 ExplainPcieSlotStatus,
1921 PcieExplainTypeSlot
1922 },
1923 {
1924 STRING_TOKEN (STR_PCIEX_ROOT_CONTROL),
1925 0x1c,
1926 FieldWidthUINT16,
1927 ExplainPcieRootControl,
1928 PcieExplainTypeRoot
1929 },
1930 {
1931 STRING_TOKEN (STR_PCIEX_RSVDP),
1932 0x1e,
1933 FieldWidthUINT16,
1934 ExplainPcieRootCap,
1935 PcieExplainTypeRoot
1936 },
1937 {
1938 STRING_TOKEN (STR_PCIEX_ROOT_STATUS),
1939 0x20,
1940 FieldWidthUINT32,
1941 ExplainPcieRootStatus,
1942 PcieExplainTypeRoot
1943 },
1944 {
1945 0,
1946 0,
1947 (PCIE_CAPREG_FIELD_WIDTH)0,
1948 NULL,
1949 PcieExplainTypeMax
1950 }
1951 };
1952
1953 //
1954 // Global Variables
1955 //
1956 PCI_CONFIG_SPACE *mConfigSpace = NULL;
1957 STATIC CONST SHELL_PARAM_ITEM ParamList[] = {
1958 {L"-s", TypeValue},
1959 {L"-i", TypeFlag},
1960 {NULL, TypeMax}
1961 };
1962
1963 CHAR16 *DevicePortTypeTable[] = {
1964 L"PCI Express Endpoint",
1965 L"Legacy PCI Express Endpoint",
1966 L"Unknown Type",
1967 L"Unknonw Type",
1968 L"Root Port of PCI Express Root Complex",
1969 L"Upstream Port of PCI Express Switch",
1970 L"Downstream Port of PCI Express Switch",
1971 L"PCI Express to PCI/PCI-X Bridge",
1972 L"PCI/PCI-X to PCI Express Bridge",
1973 L"Root Complex Integrated Endpoint",
1974 L"Root Complex Event Collector"
1975 };
1976
1977 CHAR16 *L0sLatencyStrTable[] = {
1978 L"Less than 64ns",
1979 L"64ns to less than 128ns",
1980 L"128ns to less than 256ns",
1981 L"256ns to less than 512ns",
1982 L"512ns to less than 1us",
1983 L"1us to less than 2us",
1984 L"2us-4us",
1985 L"More than 4us"
1986 };
1987
1988 CHAR16 *L1LatencyStrTable[] = {
1989 L"Less than 1us",
1990 L"1us to less than 2us",
1991 L"2us to less than 4us",
1992 L"4us to less than 8us",
1993 L"8us to less than 16us",
1994 L"16us to less than 32us",
1995 L"32us-64us",
1996 L"More than 64us"
1997 };
1998
1999 CHAR16 *ASPMCtrlStrTable[] = {
2000 L"Disabled",
2001 L"L0s Entry Enabled",
2002 L"L1 Entry Enabled",
2003 L"L0s and L1 Entry Enabled"
2004 };
2005
2006 CHAR16 *SlotPwrLmtScaleTable[] = {
2007 L"1.0x",
2008 L"0.1x",
2009 L"0.01x",
2010 L"0.001x"
2011 };
2012
2013 CHAR16 *IndicatorTable[] = {
2014 L"Reserved",
2015 L"On",
2016 L"Blink",
2017 L"Off"
2018 };
2019
2020
2021 /**
2022 Function for 'pci' command.
2023
2024 @param[in] ImageHandle Handle to the Image (NULL if Internal).
2025 @param[in] SystemTable Pointer to the System Table (NULL if Internal).
2026 **/
2027 SHELL_STATUS
2028 EFIAPI
2029 ShellCommandRunPci (
2030 IN EFI_HANDLE ImageHandle,
2031 IN EFI_SYSTEM_TABLE *SystemTable
2032 )
2033 {
2034 UINT16 Segment;
2035 UINT16 Bus;
2036 UINT16 Device;
2037 UINT16 Func;
2038 UINT64 Address;
2039 EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev;
2040 EFI_STATUS Status;
2041 PCI_COMMON_HEADER PciHeader;
2042 PCI_CONFIG_SPACE ConfigSpace;
2043 UINTN ScreenCount;
2044 UINTN TempColumn;
2045 UINTN ScreenSize;
2046 BOOLEAN ExplainData;
2047 UINTN Index;
2048 UINTN SizeOfHeader;
2049 BOOLEAN PrintTitle;
2050 UINTN HandleBufSize;
2051 EFI_HANDLE *HandleBuf;
2052 UINTN HandleCount;
2053 EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR *Descriptors;
2054 UINT16 MinBus;
2055 UINT16 MaxBus;
2056 BOOLEAN IsEnd;
2057 LIST_ENTRY *Package;
2058 CHAR16 *ProblemParam;
2059 SHELL_STATUS ShellStatus;
2060 CONST CHAR16 *Temp;
2061 UINT64 RetVal;
2062 UINT16 EnhancedDump;
2063
2064 ShellStatus = SHELL_SUCCESS;
2065 Status = EFI_SUCCESS;
2066 Address = 0;
2067 IoDev = NULL;
2068 HandleBuf = NULL;
2069 Package = NULL;
2070
2071 //
2072 // initialize the shell lib (we must be in non-auto-init...)
2073 //
2074 Status = ShellInitialize();
2075 ASSERT_EFI_ERROR(Status);
2076
2077 Status = CommandInit();
2078 ASSERT_EFI_ERROR(Status);
2079
2080 //
2081 // parse the command line
2082 //
2083 Status = ShellCommandLineParse (ParamList, &Package, &ProblemParam, TRUE);
2084 if (EFI_ERROR(Status)) {
2085 if (Status == EFI_VOLUME_CORRUPTED && ProblemParam != NULL) {
2086 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, ProblemParam);
2087 FreePool(ProblemParam);
2088 ShellStatus = SHELL_INVALID_PARAMETER;
2089 } else {
2090 ASSERT(FALSE);
2091 }
2092 } else {
2093
2094 if (ShellCommandLineGetCount(Package) == 2) {
2095 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW), gShellDebug1HiiHandle);
2096 ShellStatus = SHELL_INVALID_PARAMETER;
2097 goto Done;
2098 }
2099
2100 if (ShellCommandLineGetCount(Package) > 4) {
2101 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_MANY), gShellDebug1HiiHandle);
2102 ShellStatus = SHELL_INVALID_PARAMETER;
2103 goto Done;
2104 }
2105 if (ShellCommandLineGetFlag(Package, L"-s") && ShellCommandLineGetValue(Package, L"-s") == NULL) {
2106 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_NO_VALUE), gShellDebug1HiiHandle, L"-s");
2107 ShellStatus = SHELL_INVALID_PARAMETER;
2108 goto Done;
2109 }
2110 //
2111 // Get all instances of PciRootBridgeIo. Allocate space for 1 EFI_HANDLE and
2112 // call LibLocateHandle(), if EFI_BUFFER_TOO_SMALL is returned, allocate enough
2113 // space for handles and call it again.
2114 //
2115 HandleBufSize = sizeof (EFI_HANDLE);
2116 HandleBuf = (EFI_HANDLE *) AllocateZeroPool (HandleBufSize);
2117 if (HandleBuf == NULL) {
2118 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_OUT_MEM), gShellDebug1HiiHandle);
2119 ShellStatus = SHELL_OUT_OF_RESOURCES;
2120 goto Done;
2121 }
2122
2123 Status = gBS->LocateHandle (
2124 ByProtocol,
2125 &gEfiPciRootBridgeIoProtocolGuid,
2126 NULL,
2127 &HandleBufSize,
2128 HandleBuf
2129 );
2130
2131 if (Status == EFI_BUFFER_TOO_SMALL) {
2132 HandleBuf = ReallocatePool (sizeof (EFI_HANDLE), HandleBufSize, HandleBuf);
2133 if (HandleBuf == NULL) {
2134 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_OUT_MEM), gShellDebug1HiiHandle);
2135 ShellStatus = SHELL_OUT_OF_RESOURCES;
2136 goto Done;
2137 }
2138
2139 Status = gBS->LocateHandle (
2140 ByProtocol,
2141 &gEfiPciRootBridgeIoProtocolGuid,
2142 NULL,
2143 &HandleBufSize,
2144 HandleBuf
2145 );
2146 }
2147
2148 if (EFI_ERROR (Status)) {
2149 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PCIRBIO_NF), gShellDebug1HiiHandle);
2150 ShellStatus = SHELL_NOT_FOUND;
2151 goto Done;
2152 }
2153
2154 HandleCount = HandleBufSize / sizeof (EFI_HANDLE);
2155 //
2156 // Argument Count == 1(no other argument): enumerate all pci functions
2157 //
2158 if (ShellCommandLineGetCount(Package) == 1) {
2159 gST->ConOut->QueryMode (
2160 gST->ConOut,
2161 gST->ConOut->Mode->Mode,
2162 &TempColumn,
2163 &ScreenSize
2164 );
2165
2166 ScreenCount = 0;
2167 ScreenSize -= 4;
2168 if ((ScreenSize & 1) == 1) {
2169 ScreenSize -= 1;
2170 }
2171
2172 PrintTitle = TRUE;
2173
2174 //
2175 // For each handle, which decides a segment and a bus number range,
2176 // enumerate all devices on it.
2177 //
2178 for (Index = 0; Index < HandleCount; Index++) {
2179 Status = PciGetProtocolAndResource (
2180 HandleBuf[Index],
2181 &IoDev,
2182 &Descriptors
2183 );
2184 if (EFI_ERROR (Status)) {
2185 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_HANDLE_CFG_ERR), gShellDebug1HiiHandle, Status);
2186 ShellStatus = SHELL_NOT_FOUND;
2187 goto Done;
2188 }
2189 //
2190 // No document say it's impossible for a RootBridgeIo protocol handle
2191 // to have more than one address space descriptors, so find out every
2192 // bus range and for each of them do device enumeration.
2193 //
2194 while (TRUE) {
2195 Status = PciGetNextBusRange (&Descriptors, &MinBus, &MaxBus, &IsEnd);
2196
2197 if (EFI_ERROR (Status)) {
2198 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_BUS_RANGE_ERR), gShellDebug1HiiHandle, Status);
2199 ShellStatus = SHELL_NOT_FOUND;
2200 goto Done;
2201 }
2202
2203 if (IsEnd) {
2204 break;
2205 }
2206
2207 for (Bus = MinBus; Bus <= MaxBus; Bus++) {
2208 //
2209 // For each devices, enumerate all functions it contains
2210 //
2211 for (Device = 0; Device <= PCI_MAX_DEVICE; Device++) {
2212 //
2213 // For each function, read its configuration space and print summary
2214 //
2215 for (Func = 0; Func <= PCI_MAX_FUNC; Func++) {
2216 if (ShellGetExecutionBreakFlag ()) {
2217 ShellStatus = SHELL_ABORTED;
2218 goto Done;
2219 }
2220 Address = CALC_EFI_PCI_ADDRESS (Bus, Device, Func, 0);
2221 IoDev->Pci.Read (
2222 IoDev,
2223 EfiPciWidthUint16,
2224 Address,
2225 1,
2226 &PciHeader.VendorId
2227 );
2228
2229 //
2230 // If VendorId = 0xffff, there does not exist a device at this
2231 // location. For each device, if there is any function on it,
2232 // there must be 1 function at Function 0. So if Func = 0, there
2233 // will be no more functions in the same device, so we can break
2234 // loop to deal with the next device.
2235 //
2236 if (PciHeader.VendorId == 0xffff && Func == 0) {
2237 break;
2238 }
2239
2240 if (PciHeader.VendorId != 0xffff) {
2241
2242 if (PrintTitle) {
2243 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_TITLE), gShellDebug1HiiHandle);
2244 PrintTitle = FALSE;
2245 }
2246
2247 IoDev->Pci.Read (
2248 IoDev,
2249 EfiPciWidthUint32,
2250 Address,
2251 sizeof (PciHeader) / sizeof (UINT32),
2252 &PciHeader
2253 );
2254
2255 ShellPrintHiiEx(
2256 -1, -1, NULL, STRING_TOKEN (STR_PCI_LINE_P1), gShellDebug1HiiHandle,
2257 IoDev->SegmentNumber,
2258 Bus,
2259 Device,
2260 Func
2261 );
2262
2263 PciPrintClassCode (PciHeader.ClassCode, FALSE);
2264 ShellPrintHiiEx(
2265 -1, -1, NULL, STRING_TOKEN (STR_PCI_LINE_P2), gShellDebug1HiiHandle,
2266 PciHeader.VendorId,
2267 PciHeader.DeviceId,
2268 PciHeader.ClassCode[0]
2269 );
2270
2271 ScreenCount += 2;
2272 if (ScreenCount >= ScreenSize && ScreenSize != 0) {
2273 //
2274 // If ScreenSize == 0 we have the console redirected so don't
2275 // block updates
2276 //
2277 ScreenCount = 0;
2278 }
2279 //
2280 // If this is not a multi-function device, we can leave the loop
2281 // to deal with the next device.
2282 //
2283 if (Func == 0 && ((PciHeader.HeaderType & HEADER_TYPE_MULTI_FUNCTION) == 0x00)) {
2284 break;
2285 }
2286 }
2287 }
2288 }
2289 }
2290 //
2291 // If Descriptor is NULL, Configuration() returns EFI_UNSUPPRORED,
2292 // we assume the bus range is 0~PCI_MAX_BUS. After enumerated all
2293 // devices on all bus, we can leave loop.
2294 //
2295 if (Descriptors == NULL) {
2296 break;
2297 }
2298 }
2299 }
2300
2301 Status = EFI_SUCCESS;
2302 goto Done;
2303 }
2304
2305 ExplainData = FALSE;
2306 Segment = 0;
2307 Bus = 0;
2308 Device = 0;
2309 Func = 0;
2310 if (ShellCommandLineGetFlag(Package, L"-i")) {
2311 ExplainData = TRUE;
2312 }
2313
2314 Temp = ShellCommandLineGetValue(Package, L"-s");
2315 if (Temp != NULL) {
2316 //
2317 // Input converted to hexadecimal number.
2318 //
2319 if (!EFI_ERROR (ShellConvertStringToUint64 (Temp, &RetVal, TRUE, TRUE))) {
2320 Segment = (UINT16) RetVal;
2321 } else {
2322 ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_PARAM_INV_HEX), gShellDebug1HiiHandle);
2323 ShellStatus = SHELL_INVALID_PARAMETER;
2324 goto Done;
2325 }
2326 }
2327
2328 //
2329 // The first Argument(except "-i") is assumed to be Bus number, second
2330 // to be Device number, and third to be Func number.
2331 //
2332 Temp = ShellCommandLineGetRawValue(Package, 1);
2333 if (Temp != NULL) {
2334 //
2335 // Input converted to hexadecimal number.
2336 //
2337 if (!EFI_ERROR (ShellConvertStringToUint64 (Temp, &RetVal, TRUE, TRUE))) {
2338 Bus = (UINT16) RetVal;
2339 } else {
2340 ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_PARAM_INV_HEX), gShellDebug1HiiHandle);
2341 ShellStatus = SHELL_INVALID_PARAMETER;
2342 goto Done;
2343 }
2344
2345 if (Bus > MAX_BUS_NUMBER) {
2346 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, Temp);
2347 ShellStatus = SHELL_INVALID_PARAMETER;
2348 goto Done;
2349 }
2350 }
2351 Temp = ShellCommandLineGetRawValue(Package, 2);
2352 if (Temp != NULL) {
2353 //
2354 // Input converted to hexadecimal number.
2355 //
2356 if (!EFI_ERROR (ShellConvertStringToUint64 (Temp, &RetVal, TRUE, TRUE))) {
2357 Device = (UINT16) RetVal;
2358 } else {
2359 ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_PARAM_INV_HEX), gShellDebug1HiiHandle);
2360 ShellStatus = SHELL_INVALID_PARAMETER;
2361 goto Done;
2362 }
2363
2364 if (Device > MAX_DEVICE_NUMBER){
2365 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, Temp);
2366 ShellStatus = SHELL_INVALID_PARAMETER;
2367 goto Done;
2368 }
2369 }
2370
2371 Temp = ShellCommandLineGetRawValue(Package, 3);
2372 if (Temp != NULL) {
2373 //
2374 // Input converted to hexadecimal number.
2375 //
2376 if (!EFI_ERROR (ShellConvertStringToUint64 (Temp, &RetVal, TRUE, TRUE))) {
2377 Func = (UINT16) RetVal;
2378 } else {
2379 ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_PARAM_INV_HEX), gShellDebug1HiiHandle);
2380 ShellStatus = SHELL_INVALID_PARAMETER;
2381 goto Done;
2382 }
2383
2384 if (Func > MAX_FUNCTION_NUMBER){
2385 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, Temp);
2386 ShellStatus = SHELL_INVALID_PARAMETER;
2387 goto Done;
2388 }
2389 }
2390
2391 //
2392 // Find the protocol interface who's in charge of current segment, and its
2393 // bus range covers the current bus
2394 //
2395 Status = PciFindProtocolInterface (
2396 HandleBuf,
2397 HandleCount,
2398 Segment,
2399 Bus,
2400 &IoDev
2401 );
2402
2403 if (EFI_ERROR (Status)) {
2404 ShellPrintHiiEx(
2405 -1, -1, NULL, STRING_TOKEN (STR_PCI_NO_FIND), gShellDebug1HiiHandle,
2406 Segment,
2407 Bus
2408 );
2409 ShellStatus = SHELL_NOT_FOUND;
2410 goto Done;
2411 }
2412
2413 Address = CALC_EFI_PCI_ADDRESS (Bus, Device, Func, 0);
2414 Status = IoDev->Pci.Read (
2415 IoDev,
2416 EfiPciWidthUint8,
2417 Address,
2418 sizeof (ConfigSpace),
2419 &ConfigSpace
2420 );
2421
2422 if (EFI_ERROR (Status)) {
2423 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_NO_CFG), gShellDebug1HiiHandle, Status);
2424 ShellStatus = SHELL_ACCESS_DENIED;
2425 goto Done;
2426 }
2427
2428 mConfigSpace = &ConfigSpace;
2429 ShellPrintHiiEx(
2430 -1,
2431 -1,
2432 NULL,
2433 STRING_TOKEN (STR_PCI_INFO),
2434 gShellDebug1HiiHandle,
2435 Segment,
2436 Bus,
2437 Device,
2438 Func,
2439 Segment,
2440 Bus,
2441 Device,
2442 Func
2443 );
2444
2445 //
2446 // Dump standard header of configuration space
2447 //
2448 SizeOfHeader = sizeof (ConfigSpace.Common) + sizeof (ConfigSpace.NonCommon);
2449
2450 DumpHex (2, 0, SizeOfHeader, &ConfigSpace);
2451 ShellPrintEx(-1,-1, L"\r\n");
2452
2453 //
2454 // Dump device dependent Part of configuration space
2455 //
2456 DumpHex (
2457 2,
2458 SizeOfHeader,
2459 sizeof (ConfigSpace) - SizeOfHeader,
2460 ConfigSpace.Data
2461 );
2462
2463 //
2464 // If "-i" appears in command line, interpret data in configuration space
2465 //
2466 if (ExplainData) {
2467 EnhancedDump = 0;
2468 if (ShellCommandLineGetFlag(Package, L"-_e")) {
2469 EnhancedDump = 0xFFFF;
2470 Temp = ShellCommandLineGetValue(Package, L"-_e");
2471 if (Temp != NULL) {
2472 EnhancedDump = (UINT16) ShellHexStrToUintn (Temp);
2473 }
2474 }
2475 Status = PciExplainData (&ConfigSpace, Address, IoDev, EnhancedDump);
2476 }
2477 }
2478 Done:
2479 if (HandleBuf != NULL) {
2480 FreePool (HandleBuf);
2481 }
2482 if (Package != NULL) {
2483 ShellCommandLineFreeVarList (Package);
2484 }
2485 mConfigSpace = NULL;
2486 return ShellStatus;
2487 }
2488
2489 /**
2490 This function finds out the protocol which is in charge of the given
2491 segment, and its bus range covers the current bus number. It lookes
2492 each instances of RootBridgeIoProtocol handle, until the one meets the
2493 criteria is found.
2494
2495 @param[in] HandleBuf Buffer which holds all PCI_ROOT_BRIDIGE_IO_PROTOCOL handles.
2496 @param[in] HandleCount Count of all PCI_ROOT_BRIDIGE_IO_PROTOCOL handles.
2497 @param[in] Segment Segment number of device we are dealing with.
2498 @param[in] Bus Bus number of device we are dealing with.
2499 @param[out] IoDev Handle used to access configuration space of PCI device.
2500
2501 @retval EFI_SUCCESS The command completed successfully.
2502 @retval EFI_INVALID_PARAMETER Invalid parameter.
2503
2504 **/
2505 EFI_STATUS
2506 PciFindProtocolInterface (
2507 IN EFI_HANDLE *HandleBuf,
2508 IN UINTN HandleCount,
2509 IN UINT16 Segment,
2510 IN UINT16 Bus,
2511 OUT EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **IoDev
2512 )
2513 {
2514 UINTN Index;
2515 EFI_STATUS Status;
2516 EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR *Descriptors;
2517 UINT16 MinBus;
2518 UINT16 MaxBus;
2519 BOOLEAN IsEnd;
2520
2521 //
2522 // Go through all handles, until the one meets the criteria is found
2523 //
2524 for (Index = 0; Index < HandleCount; Index++) {
2525 Status = PciGetProtocolAndResource (HandleBuf[Index], IoDev, &Descriptors);
2526 if (EFI_ERROR (Status)) {
2527 return Status;
2528 }
2529 //
2530 // When Descriptors == NULL, the Configuration() is not implemented,
2531 // so we only check the Segment number
2532 //
2533 if (Descriptors == NULL && Segment == (*IoDev)->SegmentNumber) {
2534 return EFI_SUCCESS;
2535 }
2536
2537 if ((*IoDev)->SegmentNumber != Segment) {
2538 continue;
2539 }
2540
2541 while (TRUE) {
2542 Status = PciGetNextBusRange (&Descriptors, &MinBus, &MaxBus, &IsEnd);
2543 if (EFI_ERROR (Status)) {
2544 return Status;
2545 }
2546
2547 if (IsEnd) {
2548 break;
2549 }
2550
2551 if (MinBus <= Bus && MaxBus >= Bus) {
2552 return EFI_SUCCESS;
2553 }
2554 }
2555 }
2556
2557 return EFI_NOT_FOUND;
2558 }
2559
2560 /**
2561 This function gets the protocol interface from the given handle, and
2562 obtains its address space descriptors.
2563
2564 @param[in] Handle The PCI_ROOT_BRIDIGE_IO_PROTOCOL handle.
2565 @param[out] IoDev Handle used to access configuration space of PCI device.
2566 @param[out] Descriptors Points to the address space descriptors.
2567
2568 @retval EFI_SUCCESS The command completed successfully
2569 **/
2570 EFI_STATUS
2571 PciGetProtocolAndResource (
2572 IN EFI_HANDLE Handle,
2573 OUT EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **IoDev,
2574 OUT EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR **Descriptors
2575 )
2576 {
2577 EFI_STATUS Status;
2578
2579 //
2580 // Get inferface from protocol
2581 //
2582 Status = gBS->HandleProtocol (
2583 Handle,
2584 &gEfiPciRootBridgeIoProtocolGuid,
2585 (VOID**)IoDev
2586 );
2587
2588 if (EFI_ERROR (Status)) {
2589 return Status;
2590 }
2591 //
2592 // Call Configuration() to get address space descriptors
2593 //
2594 Status = (*IoDev)->Configuration (*IoDev, (VOID**)Descriptors);
2595 if (Status == EFI_UNSUPPORTED) {
2596 *Descriptors = NULL;
2597 return EFI_SUCCESS;
2598
2599 } else {
2600 return Status;
2601 }
2602 }
2603
2604 /**
2605 This function get the next bus range of given address space descriptors.
2606 It also moves the pointer backward a node, to get prepared to be called
2607 again.
2608
2609 @param[in, out] Descriptors Points to current position of a serial of address space
2610 descriptors.
2611 @param[out] MinBus The lower range of bus number.
2612 @param[out] MaxBus The upper range of bus number.
2613 @param[out] IsEnd Meet end of the serial of descriptors.
2614
2615 @retval EFI_SUCCESS The command completed successfully.
2616 **/
2617 EFI_STATUS
2618 PciGetNextBusRange (
2619 IN OUT EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR **Descriptors,
2620 OUT UINT16 *MinBus,
2621 OUT UINT16 *MaxBus,
2622 OUT BOOLEAN *IsEnd
2623 )
2624 {
2625 *IsEnd = FALSE;
2626
2627 //
2628 // When *Descriptors is NULL, Configuration() is not implemented, so assume
2629 // range is 0~PCI_MAX_BUS
2630 //
2631 if ((*Descriptors) == NULL) {
2632 *MinBus = 0;
2633 *MaxBus = PCI_MAX_BUS;
2634 return EFI_SUCCESS;
2635 }
2636 //
2637 // *Descriptors points to one or more address space descriptors, which
2638 // ends with a end tagged descriptor. Examine each of the descriptors,
2639 // if a bus typed one is found and its bus range covers bus, this handle
2640 // is the handle we are looking for.
2641 //
2642
2643 while ((*Descriptors)->Desc != ACPI_END_TAG_DESCRIPTOR) {
2644 if ((*Descriptors)->ResType == ACPI_ADDRESS_SPACE_TYPE_BUS) {
2645 *MinBus = (UINT16) (*Descriptors)->AddrRangeMin;
2646 *MaxBus = (UINT16) (*Descriptors)->AddrRangeMax;
2647 (*Descriptors)++;
2648 return (EFI_SUCCESS);
2649 }
2650
2651 (*Descriptors)++;
2652 }
2653
2654 if ((*Descriptors)->Desc == ACPI_END_TAG_DESCRIPTOR) {
2655 *IsEnd = TRUE;
2656 }
2657
2658 return EFI_SUCCESS;
2659 }
2660
2661 /**
2662 Explain the data in PCI configuration space. The part which is common for
2663 PCI device and bridge is interpreted in this function. It calls other
2664 functions to interpret data unique for device or bridge.
2665
2666 @param[in] ConfigSpace Data in PCI configuration space.
2667 @param[in] Address Address used to access configuration space of this PCI device.
2668 @param[in] IoDev Handle used to access configuration space of PCI device.
2669 @param[in] EnhancedDump The print format for the dump data.
2670
2671 @retval EFI_SUCCESS The command completed successfully.
2672 **/
2673 EFI_STATUS
2674 PciExplainData (
2675 IN PCI_CONFIG_SPACE *ConfigSpace,
2676 IN UINT64 Address,
2677 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
2678 IN CONST UINT16 EnhancedDump
2679 )
2680 {
2681 PCI_COMMON_HEADER *Common;
2682 PCI_HEADER_TYPE HeaderType;
2683 EFI_STATUS Status;
2684 UINT8 CapPtr;
2685
2686 Common = &(ConfigSpace->Common);
2687
2688 ShellPrintEx (-1, -1, L"\r\n");
2689
2690 //
2691 // Print Vendor Id and Device Id
2692 //
2693 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_LINE_VID_DID), gShellDebug1HiiHandle,
2694 INDEX_OF (&(Common->VendorId)),
2695 Common->VendorId,
2696 INDEX_OF (&(Common->DeviceId)),
2697 Common->DeviceId
2698 );
2699
2700 //
2701 // Print register Command
2702 //
2703 PciExplainCommand (&(Common->Command));
2704
2705 //
2706 // Print register Status
2707 //
2708 PciExplainStatus (&(Common->Status), TRUE, PciUndefined);
2709
2710 //
2711 // Print register Revision ID
2712 //
2713 ShellPrintEx(-1, -1, L"\r\n");
2714 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_LINE_RID), gShellDebug1HiiHandle,
2715 INDEX_OF (&(Common->RevisionId)),
2716 Common->RevisionId
2717 );
2718
2719 //
2720 // Print register BIST
2721 //
2722 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_LINE_BIST), gShellDebug1HiiHandle, INDEX_OF (&(Common->Bist)));
2723 if ((Common->Bist & PCI_BIT_7) != 0) {
2724 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_LINE_CAP), gShellDebug1HiiHandle, 0x0f & Common->Bist);
2725 } else {
2726 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_PCI_LINE_CAP_NO), gShellDebug1HiiHandle);
2727 }
2728 //
2729 // Print register Cache Line Size
2730 //
2731 ShellPrintHiiEx(-1, -1, NULL,
2732 STRING_TOKEN (STR_PCI2_CACHE_LINE_SIZE),
2733 gShellDebug1HiiHandle,
2734 INDEX_OF (&(Common->CacheLineSize)),
2735 Common->CacheLineSize
2736 );
2737
2738 //
2739 // Print register Latency Timer
2740 //
2741 ShellPrintHiiEx(-1, -1, NULL,
2742 STRING_TOKEN (STR_PCI2_LATENCY_TIMER),
2743 gShellDebug1HiiHandle,
2744 INDEX_OF (&(Common->PrimaryLatencyTimer)),
2745 Common->PrimaryLatencyTimer
2746 );
2747
2748 //
2749 // Print register Header Type
2750 //
2751 ShellPrintHiiEx(-1, -1, NULL,
2752 STRING_TOKEN (STR_PCI2_HEADER_TYPE),
2753 gShellDebug1HiiHandle,
2754 INDEX_OF (&(Common->HeaderType)),
2755 Common->HeaderType
2756 );
2757
2758 if ((Common->HeaderType & PCI_BIT_7) != 0) {
2759 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_MULTI_FUNCTION), gShellDebug1HiiHandle);
2760
2761 } else {
2762 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_SINGLE_FUNCTION), gShellDebug1HiiHandle);
2763 }
2764
2765 HeaderType = (PCI_HEADER_TYPE)(UINT8) (Common->HeaderType & 0x7f);
2766 switch (HeaderType) {
2767 case PciDevice:
2768 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_PCI_DEVICE), gShellDebug1HiiHandle);
2769 break;
2770
2771 case PciP2pBridge:
2772 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_P2P_BRIDGE), gShellDebug1HiiHandle);
2773 break;
2774
2775 case PciCardBusBridge:
2776 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_CARDBUS_BRIDGE), gShellDebug1HiiHandle);
2777 break;
2778
2779 default:
2780 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_RESERVED), gShellDebug1HiiHandle);
2781 HeaderType = PciUndefined;
2782 }
2783
2784 //
2785 // Print register Class Code
2786 //
2787 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_CLASS), gShellDebug1HiiHandle);
2788 PciPrintClassCode ((UINT8 *) Common->ClassCode, TRUE);
2789 ShellPrintEx (-1, -1, L"\r\n");
2790
2791 if (ShellGetExecutionBreakFlag()) {
2792 return EFI_SUCCESS;
2793 }
2794
2795 //
2796 // Interpret remaining part of PCI configuration header depending on
2797 // HeaderType
2798 //
2799 CapPtr = 0;
2800 Status = EFI_SUCCESS;
2801 switch (HeaderType) {
2802 case PciDevice:
2803 Status = PciExplainDeviceData (
2804 &(ConfigSpace->NonCommon.Device),
2805 Address,
2806 IoDev
2807 );
2808 CapPtr = ConfigSpace->NonCommon.Device.CapabilitiesPtr;
2809 break;
2810
2811 case PciP2pBridge:
2812 Status = PciExplainBridgeData (
2813 &(ConfigSpace->NonCommon.Bridge),
2814 Address,
2815 IoDev
2816 );
2817 CapPtr = ConfigSpace->NonCommon.Bridge.CapabilitiesPtr;
2818 break;
2819
2820 case PciCardBusBridge:
2821 Status = PciExplainCardBusData (
2822 &(ConfigSpace->NonCommon.CardBus),
2823 Address,
2824 IoDev
2825 );
2826 CapPtr = ConfigSpace->NonCommon.CardBus.CapabilitiesPtr;
2827 break;
2828 case PciUndefined:
2829 default:
2830 break;
2831 }
2832 //
2833 // If Status bit4 is 1, dump or explain capability structure
2834 //
2835 if ((Common->Status) & EFI_PCI_STATUS_CAPABILITY) {
2836 PciExplainCapabilityStruct (IoDev, Address, CapPtr, EnhancedDump);
2837 }
2838
2839 return Status;
2840 }
2841
2842 /**
2843 Explain the device specific part of data in PCI configuration space.
2844
2845 @param[in] Device Data in PCI configuration space.
2846 @param[in] Address Address used to access configuration space of this PCI device.
2847 @param[in] IoDev Handle used to access configuration space of PCI device.
2848
2849 @retval EFI_SUCCESS The command completed successfully.
2850 **/
2851 EFI_STATUS
2852 PciExplainDeviceData (
2853 IN PCI_DEVICE_HEADER *Device,
2854 IN UINT64 Address,
2855 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev
2856 )
2857 {
2858 UINTN Index;
2859 BOOLEAN BarExist;
2860 EFI_STATUS Status;
2861 UINTN BarCount;
2862
2863 //
2864 // Print Base Address Registers(Bar). When Bar = 0, this Bar does not
2865 // exist. If these no Bar for this function, print "none", otherwise
2866 // list detail information about this Bar.
2867 //
2868 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_BASE_ADDR), gShellDebug1HiiHandle, INDEX_OF (Device->Bar));
2869
2870 BarExist = FALSE;
2871 BarCount = sizeof (Device->Bar) / sizeof (Device->Bar[0]);
2872 for (Index = 0; Index < BarCount; Index++) {
2873 if (Device->Bar[Index] == 0) {
2874 continue;
2875 }
2876
2877 if (!BarExist) {
2878 BarExist = TRUE;
2879 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_START_TYPE), gShellDebug1HiiHandle);
2880 ShellPrintEx (-1, -1, L" --------------------------------------------------------------------------");
2881 }
2882
2883 Status = PciExplainBar (
2884 &(Device->Bar[Index]),
2885 &(mConfigSpace->Common.Command),
2886 Address,
2887 IoDev,
2888 &Index
2889 );
2890
2891 if (EFI_ERROR (Status)) {
2892 break;
2893 }
2894 }
2895
2896 if (!BarExist) {
2897 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NONE), gShellDebug1HiiHandle);
2898
2899 } else {
2900 ShellPrintEx (-1, -1, L"\r\n --------------------------------------------------------------------------");
2901 }
2902
2903 //
2904 // Print register Expansion ROM Base Address
2905 //
2906 if ((Device->ROMBar & PCI_BIT_0) == 0) {
2907 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_EXPANSION_ROM_DISABLED), gShellDebug1HiiHandle, INDEX_OF (&(Device->ROMBar)));
2908
2909 } else {
2910 ShellPrintHiiEx(-1, -1, NULL,
2911 STRING_TOKEN (STR_PCI2_EXPANSION_ROM_BASE),
2912 gShellDebug1HiiHandle,
2913 INDEX_OF (&(Device->ROMBar)),
2914 Device->ROMBar
2915 );
2916 }
2917 //
2918 // Print register Cardbus CIS ptr
2919 //
2920 ShellPrintHiiEx(-1, -1, NULL,
2921 STRING_TOKEN (STR_PCI2_CARDBUS_CIS),
2922 gShellDebug1HiiHandle,
2923 INDEX_OF (&(Device->CardBusCISPtr)),
2924 Device->CardBusCISPtr
2925 );
2926
2927 //
2928 // Print register Sub-vendor ID and subsystem ID
2929 //
2930 ShellPrintHiiEx(-1, -1, NULL,
2931 STRING_TOKEN (STR_PCI2_SUB_VENDOR_ID),
2932 gShellDebug1HiiHandle,
2933 INDEX_OF (&(Device->SubVendorId)),
2934 Device->SubVendorId
2935 );
2936
2937 ShellPrintHiiEx(-1, -1, NULL,
2938 STRING_TOKEN (STR_PCI2_SUBSYSTEM_ID),
2939 gShellDebug1HiiHandle,
2940 INDEX_OF (&(Device->SubSystemId)),
2941 Device->SubSystemId
2942 );
2943
2944 //
2945 // Print register Capabilities Ptr
2946 //
2947 ShellPrintHiiEx(-1, -1, NULL,
2948 STRING_TOKEN (STR_PCI2_CAPABILITIES_PTR),
2949 gShellDebug1HiiHandle,
2950 INDEX_OF (&(Device->CapabilitiesPtr)),
2951 Device->CapabilitiesPtr
2952 );
2953
2954 //
2955 // Print register Interrupt Line and interrupt pin
2956 //
2957 ShellPrintHiiEx(-1, -1, NULL,
2958 STRING_TOKEN (STR_PCI2_INTERRUPT_LINE),
2959 gShellDebug1HiiHandle,
2960 INDEX_OF (&(Device->InterruptLine)),
2961 Device->InterruptLine
2962 );
2963
2964 ShellPrintHiiEx(-1, -1, NULL,
2965 STRING_TOKEN (STR_PCI2_INTERRUPT_PIN),
2966 gShellDebug1HiiHandle,
2967 INDEX_OF (&(Device->InterruptPin)),
2968 Device->InterruptPin
2969 );
2970
2971 //
2972 // Print register Min_Gnt and Max_Lat
2973 //
2974 ShellPrintHiiEx(-1, -1, NULL,
2975 STRING_TOKEN (STR_PCI2_MIN_GNT),
2976 gShellDebug1HiiHandle,
2977 INDEX_OF (&(Device->MinGnt)),
2978 Device->MinGnt
2979 );
2980
2981 ShellPrintHiiEx(-1, -1, NULL,
2982 STRING_TOKEN (STR_PCI2_MAX_LAT),
2983 gShellDebug1HiiHandle,
2984 INDEX_OF (&(Device->MaxLat)),
2985 Device->MaxLat
2986 );
2987
2988 return EFI_SUCCESS;
2989 }
2990
2991 /**
2992 Explain the bridge specific part of data in PCI configuration space.
2993
2994 @param[in] Bridge Bridge specific data region in PCI configuration space.
2995 @param[in] Address Address used to access configuration space of this PCI device.
2996 @param[in] IoDev Handle used to access configuration space of PCI device.
2997
2998 @retval EFI_SUCCESS The command completed successfully.
2999 **/
3000 EFI_STATUS
3001 PciExplainBridgeData (
3002 IN PCI_BRIDGE_HEADER *Bridge,
3003 IN UINT64 Address,
3004 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev
3005 )
3006 {
3007 UINTN Index;
3008 BOOLEAN BarExist;
3009 UINTN BarCount;
3010 UINT32 IoAddress32;
3011 EFI_STATUS Status;
3012
3013 //
3014 // Print Base Address Registers. When Bar = 0, this Bar does not
3015 // exist. If these no Bar for this function, print "none", otherwise
3016 // list detail information about this Bar.
3017 //
3018 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_BASE_ADDRESS), gShellDebug1HiiHandle, INDEX_OF (&(Bridge->Bar)));
3019
3020 BarExist = FALSE;
3021 BarCount = sizeof (Bridge->Bar) / sizeof (Bridge->Bar[0]);
3022
3023 for (Index = 0; Index < BarCount; Index++) {
3024 if (Bridge->Bar[Index] == 0) {
3025 continue;
3026 }
3027
3028 if (!BarExist) {
3029 BarExist = TRUE;
3030 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_START_TYPE_2), gShellDebug1HiiHandle);
3031 ShellPrintEx (-1, -1, L" --------------------------------------------------------------------------");
3032 }
3033
3034 Status = PciExplainBar (
3035 &(Bridge->Bar[Index]),
3036 &(mConfigSpace->Common.Command),
3037 Address,
3038 IoDev,
3039 &Index
3040 );
3041
3042 if (EFI_ERROR (Status)) {
3043 break;
3044 }
3045 }
3046
3047 if (!BarExist) {
3048 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NONE), gShellDebug1HiiHandle);
3049 } else {
3050 ShellPrintEx (-1, -1, L"\r\n --------------------------------------------------------------------------");
3051 }
3052
3053 //
3054 // Expansion register ROM Base Address
3055 //
3056 if ((Bridge->ROMBar & PCI_BIT_0) == 0) {
3057 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NO_EXPANSION_ROM), gShellDebug1HiiHandle, INDEX_OF (&(Bridge->ROMBar)));
3058
3059 } else {
3060 ShellPrintHiiEx(-1, -1, NULL,
3061 STRING_TOKEN (STR_PCI2_EXPANSION_ROM_BASE_2),
3062 gShellDebug1HiiHandle,
3063 INDEX_OF (&(Bridge->ROMBar)),
3064 Bridge->ROMBar
3065 );
3066 }
3067 //
3068 // Print Bus Numbers(Primary, Secondary, and Subordinate
3069 //
3070 ShellPrintHiiEx(-1, -1, NULL,
3071 STRING_TOKEN (STR_PCI2_BUS_NUMBERS),
3072 gShellDebug1HiiHandle,
3073 INDEX_OF (&(Bridge->PrimaryBus)),
3074 INDEX_OF (&(Bridge->SecondaryBus)),
3075 INDEX_OF (&(Bridge->SubordinateBus))
3076 );
3077
3078 ShellPrintEx (-1, -1, L" ------------------------------------------------------\r\n");
3079
3080 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_BRIDGE), gShellDebug1HiiHandle, Bridge->PrimaryBus);
3081 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_BRIDGE), gShellDebug1HiiHandle, Bridge->SecondaryBus);
3082 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_BRIDGE), gShellDebug1HiiHandle, Bridge->SubordinateBus);
3083
3084 //
3085 // Print register Secondary Latency Timer
3086 //
3087 ShellPrintHiiEx(-1, -1, NULL,
3088 STRING_TOKEN (STR_PCI2_SECONDARY_TIMER),
3089 gShellDebug1HiiHandle,
3090 INDEX_OF (&(Bridge->SecondaryLatencyTimer)),
3091 Bridge->SecondaryLatencyTimer
3092 );
3093
3094 //
3095 // Print register Secondary Status
3096 //
3097 PciExplainStatus (&(Bridge->SecondaryStatus), FALSE, PciP2pBridge);
3098
3099 //
3100 // Print I/O and memory ranges this bridge forwards. There are 3 resource
3101 // types: I/O, memory, and pre-fetchable memory. For each resource type,
3102 // base and limit address are listed.
3103 //
3104 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_RESOURCE_TYPE), gShellDebug1HiiHandle);
3105 ShellPrintEx (-1, -1, L"----------------------------------------------------------------------\r\n");
3106
3107 //
3108 // IO Base & Limit
3109 //
3110 IoAddress32 = (Bridge->IoBaseUpper << 16 | Bridge->IoBase << 8);
3111 IoAddress32 &= 0xfffff000;
3112 ShellPrintHiiEx(-1, -1, NULL,
3113 STRING_TOKEN (STR_PCI2_TWO_VARS),
3114 gShellDebug1HiiHandle,
3115 INDEX_OF (&(Bridge->IoBase)),
3116 IoAddress32
3117 );
3118
3119 IoAddress32 = (Bridge->IoLimitUpper << 16 | Bridge->IoLimit << 8);
3120 IoAddress32 |= 0x00000fff;
3121 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_ONE_VAR), gShellDebug1HiiHandle, IoAddress32);
3122
3123 //
3124 // Memory Base & Limit
3125 //
3126 ShellPrintHiiEx(-1, -1, NULL,
3127 STRING_TOKEN (STR_PCI2_MEMORY),
3128 gShellDebug1HiiHandle,
3129 INDEX_OF (&(Bridge->MemoryBase)),
3130 (Bridge->MemoryBase << 16) & 0xfff00000
3131 );
3132
3133 ShellPrintHiiEx(-1, -1, NULL,
3134 STRING_TOKEN (STR_PCI2_ONE_VAR),
3135 gShellDebug1HiiHandle,
3136 (Bridge->MemoryLimit << 16) | 0x000fffff
3137 );
3138
3139 //
3140 // Pre-fetch-able Memory Base & Limit
3141 //
3142 ShellPrintHiiEx(-1, -1, NULL,
3143 STRING_TOKEN (STR_PCI2_PREFETCHABLE),
3144 gShellDebug1HiiHandle,
3145 INDEX_OF (&(Bridge->PrefetchableMemBase)),
3146 Bridge->PrefetchableBaseUpper,
3147 (Bridge->PrefetchableMemBase << 16) & 0xfff00000
3148 );
3149
3150 ShellPrintHiiEx(-1, -1, NULL,
3151 STRING_TOKEN (STR_PCI2_TWO_VARS_2),
3152 gShellDebug1HiiHandle,
3153 Bridge->PrefetchableLimitUpper,
3154 (Bridge->PrefetchableMemLimit << 16) | 0x000fffff
3155 );
3156
3157 //
3158 // Print register Capabilities Pointer
3159 //
3160 ShellPrintHiiEx(-1, -1, NULL,
3161 STRING_TOKEN (STR_PCI2_CAPABILITIES_PTR_2),
3162 gShellDebug1HiiHandle,
3163 INDEX_OF (&(Bridge->CapabilitiesPtr)),
3164 Bridge->CapabilitiesPtr
3165 );
3166
3167 //
3168 // Print register Bridge Control
3169 //
3170 PciExplainBridgeControl (&(Bridge->BridgeControl), PciP2pBridge);
3171
3172 //
3173 // Print register Interrupt Line & PIN
3174 //
3175 ShellPrintHiiEx(-1, -1, NULL,
3176 STRING_TOKEN (STR_PCI2_INTERRUPT_LINE_2),
3177 gShellDebug1HiiHandle,
3178 INDEX_OF (&(Bridge->InterruptLine)),
3179 Bridge->InterruptLine
3180 );
3181
3182 ShellPrintHiiEx(-1, -1, NULL,
3183 STRING_TOKEN (STR_PCI2_INTERRUPT_PIN),
3184 gShellDebug1HiiHandle,
3185 INDEX_OF (&(Bridge->InterruptPin)),
3186 Bridge->InterruptPin
3187 );
3188
3189 return EFI_SUCCESS;
3190 }
3191
3192 /**
3193 Explain the Base Address Register(Bar) in PCI configuration space.
3194
3195 @param[in] Bar Points to the Base Address Register intended to interpret.
3196 @param[in] Command Points to the register Command.
3197 @param[in] Address Address used to access configuration space of this PCI device.
3198 @param[in] IoDev Handle used to access configuration space of PCI device.
3199 @param[in, out] Index The Index.
3200
3201 @retval EFI_SUCCESS The command completed successfully.
3202 **/
3203 EFI_STATUS
3204 PciExplainBar (
3205 IN UINT32 *Bar,
3206 IN UINT16 *Command,
3207 IN UINT64 Address,
3208 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
3209 IN OUT UINTN *Index
3210 )
3211 {
3212 UINT16 OldCommand;
3213 UINT16 NewCommand;
3214 UINT64 Bar64;
3215 UINT32 OldBar32;
3216 UINT32 NewBar32;
3217 UINT64 OldBar64;
3218 UINT64 NewBar64;
3219 BOOLEAN IsMem;
3220 BOOLEAN IsBar32;
3221 UINT64 RegAddress;
3222
3223 IsBar32 = TRUE;
3224 Bar64 = 0;
3225 NewBar32 = 0;
3226 NewBar64 = 0;
3227
3228 //
3229 // According the bar type, list detail about this bar, for example: 32 or
3230 // 64 bits; pre-fetchable or not.
3231 //
3232 if ((*Bar & PCI_BIT_0) == 0) {
3233 //
3234 // This bar is of memory type
3235 //
3236 IsMem = TRUE;
3237
3238 if ((*Bar & PCI_BIT_1) == 0 && (*Bar & PCI_BIT_2) == 0) {
3239 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_BAR), gShellDebug1HiiHandle, *Bar & 0xfffffff0);
3240 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_MEM), gShellDebug1HiiHandle);
3241 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_32_BITS), gShellDebug1HiiHandle);
3242
3243 } else if ((*Bar & PCI_BIT_1) == 0 && (*Bar & PCI_BIT_2) != 0) {
3244 Bar64 = 0x0;
3245 CopyMem (&Bar64, Bar, sizeof (UINT64));
3246 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_ONE_VAR_2), gShellDebug1HiiHandle, (UINT32) RShiftU64 ((Bar64 & 0xfffffffffffffff0ULL), 32));
3247 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_ONE_VAR_3), gShellDebug1HiiHandle, (UINT32) (Bar64 & 0xfffffffffffffff0ULL));
3248 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_MEM), gShellDebug1HiiHandle);
3249 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_64_BITS), gShellDebug1HiiHandle);
3250 IsBar32 = FALSE;
3251 *Index += 1;
3252
3253 } else {
3254 //
3255 // Reserved
3256 //
3257 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_BAR), gShellDebug1HiiHandle, *Bar & 0xfffffff0);
3258 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_MEM_2), gShellDebug1HiiHandle);
3259 }
3260
3261 if ((*Bar & PCI_BIT_3) == 0) {
3262 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NO), gShellDebug1HiiHandle);
3263
3264 } else {
3265 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_YES), gShellDebug1HiiHandle);
3266 }
3267
3268 } else {
3269 //
3270 // This bar is of io type
3271 //
3272 IsMem = FALSE;
3273 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_ONE_VAR_4), gShellDebug1HiiHandle, *Bar & 0xfffffffc);
3274 ShellPrintEx (-1, -1, L"I/O ");
3275 }
3276
3277 //
3278 // Get BAR length(or the amount of resource this bar demands for). To get
3279 // Bar length, first we should temporarily disable I/O and memory access
3280 // of this function(by set bits in the register Command), then write all
3281 // "1"s to this bar. The bar value read back is the amount of resource
3282 // this bar demands for.
3283 //
3284 //
3285 // Disable io & mem access
3286 //
3287 OldCommand = *Command;
3288 NewCommand = (UINT16) (OldCommand & 0xfffc);
3289 RegAddress = Address | INDEX_OF (Command);
3290 IoDev->Pci.Write (IoDev, EfiPciWidthUint16, RegAddress, 1, &NewCommand);
3291
3292 RegAddress = Address | INDEX_OF (Bar);
3293
3294 //
3295 // Read after write the BAR to get the size
3296 //
3297 if (IsBar32) {
3298 OldBar32 = *Bar;
3299 NewBar32 = 0xffffffff;
3300
3301 IoDev->Pci.Write (IoDev, EfiPciWidthUint32, RegAddress, 1, &NewBar32);
3302 IoDev->Pci.Read (IoDev, EfiPciWidthUint32, RegAddress, 1, &NewBar32);
3303 IoDev->Pci.Write (IoDev, EfiPciWidthUint32, RegAddress, 1, &OldBar32);
3304
3305 if (IsMem) {
3306 NewBar32 = NewBar32 & 0xfffffff0;
3307 NewBar32 = (~NewBar32) + 1;
3308
3309 } else {
3310 NewBar32 = NewBar32 & 0xfffffffc;
3311 NewBar32 = (~NewBar32) + 1;
3312 NewBar32 = NewBar32 & 0x0000ffff;
3313 }
3314 } else {
3315
3316 OldBar64 = 0x0;
3317 CopyMem (&OldBar64, Bar, sizeof (UINT64));
3318 NewBar64 = 0xffffffffffffffffULL;
3319
3320 IoDev->Pci.Write (IoDev, EfiPciWidthUint32, RegAddress, 2, &NewBar64);
3321 IoDev->Pci.Read (IoDev, EfiPciWidthUint32, RegAddress, 2, &NewBar64);
3322 IoDev->Pci.Write (IoDev, EfiPciWidthUint32, RegAddress, 2, &OldBar64);
3323
3324 if (IsMem) {
3325 NewBar64 = NewBar64 & 0xfffffffffffffff0ULL;
3326 NewBar64 = (~NewBar64) + 1;
3327
3328 } else {
3329 NewBar64 = NewBar64 & 0xfffffffffffffffcULL;
3330 NewBar64 = (~NewBar64) + 1;
3331 NewBar64 = NewBar64 & 0x000000000000ffff;
3332 }
3333 }
3334 //
3335 // Enable io & mem access
3336 //
3337 RegAddress = Address | INDEX_OF (Command);
3338 IoDev->Pci.Write (IoDev, EfiPciWidthUint16, RegAddress, 1, &OldCommand);
3339
3340 if (IsMem) {
3341 if (IsBar32) {
3342 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NEWBAR_32), gShellDebug1HiiHandle, NewBar32);
3343 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NEWBAR_32_2), gShellDebug1HiiHandle, NewBar32 + (*Bar & 0xfffffff0) - 1);
3344
3345 } else {
3346 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_RSHIFT), gShellDebug1HiiHandle, (UINT32) RShiftU64 (NewBar64, 32));
3347 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_RSHIFT), gShellDebug1HiiHandle, (UINT32) NewBar64);
3348 ShellPrintEx (-1, -1, L" ");
3349 ShellPrintHiiEx(-1, -1, NULL,
3350 STRING_TOKEN (STR_PCI2_RSHIFT),
3351 gShellDebug1HiiHandle,
3352 (UINT32) RShiftU64 ((NewBar64 + (Bar64 & 0xfffffffffffffff0ULL) - 1), 32)
3353 );
3354 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_RSHIFT), gShellDebug1HiiHandle, (UINT32) (NewBar64 + (Bar64 & 0xfffffffffffffff0ULL) - 1));
3355
3356 }
3357 } else {
3358 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NEWBAR_32_3), gShellDebug1HiiHandle, NewBar32);
3359 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NEWBAR_32_4), gShellDebug1HiiHandle, NewBar32 + (*Bar & 0xfffffffc) - 1);
3360 }
3361
3362 return EFI_SUCCESS;
3363 }
3364
3365 /**
3366 Explain the cardbus specific part of data in PCI configuration space.
3367
3368 @param[in] CardBus CardBus specific region of PCI configuration space.
3369 @param[in] Address Address used to access configuration space of this PCI device.
3370 @param[in] IoDev Handle used to access configuration space of PCI device.
3371
3372 @retval EFI_SUCCESS The command completed successfully.
3373 **/
3374 EFI_STATUS
3375 PciExplainCardBusData (
3376 IN PCI_CARDBUS_HEADER *CardBus,
3377 IN UINT64 Address,
3378 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev
3379 )
3380 {
3381 BOOLEAN Io32Bit;
3382 PCI_CARDBUS_DATA *CardBusData;
3383
3384 ShellPrintHiiEx(-1, -1, NULL,
3385 STRING_TOKEN (STR_PCI2_CARDBUS_SOCKET),
3386 gShellDebug1HiiHandle,
3387 INDEX_OF (&(CardBus->CardBusSocketReg)),
3388 CardBus->CardBusSocketReg
3389 );
3390
3391 //
3392 // Print Secondary Status
3393 //
3394 PciExplainStatus (&(CardBus->SecondaryStatus), FALSE, PciCardBusBridge);
3395
3396 //
3397 // Print Bus Numbers(Primary bus number, CardBus bus number, and
3398 // Subordinate bus number
3399 //
3400 ShellPrintHiiEx(-1, -1, NULL,
3401 STRING_TOKEN (STR_PCI2_BUS_NUMBERS_2),
3402 gShellDebug1HiiHandle,
3403 INDEX_OF (&(CardBus->PciBusNumber)),
3404 INDEX_OF (&(CardBus->CardBusBusNumber)),
3405 INDEX_OF (&(CardBus->SubordinateBusNumber))
3406 );
3407
3408 ShellPrintEx (-1, -1, L" ------------------------------------------------------\r\n");
3409
3410 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_CARDBUS), gShellDebug1HiiHandle, CardBus->PciBusNumber);
3411 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_CARDBUS_2), gShellDebug1HiiHandle, CardBus->CardBusBusNumber);
3412 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_CARDBUS_3), gShellDebug1HiiHandle, CardBus->SubordinateBusNumber);
3413
3414 //
3415 // Print CardBus Latency Timer
3416 //
3417 ShellPrintHiiEx(-1, -1, NULL,
3418 STRING_TOKEN (STR_PCI2_CARDBUS_LATENCY),
3419 gShellDebug1HiiHandle,
3420 INDEX_OF (&(CardBus->CardBusLatencyTimer)),
3421 CardBus->CardBusLatencyTimer
3422 );
3423
3424 //
3425 // Print Memory/Io ranges this cardbus bridge forwards
3426 //
3427 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_RESOURCE_TYPE_2), gShellDebug1HiiHandle);
3428 ShellPrintEx (-1, -1, L"----------------------------------------------------------------------\r\n");
3429
3430 ShellPrintHiiEx(-1, -1, NULL,
3431 STRING_TOKEN (STR_PCI2_MEM_3),
3432 gShellDebug1HiiHandle,
3433 INDEX_OF (&(CardBus->MemoryBase0)),
3434 CardBus->BridgeControl & PCI_BIT_8 ? L" Prefetchable" : L"Non-Prefetchable",
3435 CardBus->MemoryBase0 & 0xfffff000,
3436 CardBus->MemoryLimit0 | 0x00000fff
3437 );
3438
3439 ShellPrintHiiEx(-1, -1, NULL,
3440 STRING_TOKEN (STR_PCI2_MEM_3),
3441 gShellDebug1HiiHandle,
3442 INDEX_OF (&(CardBus->MemoryBase1)),
3443 CardBus->BridgeControl & PCI_BIT_9 ? L" Prefetchable" : L"Non-Prefetchable",
3444 CardBus->MemoryBase1 & 0xfffff000,
3445 CardBus->MemoryLimit1 | 0x00000fff
3446 );
3447
3448 Io32Bit = (BOOLEAN) (CardBus->IoBase0 & PCI_BIT_0);
3449 ShellPrintHiiEx(-1, -1, NULL,
3450 STRING_TOKEN (STR_PCI2_IO_2),
3451 gShellDebug1HiiHandle,
3452 INDEX_OF (&(CardBus->IoBase0)),
3453 Io32Bit ? L" 32 bit" : L" 16 bit",
3454 CardBus->IoBase0 & (Io32Bit ? 0xfffffffc : 0x0000fffc),
3455 (CardBus->IoLimit0 & (Io32Bit ? 0xffffffff : 0x0000ffff)) | 0x00000003
3456 );
3457
3458 Io32Bit = (BOOLEAN) (CardBus->IoBase1 & PCI_BIT_0);
3459 ShellPrintHiiEx(-1, -1, NULL,
3460 STRING_TOKEN (STR_PCI2_IO_2),
3461 gShellDebug1HiiHandle,
3462 INDEX_OF (&(CardBus->IoBase1)),
3463 Io32Bit ? L" 32 bit" : L" 16 bit",
3464 CardBus->IoBase1 & (Io32Bit ? 0xfffffffc : 0x0000fffc),
3465 (CardBus->IoLimit1 & (Io32Bit ? 0xffffffff : 0x0000ffff)) | 0x00000003
3466 );
3467
3468 //
3469 // Print register Interrupt Line & PIN
3470 //
3471 ShellPrintHiiEx(-1, -1, NULL,
3472 STRING_TOKEN (STR_PCI2_INTERRUPT_LINE_3),
3473 gShellDebug1HiiHandle,
3474 INDEX_OF (&(CardBus->InterruptLine)),
3475 CardBus->InterruptLine,
3476 INDEX_OF (&(CardBus->InterruptPin)),
3477 CardBus->InterruptPin
3478 );
3479
3480 //
3481 // Print register Bridge Control
3482 //
3483 PciExplainBridgeControl (&(CardBus->BridgeControl), PciCardBusBridge);
3484
3485 //
3486 // Print some registers in data region of PCI configuration space for cardbus
3487 // bridge. Fields include: Sub VendorId, Subsystem ID, and Legacy Mode Base
3488 // Address.
3489 //
3490 CardBusData = (PCI_CARDBUS_DATA *) ((UINT8 *) CardBus + sizeof (PCI_CARDBUS_HEADER));
3491
3492 ShellPrintHiiEx(-1, -1, NULL,
3493 STRING_TOKEN (STR_PCI2_SUB_VENDOR_ID_2),
3494 gShellDebug1HiiHandle,
3495 INDEX_OF (&(CardBusData->SubVendorId)),
3496 CardBusData->SubVendorId,
3497 INDEX_OF (&(CardBusData->SubSystemId)),
3498 CardBusData->SubSystemId
3499 );
3500
3501 ShellPrintHiiEx(-1, -1, NULL,
3502 STRING_TOKEN (STR_PCI2_OPTIONAL),
3503 gShellDebug1HiiHandle,
3504 INDEX_OF (&(CardBusData->LegacyBase)),
3505 CardBusData->LegacyBase
3506 );
3507
3508 return EFI_SUCCESS;
3509 }
3510
3511 /**
3512 Explain each meaningful bit of register Status. The definition of Status is
3513 slightly different depending on the PCI header type.
3514
3515 @param[in] Status Points to the content of register Status.
3516 @param[in] MainStatus Indicates if this register is main status(not secondary
3517 status).
3518 @param[in] HeaderType Header type of this PCI device.
3519
3520 @retval EFI_SUCCESS The command completed successfully.
3521 **/
3522 EFI_STATUS
3523 PciExplainStatus (
3524 IN UINT16 *Status,
3525 IN BOOLEAN MainStatus,
3526 IN PCI_HEADER_TYPE HeaderType
3527 )
3528 {
3529 if (MainStatus) {
3530 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_STATUS), gShellDebug1HiiHandle, INDEX_OF (Status), *Status);
3531
3532 } else {
3533 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_SECONDARY_STATUS), gShellDebug1HiiHandle, INDEX_OF (Status), *Status);
3534 }
3535
3536 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_NEW_CAPABILITIES), gShellDebug1HiiHandle, (*Status & PCI_BIT_4) != 0);
3537
3538 //
3539 // Bit 5 is meaningless for CardBus Bridge
3540 //
3541 if (HeaderType == PciCardBusBridge) {
3542 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_66_CAPABLE), gShellDebug1HiiHandle, (*Status & PCI_BIT_5) != 0);
3543
3544 } else {
3545 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_66_CAPABLE_2), gShellDebug1HiiHandle, (*Status & PCI_BIT_5) != 0);
3546 }
3547
3548 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_FAST_BACK), gShellDebug1HiiHandle, (*Status & PCI_BIT_7) != 0);
3549
3550 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_MASTER_DATA), gShellDebug1HiiHandle, (*Status & PCI_BIT_8) != 0);
3551 //
3552 // Bit 9 and bit 10 together decides the DEVSEL timing
3553 //
3554 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_DEVSEL_TIMING), gShellDebug1HiiHandle);
3555 if ((*Status & PCI_BIT_9) == 0 && (*Status & PCI_BIT_10) == 0) {
3556 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_FAST), gShellDebug1HiiHandle);
3557
3558 } else if ((*Status & PCI_BIT_9) != 0 && (*Status & PCI_BIT_10) == 0) {
3559 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_MEDIUM), gShellDebug1HiiHandle);
3560
3561 } else if ((*Status & PCI_BIT_9) == 0 && (*Status & PCI_BIT_10) != 0) {
3562 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_SLOW), gShellDebug1HiiHandle);
3563
3564 } else {
3565 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_RESERVED_2), gShellDebug1HiiHandle);
3566 }
3567
3568 ShellPrintHiiEx(-1, -1, NULL,
3569 STRING_TOKEN (STR_PCI2_SIGNALED_TARGET),
3570 gShellDebug1HiiHandle,
3571 (*Status & PCI_BIT_11) != 0
3572 );
3573
3574 ShellPrintHiiEx(-1, -1, NULL,
3575 STRING_TOKEN (STR_PCI2_RECEIVED_TARGET),
3576 gShellDebug1HiiHandle,
3577 (*Status & PCI_BIT_12) != 0
3578 );
3579
3580 ShellPrintHiiEx(-1, -1, NULL,
3581 STRING_TOKEN (STR_PCI2_RECEIVED_MASTER),
3582 gShellDebug1HiiHandle,
3583 (*Status & PCI_BIT_13) != 0
3584 );
3585
3586 if (MainStatus) {
3587 ShellPrintHiiEx(-1, -1, NULL,
3588 STRING_TOKEN (STR_PCI2_SIGNALED_ERROR),
3589 gShellDebug1HiiHandle,
3590 (*Status & PCI_BIT_14) != 0
3591 );
3592
3593 } else {
3594 ShellPrintHiiEx(-1, -1, NULL,
3595 STRING_TOKEN (STR_PCI2_RECEIVED_ERROR),
3596 gShellDebug1HiiHandle,
3597 (*Status & PCI_BIT_14) != 0
3598 );
3599 }
3600
3601 ShellPrintHiiEx(-1, -1, NULL,
3602 STRING_TOKEN (STR_PCI2_DETECTED_ERROR),
3603 gShellDebug1HiiHandle,
3604 (*Status & PCI_BIT_15) != 0
3605 );
3606
3607 return EFI_SUCCESS;
3608 }
3609
3610 /**
3611 Explain each meaningful bit of register Command.
3612
3613 @param[in] Command Points to the content of register Command.
3614
3615 @retval EFI_SUCCESS The command completed successfully.
3616 **/
3617 EFI_STATUS
3618 PciExplainCommand (
3619 IN UINT16 *Command
3620 )
3621 {
3622 //
3623 // Print the binary value of register Command
3624 //
3625 ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_PCI2_COMMAND), gShellDebug1HiiHandle, INDEX_OF (Command), *Command);
3626
3627 //
3628 // Explain register Command bit by bit
3629 //
3630 ShellPrintHiiEx(-1, -1, NULL,
3631 STRING_TOKEN (STR_PCI2_SPACE_ACCESS_DENIED),
3632 gShellDebug1HiiHandle,
3633 (*Command & PCI_BIT_0) != 0
3634 );
3635
3636 ShellPrintHiiEx(-1, -1, NULL,
3637 STRING_TOKEN (STR_PCI2_MEMORY_SPACE),
3638 gShellDebug1HiiHandle,
3639 (*Command & PCI_BIT_1) != 0
3640 );
3641
3642 ShellPrintHiiEx(-1, -1, NULL,
3643 STRING_TOKEN (STR_PCI2_BEHAVE_BUS_MASTER),
3644 gShellDebug1HiiHandle,
3645 (*Command & PCI_BIT_2) != 0
3646 );
3647
3648 ShellPrintHiiEx(-1, -1, NULL,
3649 STRING_TOKEN (STR_PCI2_MONITOR_SPECIAL_CYCLE),
3650 gShellDebug1HiiHandle,
3651 (*Command & PCI_BIT_3) != 0
3652 );
3653
3654 ShellPrintHiiEx(-1, -1, NULL,
3655 STRING_TOKEN (STR_PCI2_MEM_WRITE_INVALIDATE),
3656 gShellDebug1HiiHandle,
3657 (*Command & PCI_BIT_4) != 0
3658 );
3659
3660 ShellPrintHiiEx(-1, -1, NULL,
3661 STRING_TOKEN (STR_PCI2_PALETTE_SNOOPING),
3662 gShellDebug1HiiHandle,
3663 (*Command & PCI_BIT_5) != 0
3664 );
3665
3666 ShellPrintHiiEx(-1, -1, NULL,
3667 STRING_TOKEN (STR_PCI2_ASSERT_PERR),
3668 gShellDebug1HiiHandle,
3669 (*Command & PCI_BIT_6) != 0
3670 );
3671
3672 ShellPrintHiiEx(-1, -1, NULL,
3673 STRING_TOKEN (STR_PCI2_DO_ADDR_STEPPING),
3674 gShellDebug1HiiHandle,
3675 (*Command & PCI_BIT_7) != 0
3676 );
3677
3678 ShellPrintHiiEx(-1, -1, NULL,
3679 STRING_TOKEN (STR_PCI2_SERR_DRIVER),
3680 gShellDebug1HiiHandle,
3681 (*Command & PCI_BIT_8) != 0
3682 );
3683
3684 ShellPrintHiiEx(-1, -1, NULL,
3685 STRING_TOKEN (STR_PCI2_FAST_BACK_2),
3686 gShellDebug1HiiHandle,
3687 (*Command & PCI_BIT_9) != 0
3688 );
3689
3690 return EFI_SUCCESS;
3691 }
3692
3693 /**
3694 Explain each meaningful bit of register Bridge Control.
3695
3696 @param[in] BridgeControl Points to the content of register Bridge Control.
3697 @param[in] HeaderType The headertype.
3698
3699 @retval EFI_SUCCESS The command completed successfully.
3700 **/
3701 EFI_STATUS
3702 PciExplainBridgeControl (
3703 IN UINT16 *BridgeControl,
3704 IN PCI_HEADER_TYPE HeaderType
3705 )
3706 {
3707 ShellPrintHiiEx(-1, -1, NULL,
3708 STRING_TOKEN (STR_PCI2_BRIDGE_CONTROL),
3709 gShellDebug1HiiHandle,
3710 INDEX_OF (BridgeControl),
3711 *BridgeControl
3712 );
3713
3714 ShellPrintHiiEx(-1, -1, NULL,
3715 STRING_TOKEN (STR_PCI2_PARITY_ERROR),
3716 gShellDebug1HiiHandle,
3717 (*BridgeControl & PCI_BIT_0) != 0
3718 );
3719 ShellPrintHiiEx(-1, -1, NULL,
3720 STRING_TOKEN (STR_PCI2_SERR_ENABLE),
3721 gShellDebug1HiiHandle,
3722 (*BridgeControl & PCI_BIT_1) != 0
3723 );
3724 ShellPrintHiiEx(-1, -1, NULL,
3725 STRING_TOKEN (STR_PCI2_ISA_ENABLE),
3726 gShellDebug1HiiHandle,
3727 (*BridgeControl & PCI_BIT_2) != 0
3728 );
3729 ShellPrintHiiEx(-1, -1, NULL,
3730 STRING_TOKEN (STR_PCI2_VGA_ENABLE),
3731 gShellDebug1HiiHandle,
3732 (*BridgeControl & PCI_BIT_3) != 0
3733 );
3734 ShellPrintHiiEx(-1, -1, NULL,
3735 STRING_TOKEN (STR_PCI2_MASTER_ABORT),
3736 gShellDebug1HiiHandle,
3737 (*BridgeControl & PCI_BIT_5) != 0
3738 );
3739
3740 //
3741 // Register Bridge Control has some slight differences between P2P bridge
3742 // and Cardbus bridge from bit 6 to bit 11.
3743 //
3744 if (HeaderType == PciP2pBridge) {
3745 ShellPrintHiiEx(-1, -1, NULL,
3746 STRING_TOKEN (STR_PCI2_SECONDARY_BUS_RESET),
3747 gShellDebug1HiiHandle,
3748 (*BridgeControl & PCI_BIT_6) != 0
3749 );
3750 ShellPrintHiiEx(-1, -1, NULL,
3751 STRING_TOKEN (STR_PCI2_FAST_ENABLE),
3752 gShellDebug1HiiHandle,
3753 (*BridgeControl & PCI_BIT_7) != 0
3754 );
3755 ShellPrintHiiEx(-1, -1, NULL,
3756 STRING_TOKEN (STR_PCI2_PRIMARY_DISCARD_TIMER),
3757 gShellDebug1HiiHandle,
3758 (*BridgeControl & PCI_BIT_8)!=0 ? L"2^10" : L"2^15"
3759 );
3760 ShellPrintHiiEx(-1, -1, NULL,
3761 STRING_TOKEN (STR_PCI2_SECONDARY_DISCARD_TIMER),
3762 gShellDebug1HiiHandle,
3763 (*BridgeControl & PCI_BIT_9)!=0 ? L"2^10" : L"2^15"
3764 );
3765 ShellPrintHiiEx(-1, -1, NULL,
3766 STRING_TOKEN (STR_PCI2_DISCARD_TIMER_STATUS),
3767 gShellDebug1HiiHandle,
3768 (*BridgeControl & PCI_BIT_10) != 0
3769 );
3770 ShellPrintHiiEx(-1, -1, NULL,
3771 STRING_TOKEN (STR_PCI2_DISCARD_TIMER_SERR),
3772 gShellDebug1HiiHandle,
3773 (*BridgeControl & PCI_BIT_11) != 0
3774 );
3775
3776 } else {
3777 ShellPrintHiiEx(-1, -1, NULL,
3778 STRING_TOKEN (STR_PCI2_CARDBUS_RESET),
3779 gShellDebug1HiiHandle,
3780 (*BridgeControl & PCI_BIT_6) != 0
3781 );
3782 ShellPrintHiiEx(-1, -1, NULL,
3783 STRING_TOKEN (STR_PCI2_IREQ_ENABLE),
3784 gShellDebug1HiiHandle,
3785 (*BridgeControl & PCI_BIT_7) != 0
3786 );
3787 ShellPrintHiiEx(-1, -1, NULL,
3788 STRING_TOKEN (STR_PCI2_WRITE_POSTING_ENABLE),
3789 gShellDebug1HiiHandle,
3790 (*BridgeControl & PCI_BIT_10) != 0
3791 );
3792 }
3793
3794 return EFI_SUCCESS;
3795 }
3796
3797 /**
3798 Print each capability structure.
3799
3800 @param[in] IoDev The pointer to the deivce.
3801 @param[in] Address The address to start at.
3802 @param[in] CapPtr The offset from the address.
3803 @param[in] EnhancedDump The print format for the dump data.
3804
3805 @retval EFI_SUCCESS The operation was successful.
3806 **/
3807 EFI_STATUS
3808 PciExplainCapabilityStruct (
3809 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
3810 IN UINT64 Address,
3811 IN UINT8 CapPtr,
3812 IN CONST UINT16 EnhancedDump
3813 )
3814 {
3815 UINT8 CapabilityPtr;
3816 UINT16 CapabilityEntry;
3817 UINT8 CapabilityID;
3818 UINT64 RegAddress;
3819
3820 CapabilityPtr = CapPtr;
3821
3822 //
3823 // Go through the Capability list
3824 //
3825 while ((CapabilityPtr >= 0x40) && ((CapabilityPtr & 0x03) == 0x00)) {
3826 RegAddress = Address + CapabilityPtr;
3827 IoDev->Pci.Read (IoDev, EfiPciWidthUint16, RegAddress, 1, &CapabilityEntry);
3828
3829 CapabilityID = (UINT8) CapabilityEntry;
3830
3831 //
3832 // Explain PciExpress data
3833 //
3834 if (EFI_PCI_CAPABILITY_ID_PCIEXP == CapabilityID) {
3835 PciExplainPciExpress (IoDev, Address, CapabilityPtr, EnhancedDump);
3836 return EFI_SUCCESS;
3837 }
3838 //
3839 // Explain other capabilities here
3840 //
3841 CapabilityPtr = (UINT8) (CapabilityEntry >> 8);
3842 }
3843
3844 return EFI_SUCCESS;
3845 }
3846
3847 /**
3848 Print out information of the capability information.
3849
3850 @param[in] PciExpressCap The pointer to the structure about the device.
3851
3852 @retval EFI_SUCCESS The operation was successful.
3853 **/
3854 EFI_STATUS
3855 ExplainPcieCapReg (
3856 IN PCIE_CAP_STURCTURE *PciExpressCap
3857 )
3858 {
3859 UINT16 PcieCapReg;
3860 CHAR16 *DevicePortType;
3861
3862 PcieCapReg = PciExpressCap->PcieCapReg;
3863 ShellPrintEx (-1, -1,
3864 L" Capability Version(3:0): %E0x%04x%N\r\n",
3865 PCIE_CAP_VERSION (PcieCapReg)
3866 );
3867 if ((UINT8) PCIE_CAP_DEVICEPORT_TYPE (PcieCapReg) < PCIE_DEVICE_PORT_TYPE_MAX) {
3868 DevicePortType = DevicePortTypeTable[PCIE_CAP_DEVICEPORT_TYPE (PcieCapReg)];
3869 } else {
3870 DevicePortType = L"Unknown Type";
3871 }
3872 ShellPrintEx (-1, -1,
3873 L" Device/PortType(7:4): %E%s%N\r\n",
3874 DevicePortType
3875 );
3876 //
3877 // 'Slot Implemented' is only valid for:
3878 // a) Root Port of PCI Express Root Complex, or
3879 // b) Downstream Port of PCI Express Switch
3880 //
3881 if (PCIE_CAP_DEVICEPORT_TYPE (PcieCapReg) == PCIE_ROOT_COMPLEX_ROOT_PORT ||
3882 PCIE_CAP_DEVICEPORT_TYPE (PcieCapReg) == PCIE_SWITCH_DOWNSTREAM_PORT) {
3883 ShellPrintEx (-1, -1,
3884 L" Slot Implemented(8): %E%d%N\r\n",
3885 PCIE_CAP_SLOT_IMPLEMENTED (PcieCapReg)
3886 );
3887 }
3888 ShellPrintEx (-1, -1,
3889 L" Interrupt Message Number(13:9): %E0x%05x%N\r\n",
3890 PCIE_CAP_INT_MSG_NUM (PcieCapReg)
3891 );
3892 return EFI_SUCCESS;
3893 }
3894
3895 /**
3896 Print out information of the device capability information.
3897
3898 @param[in] PciExpressCap The pointer to the structure about the device.
3899
3900 @retval EFI_SUCCESS The operation was successful.
3901 **/
3902 EFI_STATUS
3903 ExplainPcieDeviceCap (
3904 IN PCIE_CAP_STURCTURE *PciExpressCap
3905 )
3906 {
3907 UINT16 PcieCapReg;
3908 UINT32 PcieDeviceCap;
3909 UINT8 DevicePortType;
3910 UINT8 L0sLatency;
3911 UINT8 L1Latency;
3912
3913 PcieCapReg = PciExpressCap->PcieCapReg;
3914 PcieDeviceCap = PciExpressCap->PcieDeviceCap;
3915 DevicePortType = (UINT8) PCIE_CAP_DEVICEPORT_TYPE (PcieCapReg);
3916 ShellPrintEx (-1, -1, L" Max_Payload_Size Supported(2:0): ");
3917 if (PCIE_CAP_MAX_PAYLOAD (PcieDeviceCap) < 6) {
3918 ShellPrintEx (-1, -1, L"%E%d bytes%N\r\n", 1 << (PCIE_CAP_MAX_PAYLOAD (PcieDeviceCap) + 7));
3919 } else {
3920 ShellPrintEx (-1, -1, L"%EUnknown%N\r\n");
3921 }
3922 ShellPrintEx (-1, -1,
3923 L" Phantom Functions Supported(4:3): %E%d%N\r\n",
3924 PCIE_CAP_PHANTOM_FUNC (PcieDeviceCap)
3925 );
3926 ShellPrintEx (-1, -1,
3927 L" Extended Tag Field Supported(5): %E%d-bit Tag field supported%N\r\n",
3928 PCIE_CAP_EXTENDED_TAG (PcieDeviceCap) ? 8 : 5
3929 );
3930 //
3931 // Endpoint L0s and L1 Acceptable Latency is only valid for Endpoint
3932 //
3933 if (IS_PCIE_ENDPOINT (DevicePortType)) {
3934 L0sLatency = (UINT8) PCIE_CAP_L0SLATENCY (PcieDeviceCap);
3935 L1Latency = (UINT8) PCIE_CAP_L1LATENCY (PcieDeviceCap);
3936 ShellPrintEx (-1, -1, L" Endpoint L0s Acceptable Latency(8:6): ");
3937 if (L0sLatency < 4) {
3938 ShellPrintEx (-1, -1, L"%EMaximum of %d ns%N\r\n", 1 << (L0sLatency + 6));
3939 } else {
3940 if (L0sLatency < 7) {
3941 ShellPrintEx (-1, -1, L"%EMaximum of %d us%N\r\n", 1 << (L0sLatency - 3));
3942 } else {
3943 ShellPrintEx (-1, -1, L"%ENo limit%N\r\n");
3944 }
3945 }
3946 ShellPrintEx (-1, -1, L" Endpoint L1 Acceptable Latency(11:9): ");
3947 if (L1Latency < 7) {
3948 ShellPrintEx (-1, -1, L"%EMaximum of %d us%N\r\n", 1 << (L1Latency + 1));
3949 } else {
3950 ShellPrintEx (-1, -1, L"%ENo limit%N\r\n");
3951 }
3952 }
3953 ShellPrintEx (-1, -1,
3954 L" Role-based Error Reporting(15): %E%d%N\r\n",
3955 PCIE_CAP_ERR_REPORTING (PcieDeviceCap)
3956 );
3957 //
3958 // Only valid for Upstream Port:
3959 // a) Captured Slot Power Limit Value
3960 // b) Captured Slot Power Scale
3961 //
3962 if (DevicePortType == PCIE_SWITCH_UPSTREAM_PORT) {
3963 ShellPrintEx (-1, -1,
3964 L" Captured Slot Power Limit Value(25:18): %E0x%02x%N\r\n",
3965 PCIE_CAP_SLOT_POWER_VALUE (PcieDeviceCap)
3966 );
3967 ShellPrintEx (-1, -1,
3968 L" Captured Slot Power Limit Scale(27:26): %E%s%N\r\n",
3969 SlotPwrLmtScaleTable[PCIE_CAP_SLOT_POWER_SCALE (PcieDeviceCap)]
3970 );
3971 }
3972 //
3973 // Function Level Reset Capability is only valid for Endpoint
3974 //
3975 if (IS_PCIE_ENDPOINT (DevicePortType)) {
3976 ShellPrintEx (-1, -1,
3977 L" Function Level Reset Capability(28): %E%d%N\r\n",
3978 PCIE_CAP_FUNC_LEVEL_RESET (PcieDeviceCap)
3979 );
3980 }
3981 return EFI_SUCCESS;
3982 }
3983
3984 /**
3985 Print out information of the device control information.
3986
3987 @param[in] PciExpressCap The pointer to the structure about the device.
3988
3989 @retval EFI_SUCCESS The operation was successful.
3990 **/
3991 EFI_STATUS
3992 ExplainPcieDeviceControl (
3993 IN PCIE_CAP_STURCTURE *PciExpressCap
3994 )
3995 {
3996 UINT16 PcieCapReg;
3997 UINT16 PcieDeviceControl;
3998
3999 PcieCapReg = PciExpressCap->PcieCapReg;
4000 PcieDeviceControl = PciExpressCap->DeviceControl;
4001 ShellPrintEx (-1, -1,
4002 L" Correctable Error Reporting Enable(0): %E%d%N\r\n",
4003 PCIE_CAP_COR_ERR_REPORTING_ENABLE (PcieDeviceControl)
4004 );
4005 ShellPrintEx (-1, -1,
4006 L" Non-Fatal Error Reporting Enable(1): %E%d%N\r\n",
4007 PCIE_CAP_NONFAT_ERR_REPORTING_ENABLE (PcieDeviceControl)
4008 );
4009 ShellPrintEx (-1, -1,
4010 L" Fatal Error Reporting Enable(2): %E%d%N\r\n",
4011 PCIE_CAP_FATAL_ERR_REPORTING_ENABLE (PcieDeviceControl)
4012 );
4013 ShellPrintEx (-1, -1,
4014 L" Unsupported Request Reporting Enable(3): %E%d%N\r\n",
4015 PCIE_CAP_UNSUP_REQ_REPORTING_ENABLE (PcieDeviceControl)
4016 );
4017 ShellPrintEx (-1, -1,
4018 L" Enable Relaxed Ordering(4): %E%d%N\r\n",
4019 PCIE_CAP_RELAXED_ORDERING_ENABLE (PcieDeviceControl)
4020 );
4021 ShellPrintEx (-1, -1, L" Max_Payload_Size(7:5): ");
4022 if (PCIE_CAP_MAX_PAYLOAD_SIZE (PcieDeviceControl) < 6) {
4023 ShellPrintEx (-1, -1, L"%E%d bytes%N\r\n", 1 << (PCIE_CAP_MAX_PAYLOAD_SIZE (PcieDeviceControl) + 7));
4024 } else {
4025 ShellPrintEx (-1, -1, L"%EUnknown%N\r\n");
4026 }
4027 ShellPrintEx (-1, -1,
4028 L" Extended Tag Field Enable(8): %E%d%N\r\n",
4029 PCIE_CAP_EXTENDED_TAG_ENABLE (PcieDeviceControl)
4030 );
4031 ShellPrintEx (-1, -1,
4032 L" Phantom Functions Enable(9): %E%d%N\r\n",
4033 PCIE_CAP_PHANTOM_FUNC_ENABLE (PcieDeviceControl)
4034 );
4035 ShellPrintEx (-1, -1,
4036 L" Auxiliary (AUX) Power PM Enable(10): %E%d%N\r\n",
4037 PCIE_CAP_AUX_PM_ENABLE (PcieDeviceControl)
4038 );
4039 ShellPrintEx (-1, -1,
4040 L" Enable No Snoop(11): %E%d%N\r\n",
4041 PCIE_CAP_NO_SNOOP_ENABLE (PcieDeviceControl)
4042 );
4043 ShellPrintEx (-1, -1, L" Max_Read_Request_Size(14:12): ");
4044 if (PCIE_CAP_MAX_READ_REQ_SIZE (PcieDeviceControl) < 6) {
4045 ShellPrintEx (-1, -1, L"%E%d bytes%N\r\n", 1 << (PCIE_CAP_MAX_READ_REQ_SIZE (PcieDeviceControl) + 7));
4046 } else {
4047 ShellPrintEx (-1, -1, L"%EUnknown%N\r\n");
4048 }
4049 //
4050 // Read operation is only valid for PCI Express to PCI/PCI-X Bridges
4051 //
4052 if (PCIE_CAP_DEVICEPORT_TYPE (PcieCapReg) == PCIE_PCIE_TO_PCIX_BRIDGE) {
4053 ShellPrintEx (-1, -1,
4054 L" Bridge Configuration Retry Enable(15): %E%d%N\r\n",
4055 PCIE_CAP_BRG_CONF_RETRY (PcieDeviceControl)
4056 );
4057 }
4058 return EFI_SUCCESS;
4059 }
4060
4061 /**
4062 Print out information of the device status information.
4063
4064 @param[in] PciExpressCap The pointer to the structure about the device.
4065
4066 @retval EFI_SUCCESS The operation was successful.
4067 **/
4068 EFI_STATUS
4069 ExplainPcieDeviceStatus (
4070 IN PCIE_CAP_STURCTURE *PciExpressCap
4071 )
4072 {
4073 UINT16 PcieDeviceStatus;
4074
4075 PcieDeviceStatus = PciExpressCap->DeviceStatus;
4076 ShellPrintEx (-1, -1,
4077 L" Correctable Error Detected(0): %E%d%N\r\n",
4078 PCIE_CAP_COR_ERR_DETECTED (PcieDeviceStatus)
4079 );
4080 ShellPrintEx (-1, -1,
4081 L" Non-Fatal Error Detected(1): %E%d%N\r\n",
4082 PCIE_CAP_NONFAT_ERR_DETECTED (PcieDeviceStatus)
4083 );
4084 ShellPrintEx (-1, -1,
4085 L" Fatal Error Detected(2): %E%d%N\r\n",
4086 PCIE_CAP_FATAL_ERR_DETECTED (PcieDeviceStatus)
4087 );
4088 ShellPrintEx (-1, -1,
4089 L" Unsupported Request Detected(3): %E%d%N\r\n",
4090 PCIE_CAP_UNSUP_REQ_DETECTED (PcieDeviceStatus)
4091 );
4092 ShellPrintEx (-1, -1,
4093 L" AUX Power Detected(4): %E%d%N\r\n",
4094 PCIE_CAP_AUX_POWER_DETECTED (PcieDeviceStatus)
4095 );
4096 ShellPrintEx (-1, -1,
4097 L" Transactions Pending(5): %E%d%N\r\n",
4098 PCIE_CAP_TRANSACTION_PENDING (PcieDeviceStatus)
4099 );
4100 return EFI_SUCCESS;
4101 }
4102
4103 /**
4104 Print out information of the device link information.
4105
4106 @param[in] PciExpressCap The pointer to the structure about the device.
4107
4108 @retval EFI_SUCCESS The operation was successful.
4109 **/
4110 EFI_STATUS
4111 ExplainPcieLinkCap (
4112 IN PCIE_CAP_STURCTURE *PciExpressCap
4113 )
4114 {
4115 UINT32 PcieLinkCap;
4116 CHAR16 *MaxLinkSpeed;
4117 CHAR16 *AspmValue;
4118
4119 PcieLinkCap = PciExpressCap->LinkCap;
4120 switch (PCIE_CAP_MAX_LINK_SPEED (PcieLinkCap)) {
4121 case 1:
4122 MaxLinkSpeed = L"2.5 GT/s";
4123 break;
4124 case 2:
4125 MaxLinkSpeed = L"5.0 GT/s";
4126 break;
4127 case 3:
4128 MaxLinkSpeed = L"8.0 GT/s";
4129 break;
4130 default:
4131 MaxLinkSpeed = L"Unknown";
4132 break;
4133 }
4134 ShellPrintEx (-1, -1,
4135 L" Maximum Link Speed(3:0): %E%s%N\r\n",
4136 MaxLinkSpeed
4137 );
4138 ShellPrintEx (-1, -1,
4139 L" Maximum Link Width(9:4): %Ex%d%N\r\n",
4140 PCIE_CAP_MAX_LINK_WIDTH (PcieLinkCap)
4141 );
4142 switch (PCIE_CAP_ASPM_SUPPORT (PcieLinkCap)) {
4143 case 0:
4144 AspmValue = L"Not";
4145 break;
4146 case 1:
4147 AspmValue = L"L0s";
4148 break;
4149 case 2:
4150 AspmValue = L"L1";
4151 break;
4152 case 3:
4153 AspmValue = L"L0s and L1";
4154 break;
4155 default:
4156 AspmValue = L"Reserved";
4157 break;
4158 }
4159 ShellPrintEx (-1, -1,
4160 L" Active State Power Management Support(11:10): %E%s Supported%N\r\n",
4161 AspmValue
4162 );
4163 ShellPrintEx (-1, -1,
4164 L" L0s Exit Latency(14:12): %E%s%N\r\n",
4165 L0sLatencyStrTable[PCIE_CAP_L0S_LATENCY (PcieLinkCap)]
4166 );
4167 ShellPrintEx (-1, -1,
4168 L" L1 Exit Latency(17:15): %E%s%N\r\n",
4169 L1LatencyStrTable[PCIE_CAP_L0S_LATENCY (PcieLinkCap)]
4170 );
4171 ShellPrintEx (-1, -1,
4172 L" Clock Power Management(18): %E%d%N\r\n",
4173 PCIE_CAP_CLOCK_PM (PcieLinkCap)
4174 );
4175 ShellPrintEx (-1, -1,
4176 L" Surprise Down Error Reporting Capable(19): %E%d%N\r\n",
4177 PCIE_CAP_SUP_DOWN_ERR_REPORTING (PcieLinkCap)
4178 );
4179 ShellPrintEx (-1, -1,
4180 L" Data Link Layer Link Active Reporting Capable(20): %E%d%N\r\n",
4181 PCIE_CAP_LINK_ACTIVE_REPORTING (PcieLinkCap)
4182 );
4183 ShellPrintEx (-1, -1,
4184 L" Link Bandwidth Notification Capability(21): %E%d%N\r\n",
4185 PCIE_CAP_LINK_BWD_NOTIF_CAP (PcieLinkCap)
4186 );
4187 ShellPrintEx (-1, -1,
4188 L" Port Number(31:24): %E0x%02x%N\r\n",
4189 PCIE_CAP_PORT_NUMBER (PcieLinkCap)
4190 );
4191 return EFI_SUCCESS;
4192 }
4193
4194 /**
4195 Print out information of the device link control information.
4196
4197 @param[in] PciExpressCap The pointer to the structure about the device.
4198
4199 @retval EFI_SUCCESS The operation was successful.
4200 **/
4201 EFI_STATUS
4202 ExplainPcieLinkControl (
4203 IN PCIE_CAP_STURCTURE *PciExpressCap
4204 )
4205 {
4206 UINT16 PcieLinkControl;
4207 UINT8 DevicePortType;
4208
4209 PcieLinkControl = PciExpressCap->LinkControl;
4210 DevicePortType = (UINT8) PCIE_CAP_DEVICEPORT_TYPE (PciExpressCap->PcieCapReg);
4211 ShellPrintEx (-1, -1,
4212 L" Active State Power Management Control(1:0): %E%s%N\r\n",
4213 ASPMCtrlStrTable[PCIE_CAP_ASPM_CONTROL (PcieLinkControl)]
4214 );
4215 //
4216 // RCB is not applicable to switches
4217 //
4218 if (!IS_PCIE_SWITCH(DevicePortType)) {
4219 ShellPrintEx (-1, -1,
4220 L" Read Completion Boundary (RCB)(3): %E%d byte%N\r\n",
4221 1 << (PCIE_CAP_RCB (PcieLinkControl) + 6)
4222 );
4223 }
4224 //
4225 // Link Disable is reserved on
4226 // a) Endpoints
4227 // b) PCI Express to PCI/PCI-X bridges
4228 // c) Upstream Ports of Switches
4229 //
4230 if (!IS_PCIE_ENDPOINT (DevicePortType) &&
4231 DevicePortType != PCIE_SWITCH_UPSTREAM_PORT &&
4232 DevicePortType != PCIE_PCIE_TO_PCIX_BRIDGE) {
4233 ShellPrintEx (-1, -1,
4234 L" Link Disable(4): %E%d%N\r\n",
4235 PCIE_CAP_LINK_DISABLE (PcieLinkControl)
4236 );
4237 }
4238 ShellPrintEx (-1, -1,
4239 L" Common Clock Configuration(6): %E%d%N\r\n",
4240 PCIE_CAP_COMMON_CLK_CONF (PcieLinkControl)
4241 );
4242 ShellPrintEx (-1, -1,
4243 L" Extended Synch(7): %E%d%N\r\n",
4244 PCIE_CAP_EXT_SYNC (PcieLinkControl)
4245 );
4246 ShellPrintEx (-1, -1,
4247 L" Enable Clock Power Management(8): %E%d%N\r\n",
4248 PCIE_CAP_CLK_PWR_MNG (PcieLinkControl)
4249 );
4250 ShellPrintEx (-1, -1,
4251 L" Hardware Autonomous Width Disable(9): %E%d%N\r\n",
4252 PCIE_CAP_HW_AUTO_WIDTH_DISABLE (PcieLinkControl)
4253 );
4254 ShellPrintEx (-1, -1,
4255 L" Link Bandwidth Management Interrupt Enable(10): %E%d%N\r\n",
4256 PCIE_CAP_LINK_BDW_MNG_INT_EN (PcieLinkControl)
4257 );
4258 ShellPrintEx (-1, -1,
4259 L" Link Autonomous Bandwidth Interrupt Enable(11): %E%d%N\r\n",
4260 PCIE_CAP_LINK_AUTO_BDW_INT_EN (PcieLinkControl)
4261 );
4262 return EFI_SUCCESS;
4263 }
4264
4265 /**
4266 Print out information of the device link status information.
4267
4268 @param[in] PciExpressCap The pointer to the structure about the device.
4269
4270 @retval EFI_SUCCESS The operation was successful.
4271 **/
4272 EFI_STATUS
4273 ExplainPcieLinkStatus (
4274 IN PCIE_CAP_STURCTURE *PciExpressCap
4275 )
4276 {
4277 UINT16 PcieLinkStatus;
4278 CHAR16 *CurLinkSpeed;
4279
4280 PcieLinkStatus = PciExpressCap->LinkStatus;
4281 switch (PCIE_CAP_CUR_LINK_SPEED (PcieLinkStatus)) {
4282 case 1:
4283 CurLinkSpeed = L"2.5 GT/s";
4284 break;
4285 case 2:
4286 CurLinkSpeed = L"5.0 GT/s";
4287 break;
4288 case 3:
4289 CurLinkSpeed = L"8.0 GT/s";
4290 break;
4291 default:
4292 CurLinkSpeed = L"Reserved";
4293 break;
4294 }
4295 ShellPrintEx (-1, -1,
4296 L" Current Link Speed(3:0): %E%s%N\r\n",
4297 CurLinkSpeed
4298 );
4299 ShellPrintEx (-1, -1,
4300 L" Negotiated Link Width(9:4): %Ex%d%N\r\n",
4301 PCIE_CAP_NEGO_LINK_WIDTH (PcieLinkStatus)
4302 );
4303 ShellPrintEx (-1, -1,
4304 L" Link Training(11): %E%d%N\r\n",
4305 PCIE_CAP_LINK_TRAINING (PcieLinkStatus)
4306 );
4307 ShellPrintEx (-1, -1,
4308 L" Slot Clock Configuration(12): %E%d%N\r\n",
4309 PCIE_CAP_SLOT_CLK_CONF (PcieLinkStatus)
4310 );
4311 ShellPrintEx (-1, -1,
4312 L" Data Link Layer Link Active(13): %E%d%N\r\n",
4313 PCIE_CAP_DATA_LINK_ACTIVE (PcieLinkStatus)
4314 );
4315 ShellPrintEx (-1, -1,
4316 L" Link Bandwidth Management Status(14): %E%d%N\r\n",
4317 PCIE_CAP_LINK_BDW_MNG_STAT (PcieLinkStatus)
4318 );
4319 ShellPrintEx (-1, -1,
4320 L" Link Autonomous Bandwidth Status(15): %E%d%N\r\n",
4321 PCIE_CAP_LINK_AUTO_BDW_STAT (PcieLinkStatus)
4322 );
4323 return EFI_SUCCESS;
4324 }
4325
4326 /**
4327 Print out information of the device slot information.
4328
4329 @param[in] PciExpressCap The pointer to the structure about the device.
4330
4331 @retval EFI_SUCCESS The operation was successful.
4332 **/
4333 EFI_STATUS
4334 ExplainPcieSlotCap (
4335 IN PCIE_CAP_STURCTURE *PciExpressCap
4336 )
4337 {
4338 UINT32 PcieSlotCap;
4339
4340 PcieSlotCap = PciExpressCap->SlotCap;
4341
4342 ShellPrintEx (-1, -1,
4343 L" Attention Button Present(0): %E%d%N\r\n",
4344 PCIE_CAP_ATT_BUT_PRESENT (PcieSlotCap)
4345 );
4346 ShellPrintEx (-1, -1,
4347 L" Power Controller Present(1): %E%d%N\r\n",
4348 PCIE_CAP_PWR_CTRLLER_PRESENT (PcieSlotCap)
4349 );
4350 ShellPrintEx (-1, -1,
4351 L" MRL Sensor Present(2): %E%d%N\r\n",
4352 PCIE_CAP_MRL_SENSOR_PRESENT (PcieSlotCap)
4353 );
4354 ShellPrintEx (-1, -1,
4355 L" Attention Indicator Present(3): %E%d%N\r\n",
4356 PCIE_CAP_ATT_IND_PRESENT (PcieSlotCap)
4357 );
4358 ShellPrintEx (-1, -1,
4359 L" Power Indicator Present(4): %E%d%N\r\n",
4360 PCIE_CAP_PWD_IND_PRESENT (PcieSlotCap)
4361 );
4362 ShellPrintEx (-1, -1,
4363 L" Hot-Plug Surprise(5): %E%d%N\r\n",
4364 PCIE_CAP_HOTPLUG_SUPPRISE (PcieSlotCap)
4365 );
4366 ShellPrintEx (-1, -1,
4367 L" Hot-Plug Capable(6): %E%d%N\r\n",
4368 PCIE_CAP_HOTPLUG_CAPABLE (PcieSlotCap)
4369 );
4370 ShellPrintEx (-1, -1,
4371 L" Slot Power Limit Value(14:7): %E0x%02x%N\r\n",
4372 PCIE_CAP_SLOT_PWR_LIMIT_VALUE (PcieSlotCap)
4373 );
4374 ShellPrintEx (-1, -1,
4375 L" Slot Power Limit Scale(16:15): %E%s%N\r\n",
4376 SlotPwrLmtScaleTable[PCIE_CAP_SLOT_PWR_LIMIT_SCALE (PcieSlotCap)]
4377 );
4378 ShellPrintEx (-1, -1,
4379 L" Electromechanical Interlock Present(17): %E%d%N\r\n",
4380 PCIE_CAP_ELEC_INTERLOCK_PRESENT (PcieSlotCap)
4381 );
4382 ShellPrintEx (-1, -1,
4383 L" No Command Completed Support(18): %E%d%N\r\n",
4384 PCIE_CAP_NO_COMM_COMPLETED_SUP (PcieSlotCap)
4385 );
4386 ShellPrintEx (-1, -1,
4387 L" Physical Slot Number(31:19): %E%d%N\r\n",
4388 PCIE_CAP_PHY_SLOT_NUM (PcieSlotCap)
4389 );
4390
4391 return EFI_SUCCESS;
4392 }
4393
4394 /**
4395 Print out information of the device slot control information.
4396
4397 @param[in] PciExpressCap The pointer to the structure about the device.
4398
4399 @retval EFI_SUCCESS The operation was successful.
4400 **/
4401 EFI_STATUS
4402 ExplainPcieSlotControl (
4403 IN PCIE_CAP_STURCTURE *PciExpressCap
4404 )
4405 {
4406 UINT16 PcieSlotControl;
4407
4408 PcieSlotControl = PciExpressCap->SlotControl;
4409 ShellPrintEx (-1, -1,
4410 L" Attention Button Pressed Enable(0): %E%d%N\r\n",
4411 PCIE_CAP_ATT_BUT_ENABLE (PcieSlotControl)
4412 );
4413 ShellPrintEx (-1, -1,
4414 L" Power Fault Detected Enable(1): %E%d%N\r\n",
4415 PCIE_CAP_PWR_FLT_DETECT_ENABLE (PcieSlotControl)
4416 );
4417 ShellPrintEx (-1, -1,
4418 L" MRL Sensor Changed Enable(2): %E%d%N\r\n",
4419 PCIE_CAP_MRL_SENSOR_CHANGE_ENABLE (PcieSlotControl)
4420 );
4421 ShellPrintEx (-1, -1,
4422 L" Presence Detect Changed Enable(3): %E%d%N\r\n",
4423 PCIE_CAP_PRES_DETECT_CHANGE_ENABLE (PcieSlotControl)
4424 );
4425 ShellPrintEx (-1, -1,
4426 L" Command Completed Interrupt Enable(4): %E%d%N\r\n",
4427 PCIE_CAP_COMM_CMPL_INT_ENABLE (PcieSlotControl)
4428 );
4429 ShellPrintEx (-1, -1,
4430 L" Hot-Plug Interrupt Enable(5): %E%d%N\r\n",
4431 PCIE_CAP_HOTPLUG_INT_ENABLE (PcieSlotControl)
4432 );
4433 ShellPrintEx (-1, -1,
4434 L" Attention Indicator Control(7:6): %E%s%N\r\n",
4435 IndicatorTable[PCIE_CAP_ATT_IND_CTRL (PcieSlotControl)]
4436 );
4437 ShellPrintEx (-1, -1,
4438 L" Power Indicator Control(9:8): %E%s%N\r\n",
4439 IndicatorTable[PCIE_CAP_PWR_IND_CTRL (PcieSlotControl)]
4440 );
4441 ShellPrintEx (-1, -1, L" Power Controller Control(10): %EPower ");
4442 if (PCIE_CAP_PWR_CTRLLER_CTRL (PcieSlotControl)) {
4443 ShellPrintEx (-1, -1, L"Off%N\r\n");
4444 } else {
4445 ShellPrintEx (-1, -1, L"On%N\r\n");
4446 }
4447 ShellPrintEx (-1, -1,
4448 L" Electromechanical Interlock Control(11): %E%d%N\r\n",
4449 PCIE_CAP_ELEC_INTERLOCK_CTRL (PcieSlotControl)
4450 );
4451 ShellPrintEx (-1, -1,
4452 L" Data Link Layer State Changed Enable(12): %E%d%N\r\n",
4453 PCIE_CAP_DLINK_STAT_CHANGE_ENABLE (PcieSlotControl)
4454 );
4455 return EFI_SUCCESS;
4456 }
4457
4458 /**
4459 Print out information of the device slot status information.
4460
4461 @param[in] PciExpressCap The pointer to the structure about the device.
4462
4463 @retval EFI_SUCCESS The operation was successful.
4464 **/
4465 EFI_STATUS
4466 ExplainPcieSlotStatus (
4467 IN PCIE_CAP_STURCTURE *PciExpressCap
4468 )
4469 {
4470 UINT16 PcieSlotStatus;
4471
4472 PcieSlotStatus = PciExpressCap->SlotStatus;
4473
4474 ShellPrintEx (-1, -1,
4475 L" Attention Button Pressed(0): %E%d%N\r\n",
4476 PCIE_CAP_ATT_BUT_PRESSED (PcieSlotStatus)
4477 );
4478 ShellPrintEx (-1, -1,
4479 L" Power Fault Detected(1): %E%d%N\r\n",
4480 PCIE_CAP_PWR_FLT_DETECTED (PcieSlotStatus)
4481 );
4482 ShellPrintEx (-1, -1,
4483 L" MRL Sensor Changed(2): %E%d%N\r\n",
4484 PCIE_CAP_MRL_SENSOR_CHANGED (PcieSlotStatus)
4485 );
4486 ShellPrintEx (-1, -1,
4487 L" Presence Detect Changed(3): %E%d%N\r\n",
4488 PCIE_CAP_PRES_DETECT_CHANGED (PcieSlotStatus)
4489 );
4490 ShellPrintEx (-1, -1,
4491 L" Command Completed(4): %E%d%N\r\n",
4492 PCIE_CAP_COMM_COMPLETED (PcieSlotStatus)
4493 );
4494 ShellPrintEx (-1, -1, L" MRL Sensor State(5): %EMRL ");
4495 if (PCIE_CAP_MRL_SENSOR_STATE (PcieSlotStatus)) {
4496 ShellPrintEx (-1, -1, L" Opened%N\r\n");
4497 } else {
4498 ShellPrintEx (-1, -1, L" Closed%N\r\n");
4499 }
4500 ShellPrintEx (-1, -1, L" Presence Detect State(6): ");
4501 if (PCIE_CAP_PRES_DETECT_STATE (PcieSlotStatus)) {
4502 ShellPrintEx (-1, -1, L"%ECard Present in slot%N\r\n");
4503 } else {
4504 ShellPrintEx (-1, -1, L"%ESlot Empty%N\r\n");
4505 }
4506 ShellPrintEx (-1, -1, L" Electromechanical Interlock Status(7): %EElectromechanical Interlock ");
4507 if (PCIE_CAP_ELEC_INTERLOCK_STATE (PcieSlotStatus)) {
4508 ShellPrintEx (-1, -1, L"Engaged%N\r\n");
4509 } else {
4510 ShellPrintEx (-1, -1, L"Disengaged%N\r\n");
4511 }
4512 ShellPrintEx (-1, -1,
4513 L" Data Link Layer State Changed(8): %E%d%N\r\n",
4514 PCIE_CAP_DLINK_STAT_CHANGED (PcieSlotStatus)
4515 );
4516 return EFI_SUCCESS;
4517 }
4518
4519 /**
4520 Print out information of the device root information.
4521
4522 @param[in] PciExpressCap The pointer to the structure about the device.
4523
4524 @retval EFI_SUCCESS The operation was successful.
4525 **/
4526 EFI_STATUS
4527 ExplainPcieRootControl (
4528 IN PCIE_CAP_STURCTURE *PciExpressCap
4529 )
4530 {
4531 UINT16 PcieRootControl;
4532
4533 PcieRootControl = PciExpressCap->RootControl;
4534
4535 ShellPrintEx (-1, -1,
4536 L" System Error on Correctable Error Enable(0): %E%d%N\r\n",
4537 PCIE_CAP_SYSERR_ON_CORERR_EN (PcieRootControl)
4538 );
4539 ShellPrintEx (-1, -1,
4540 L" System Error on Non-Fatal Error Enable(1): %E%d%N\r\n",
4541 PCIE_CAP_SYSERR_ON_NONFATERR_EN (PcieRootControl)
4542 );
4543 ShellPrintEx (-1, -1,
4544 L" System Error on Fatal Error Enable(2): %E%d%N\r\n",
4545 PCIE_CAP_SYSERR_ON_FATERR_EN (PcieRootControl)
4546 );
4547 ShellPrintEx (-1, -1,
4548 L" PME Interrupt Enable(3): %E%d%N\r\n",
4549 PCIE_CAP_PME_INT_ENABLE (PcieRootControl)
4550 );
4551 ShellPrintEx (-1, -1,
4552 L" CRS Software Visibility Enable(4): %E%d%N\r\n",
4553 PCIE_CAP_CRS_SW_VIS_ENABLE (PcieRootControl)
4554 );
4555
4556 return EFI_SUCCESS;
4557 }
4558
4559 /**
4560 Print out information of the device root capability information.
4561
4562 @param[in] PciExpressCap The pointer to the structure about the device.
4563
4564 @retval EFI_SUCCESS The operation was successful.
4565 **/
4566 EFI_STATUS
4567 ExplainPcieRootCap (
4568 IN PCIE_CAP_STURCTURE *PciExpressCap
4569 )
4570 {
4571 UINT16 PcieRootCap;
4572
4573 PcieRootCap = PciExpressCap->RsvdP;
4574
4575 ShellPrintEx (-1, -1,
4576 L" CRS Software Visibility(0): %E%d%N\r\n",
4577 PCIE_CAP_CRS_SW_VIS (PcieRootCap)
4578 );
4579
4580 return EFI_SUCCESS;
4581 }
4582
4583 /**
4584 Print out information of the device root status information.
4585
4586 @param[in] PciExpressCap The pointer to the structure about the device.
4587
4588 @retval EFI_SUCCESS The operation was successful.
4589 **/
4590 EFI_STATUS
4591 ExplainPcieRootStatus (
4592 IN PCIE_CAP_STURCTURE *PciExpressCap
4593 )
4594 {
4595 UINT32 PcieRootStatus;
4596
4597 PcieRootStatus = PciExpressCap->RootStatus;
4598
4599 ShellPrintEx (-1, -1,
4600 L" PME Requester ID(15:0): %E0x%04x%N\r\n",
4601 PCIE_CAP_PME_REQ_ID (PcieRootStatus)
4602 );
4603 ShellPrintEx (-1, -1,
4604 L" PME Status(16): %E%d%N\r\n",
4605 PCIE_CAP_PME_STATUS (PcieRootStatus)
4606 );
4607 ShellPrintEx (-1, -1,
4608 L" PME Pending(17): %E%d%N\r\n",
4609 PCIE_CAP_PME_PENDING (PcieRootStatus)
4610 );
4611 return EFI_SUCCESS;
4612 }
4613
4614 /**
4615 Function to interpret and print out the link control structure
4616
4617 @param[in] HeaderAddress The Address of this capability header.
4618 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4619 **/
4620 EFI_STATUS
4621 EFIAPI
4622 PrintInterpretedExtendedCompatibilityLinkControl (
4623 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4624 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4625 )
4626 {
4627 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_INTERNAL_LINK_CONTROL *Header;
4628 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_INTERNAL_LINK_CONTROL*)HeaderAddress;
4629
4630 ShellPrintHiiEx(
4631 -1, -1, NULL,
4632 STRING_TOKEN (STR_PCI_EXT_CAP_LINK_CONTROL),
4633 gShellDebug1HiiHandle,
4634 Header->RootComplexLinkCapabilities,
4635 Header->RootComplexLinkControl,
4636 Header->RootComplexLinkStatus
4637 );
4638 DumpHex (
4639 4,
4640 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4641 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_INTERNAL_LINK_CONTROL),
4642 (VOID *) (HeaderAddress)
4643 );
4644 return (EFI_SUCCESS);
4645 }
4646
4647 /**
4648 Function to interpret and print out the power budgeting structure
4649
4650 @param[in] HeaderAddress The Address of this capability header.
4651 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4652 **/
4653 EFI_STATUS
4654 EFIAPI
4655 PrintInterpretedExtendedCompatibilityPowerBudgeting (
4656 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4657 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4658 )
4659 {
4660 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_POWER_BUDGETING *Header;
4661 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_POWER_BUDGETING*)HeaderAddress;
4662
4663 ShellPrintHiiEx(
4664 -1, -1, NULL,
4665 STRING_TOKEN (STR_PCI_EXT_CAP_POWER),
4666 gShellDebug1HiiHandle,
4667 Header->DataSelect,
4668 Header->Data,
4669 Header->PowerBudgetCapability
4670 );
4671 DumpHex (
4672 4,
4673 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4674 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_POWER_BUDGETING),
4675 (VOID *) (HeaderAddress)
4676 );
4677 return (EFI_SUCCESS);
4678 }
4679
4680 /**
4681 Function to interpret and print out the ACS structure
4682
4683 @param[in] HeaderAddress The Address of this capability header.
4684 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4685 **/
4686 EFI_STATUS
4687 EFIAPI
4688 PrintInterpretedExtendedCompatibilityAcs (
4689 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4690 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4691 )
4692 {
4693 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_ACS_EXTENDED *Header;
4694 UINT16 VectorSize;
4695 UINT16 LoopCounter;
4696
4697 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_ACS_EXTENDED*)HeaderAddress;
4698 VectorSize = 0;
4699
4700 ShellPrintHiiEx(
4701 -1, -1, NULL,
4702 STRING_TOKEN (STR_PCI_EXT_CAP_ACS),
4703 gShellDebug1HiiHandle,
4704 Header->AcsCapability,
4705 Header->AcsControl
4706 );
4707 if (PCI_EXPRESS_EXTENDED_CAPABILITY_ACS_EXTENDED_GET_EGRES_CONTROL(Header)) {
4708 VectorSize = PCI_EXPRESS_EXTENDED_CAPABILITY_ACS_EXTENDED_GET_EGRES_VECTOR_SIZE(Header);
4709 if (VectorSize == 0) {
4710 VectorSize = 256;
4711 }
4712 for (LoopCounter = 0 ; LoopCounter * 8 < VectorSize ; LoopCounter++) {
4713 ShellPrintHiiEx(
4714 -1, -1, NULL,
4715 STRING_TOKEN (STR_PCI_EXT_CAP_ACS2),
4716 gShellDebug1HiiHandle,
4717 LoopCounter + 1,
4718 Header->EgressControlVectorArray[LoopCounter]
4719 );
4720 }
4721 }
4722 DumpHex (
4723 4,
4724 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4725 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_ACS_EXTENDED) + (VectorSize / 8) - 1,
4726 (VOID *) (HeaderAddress)
4727 );
4728 return (EFI_SUCCESS);
4729 }
4730
4731 /**
4732 Function to interpret and print out the latency tolerance reporting structure
4733
4734 @param[in] HeaderAddress The Address of this capability header.
4735 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4736 **/
4737 EFI_STATUS
4738 EFIAPI
4739 PrintInterpretedExtendedCompatibilityLatencyToleranceReporting (
4740 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4741 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4742 )
4743 {
4744 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_LATENCE_TOLERANCE_REPORTING *Header;
4745 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_LATENCE_TOLERANCE_REPORTING*)HeaderAddress;
4746
4747 ShellPrintHiiEx(
4748 -1, -1, NULL,
4749 STRING_TOKEN (STR_PCI_EXT_CAP_LAT),
4750 gShellDebug1HiiHandle,
4751 Header->MaxSnoopLatency,
4752 Header->MaxNoSnoopLatency
4753 );
4754 DumpHex (
4755 4,
4756 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4757 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_LATENCE_TOLERANCE_REPORTING),
4758 (VOID *) (HeaderAddress)
4759 );
4760 return (EFI_SUCCESS);
4761 }
4762
4763 /**
4764 Function to interpret and print out the serial number structure
4765
4766 @param[in] HeaderAddress The Address of this capability header.
4767 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4768 **/
4769 EFI_STATUS
4770 EFIAPI
4771 PrintInterpretedExtendedCompatibilitySerialNumber (
4772 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4773 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4774 )
4775 {
4776 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_SERIAL_NUMBER *Header;
4777 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_SERIAL_NUMBER*)HeaderAddress;
4778
4779 ShellPrintHiiEx(
4780 -1, -1, NULL,
4781 STRING_TOKEN (STR_PCI_EXT_CAP_SN),
4782 gShellDebug1HiiHandle,
4783 Header->SerialNumber
4784 );
4785 DumpHex (
4786 4,
4787 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4788 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_SERIAL_NUMBER),
4789 (VOID *) (HeaderAddress)
4790 );
4791 return (EFI_SUCCESS);
4792 }
4793
4794 /**
4795 Function to interpret and print out the RCRB structure
4796
4797 @param[in] HeaderAddress The Address of this capability header.
4798 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4799 **/
4800 EFI_STATUS
4801 EFIAPI
4802 PrintInterpretedExtendedCompatibilityRcrb (
4803 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4804 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4805 )
4806 {
4807 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_RCRB_HEADER *Header;
4808 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_RCRB_HEADER*)HeaderAddress;
4809
4810 ShellPrintHiiEx(
4811 -1, -1, NULL,
4812 STRING_TOKEN (STR_PCI_EXT_CAP_RCRB),
4813 gShellDebug1HiiHandle,
4814 Header->VendorId,
4815 Header->DeviceId,
4816 Header->RcrbCapabilities,
4817 Header->RcrbControl
4818 );
4819 DumpHex (
4820 4,
4821 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4822 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_RCRB_HEADER),
4823 (VOID *) (HeaderAddress)
4824 );
4825 return (EFI_SUCCESS);
4826 }
4827
4828 /**
4829 Function to interpret and print out the vendor specific structure
4830
4831 @param[in] HeaderAddress The Address of this capability header.
4832 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4833 **/
4834 EFI_STATUS
4835 EFIAPI
4836 PrintInterpretedExtendedCompatibilityVendorSpecific (
4837 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4838 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4839 )
4840 {
4841 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_VENDOR_SPECIFIC *Header;
4842 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_VENDOR_SPECIFIC*)HeaderAddress;
4843
4844 ShellPrintHiiEx(
4845 -1, -1, NULL,
4846 STRING_TOKEN (STR_PCI_EXT_CAP_VEN),
4847 gShellDebug1HiiHandle,
4848 Header->VendorSpecificHeader
4849 );
4850 DumpHex (
4851 4,
4852 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4853 PCI_EXPRESS_EXTENDED_CAPABILITY_VENDOR_SPECIFIC_GET_SIZE(Header),
4854 (VOID *) (HeaderAddress)
4855 );
4856 return (EFI_SUCCESS);
4857 }
4858
4859 /**
4860 Function to interpret and print out the Event Collector Endpoint Association structure
4861
4862 @param[in] HeaderAddress The Address of this capability header.
4863 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4864 **/
4865 EFI_STATUS
4866 EFIAPI
4867 PrintInterpretedExtendedCompatibilityECEA (
4868 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4869 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4870 )
4871 {
4872 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_EVENT_COLLECTOR_ENDPOINT_ASSOCIATION *Header;
4873 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_EVENT_COLLECTOR_ENDPOINT_ASSOCIATION*)HeaderAddress;
4874
4875 ShellPrintHiiEx(
4876 -1, -1, NULL,
4877 STRING_TOKEN (STR_PCI_EXT_CAP_ECEA),
4878 gShellDebug1HiiHandle,
4879 Header->AssociationBitmap
4880 );
4881 DumpHex (
4882 4,
4883 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4884 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_EVENT_COLLECTOR_ENDPOINT_ASSOCIATION),
4885 (VOID *) (HeaderAddress)
4886 );
4887 return (EFI_SUCCESS);
4888 }
4889
4890 /**
4891 Function to interpret and print out the ARI structure
4892
4893 @param[in] HeaderAddress The Address of this capability header.
4894 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4895 **/
4896 EFI_STATUS
4897 EFIAPI
4898 PrintInterpretedExtendedCompatibilityAri (
4899 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4900 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4901 )
4902 {
4903 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_ARI_CAPABILITY *Header;
4904 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_ARI_CAPABILITY*)HeaderAddress;
4905
4906 ShellPrintHiiEx(
4907 -1, -1, NULL,
4908 STRING_TOKEN (STR_PCI_EXT_CAP_ARI),
4909 gShellDebug1HiiHandle,
4910 Header->AriCapability,
4911 Header->AriControl
4912 );
4913 DumpHex (
4914 4,
4915 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4916 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_ARI_CAPABILITY),
4917 (VOID *) (HeaderAddress)
4918 );
4919 return (EFI_SUCCESS);
4920 }
4921
4922 /**
4923 Function to interpret and print out the DPA structure
4924
4925 @param[in] HeaderAddress The Address of this capability header.
4926 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4927 **/
4928 EFI_STATUS
4929 EFIAPI
4930 PrintInterpretedExtendedCompatibilityDynamicPowerAllocation (
4931 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4932 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4933 )
4934 {
4935 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_DYNAMIC_POWER_ALLOCATION *Header;
4936 UINT8 LinkCount;
4937 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_DYNAMIC_POWER_ALLOCATION*)HeaderAddress;
4938
4939 ShellPrintHiiEx(
4940 -1, -1, NULL,
4941 STRING_TOKEN (STR_PCI_EXT_CAP_DPA),
4942 gShellDebug1HiiHandle,
4943 Header->DpaCapability,
4944 Header->DpaLatencyIndicator,
4945 Header->DpaStatus,
4946 Header->DpaControl
4947 );
4948 for (LinkCount = 0 ; LinkCount < PCI_EXPRESS_EXTENDED_CAPABILITY_DYNAMIC_POWER_ALLOCATION_GET_SUBSTATE_MAX(Header) + 1 ; LinkCount++) {
4949 ShellPrintHiiEx(
4950 -1, -1, NULL,
4951 STRING_TOKEN (STR_PCI_EXT_CAP_DPA2),
4952 gShellDebug1HiiHandle,
4953 LinkCount+1,
4954 Header->DpaPowerAllocationArray[LinkCount]
4955 );
4956 }
4957 DumpHex (
4958 4,
4959 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
4960 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_DYNAMIC_POWER_ALLOCATION) - 1 + PCI_EXPRESS_EXTENDED_CAPABILITY_DYNAMIC_POWER_ALLOCATION_GET_SUBSTATE_MAX(Header),
4961 (VOID *) (HeaderAddress)
4962 );
4963 return (EFI_SUCCESS);
4964 }
4965
4966 /**
4967 Function to interpret and print out the link declaration structure
4968
4969 @param[in] HeaderAddress The Address of this capability header.
4970 @param[in] HeadersBaseAddress The address of all the extended capability headers.
4971 **/
4972 EFI_STATUS
4973 EFIAPI
4974 PrintInterpretedExtendedCompatibilityLinkDeclaration (
4975 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
4976 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
4977 )
4978 {
4979 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_LINK_DECLARATION *Header;
4980 UINT8 LinkCount;
4981 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_LINK_DECLARATION*)HeaderAddress;
4982
4983 ShellPrintHiiEx(
4984 -1, -1, NULL,
4985 STRING_TOKEN (STR_PCI_EXT_CAP_LINK_DECLAR),
4986 gShellDebug1HiiHandle,
4987 Header->ElementSelfDescription
4988 );
4989
4990 for (LinkCount = 0 ; LinkCount < PCI_EXPRESS_EXTENDED_CAPABILITY_LINK_DECLARATION_GET_LINK_COUNT(Header) ; LinkCount++) {
4991 ShellPrintHiiEx(
4992 -1, -1, NULL,
4993 STRING_TOKEN (STR_PCI_EXT_CAP_LINK_DECLAR2),
4994 gShellDebug1HiiHandle,
4995 LinkCount+1,
4996 Header->LinkEntry[LinkCount]
4997 );
4998 }
4999 DumpHex (
5000 4,
5001 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
5002 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_LINK_DECLARATION) + (PCI_EXPRESS_EXTENDED_CAPABILITY_LINK_DECLARATION_GET_LINK_COUNT(Header)-1)*sizeof(UINT32),
5003 (VOID *) (HeaderAddress)
5004 );
5005 return (EFI_SUCCESS);
5006 }
5007
5008 /**
5009 Function to interpret and print out the Advanced Error Reporting structure
5010
5011 @param[in] HeaderAddress The Address of this capability header.
5012 @param[in] HeadersBaseAddress The address of all the extended capability headers.
5013 **/
5014 EFI_STATUS
5015 EFIAPI
5016 PrintInterpretedExtendedCompatibilityAer (
5017 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
5018 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
5019 )
5020 {
5021 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_ADVANCED_ERROR_REPORTING *Header;
5022 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_ADVANCED_ERROR_REPORTING*)HeaderAddress;
5023
5024 ShellPrintHiiEx(
5025 -1, -1, NULL,
5026 STRING_TOKEN (STR_PCI_EXT_CAP_AER),
5027 gShellDebug1HiiHandle,
5028 Header->UncorrectableErrorStatus,
5029 Header->UncorrectableErrorMask,
5030 Header->UncorrectableErrorSeverity,
5031 Header->CorrectableErrorStatus,
5032 Header->CorrectableErrorMask,
5033 Header->AdvancedErrorCapabilitiesAndControl,
5034 Header->HeaderLog,
5035 Header->RootErrorCommand,
5036 Header->RootErrorStatus,
5037 Header->ErrorSourceIdentification,
5038 Header->CorrectableErrorSourceIdentification,
5039 Header->TlpPrefixLog[0],
5040 Header->TlpPrefixLog[1],
5041 Header->TlpPrefixLog[2],
5042 Header->TlpPrefixLog[3]
5043 );
5044 DumpHex (
5045 4,
5046 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
5047 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_ADVANCED_ERROR_REPORTING),
5048 (VOID *) (HeaderAddress)
5049 );
5050 return (EFI_SUCCESS);
5051 }
5052
5053 /**
5054 Function to interpret and print out the multicast structure
5055
5056 @param[in] HeaderAddress The Address of this capability header.
5057 @param[in] HeadersBaseAddress The address of all the extended capability headers.
5058 @param[in] PciExpressCapPtr The address of the PCIe capabilities structure.
5059 **/
5060 EFI_STATUS
5061 EFIAPI
5062 PrintInterpretedExtendedCompatibilityMulticast (
5063 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
5064 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress,
5065 IN CONST PCIE_CAP_STURCTURE *PciExpressCapPtr
5066 )
5067 {
5068 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_MULTICAST *Header;
5069 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_MULTICAST*)HeaderAddress;
5070
5071 ShellPrintHiiEx(
5072 -1, -1, NULL,
5073 STRING_TOKEN (STR_PCI_EXT_CAP_MULTICAST),
5074 gShellDebug1HiiHandle,
5075 Header->MultiCastCapability,
5076 Header->MulticastControl,
5077 Header->McBaseAddress,
5078 Header->McReceiveAddress,
5079 Header->McBlockAll,
5080 Header->McBlockUntranslated,
5081 Header->McOverlayBar
5082 );
5083
5084 DumpHex (
5085 4,
5086 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
5087 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_MULTICAST),
5088 (VOID *) (HeaderAddress)
5089 );
5090
5091 return (EFI_SUCCESS);
5092 }
5093
5094 /**
5095 Function to interpret and print out the virtual channel and multi virtual channel structure
5096
5097 @param[in] HeaderAddress The Address of this capability header.
5098 @param[in] HeadersBaseAddress The address of all the extended capability headers.
5099 **/
5100 EFI_STATUS
5101 EFIAPI
5102 PrintInterpretedExtendedCompatibilityVirtualChannel (
5103 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
5104 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
5105 )
5106 {
5107 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_VIRTUAL_CHANNEL_CAPABILITY *Header;
5108 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_VIRTUAL_CHANNEL_VC *CapabilityItem;
5109 UINT32 ItemCount;
5110 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_VIRTUAL_CHANNEL_CAPABILITY*)HeaderAddress;
5111
5112 ShellPrintHiiEx(
5113 -1, -1, NULL,
5114 STRING_TOKEN (STR_PCI_EXT_CAP_VC_BASE),
5115 gShellDebug1HiiHandle,
5116 Header->ExtendedVcCount,
5117 Header->PortVcCapability1,
5118 Header->PortVcCapability2,
5119 Header->VcArbTableOffset,
5120 Header->PortVcControl,
5121 Header->PortVcStatus
5122 );
5123 for (ItemCount = 0 ; ItemCount < Header->ExtendedVcCount ; ItemCount++) {
5124 CapabilityItem = &Header->Capability[ItemCount];
5125 ShellPrintHiiEx(
5126 -1, -1, NULL,
5127 STRING_TOKEN (STR_PCI_EXT_CAP_VC_ITEM),
5128 gShellDebug1HiiHandle,
5129 ItemCount+1,
5130 CapabilityItem->VcResourceCapability,
5131 CapabilityItem->PortArbTableOffset,
5132 CapabilityItem->VcResourceControl,
5133 CapabilityItem->VcResourceStatus
5134 );
5135 }
5136
5137 DumpHex (
5138 4,
5139 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
5140 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_VIRTUAL_CHANNEL_VC) + (Header->ExtendedVcCount - 1) * sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_VIRTUAL_CHANNEL_CAPABILITY),
5141 (VOID *) (HeaderAddress)
5142 );
5143
5144 return (EFI_SUCCESS);
5145 }
5146
5147 /**
5148 Function to interpret and print out the resizeable bar structure
5149
5150 @param[in] HeaderAddress The Address of this capability header.
5151 @param[in] HeadersBaseAddress The address of all the extended capability headers.
5152 **/
5153 EFI_STATUS
5154 EFIAPI
5155 PrintInterpretedExtendedCompatibilityResizeableBar (
5156 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
5157 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
5158 )
5159 {
5160 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_RESIZABLE_BAR *Header;
5161 UINT32 ItemCount;
5162 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_RESIZABLE_BAR*)HeaderAddress;
5163
5164 for (ItemCount = 0 ; ItemCount < (UINT32)GET_NUMBER_RESIZABLE_BARS(Header) ; ItemCount++) {
5165 ShellPrintHiiEx(
5166 -1, -1, NULL,
5167 STRING_TOKEN (STR_PCI_EXT_CAP_RESIZE_BAR),
5168 gShellDebug1HiiHandle,
5169 ItemCount+1,
5170 Header->Capability[ItemCount].ResizableBarCapability,
5171 Header->Capability[ItemCount].ResizableBarControl
5172 );
5173 }
5174
5175 DumpHex (
5176 4,
5177 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
5178 (UINT32)GET_NUMBER_RESIZABLE_BARS(Header) * sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_RESIZABLE_BAR_ENTRY),
5179 (VOID *) (HeaderAddress)
5180 );
5181
5182 return (EFI_SUCCESS);
5183 }
5184
5185 /**
5186 Function to interpret and print out the TPH structure
5187
5188 @param[in] HeaderAddress The Address of this capability header.
5189 @param[in] HeadersBaseAddress The address of all the extended capability headers.
5190 **/
5191 EFI_STATUS
5192 EFIAPI
5193 PrintInterpretedExtendedCompatibilityTph (
5194 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
5195 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress
5196 )
5197 {
5198 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_TPH *Header;
5199 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_TPH*)HeaderAddress;
5200
5201 ShellPrintHiiEx(
5202 -1, -1, NULL,
5203 STRING_TOKEN (STR_PCI_EXT_CAP_TPH),
5204 gShellDebug1HiiHandle,
5205 Header->TphRequesterCapability,
5206 Header->TphRequesterControl
5207 );
5208 DumpHex (
5209 8,
5210 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)Header->TphStTable - (UINT8*)HeadersBaseAddress),
5211 GET_TPH_TABLE_SIZE(Header),
5212 (VOID *)Header->TphStTable
5213 );
5214
5215 DumpHex (
5216 4,
5217 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
5218 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_TPH) + GET_TPH_TABLE_SIZE(Header) - sizeof(UINT16),
5219 (VOID *) (HeaderAddress)
5220 );
5221
5222 return (EFI_SUCCESS);
5223 }
5224
5225 /**
5226 Function to interpret and print out the secondary PCIe capability structure
5227
5228 @param[in] HeaderAddress The Address of this capability header.
5229 @param[in] HeadersBaseAddress The address of all the extended capability headers.
5230 @param[in] PciExpressCapPtr The address of the PCIe capabilities structure.
5231 **/
5232 EFI_STATUS
5233 EFIAPI
5234 PrintInterpretedExtendedCompatibilitySecondary (
5235 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
5236 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress,
5237 IN CONST PCIE_CAP_STURCTURE *PciExpressCapPtr
5238 )
5239 {
5240 CONST PCI_EXPRESS_EXTENDED_CAPABILITIES_SECONDARY_PCIE *Header;
5241 Header = (PCI_EXPRESS_EXTENDED_CAPABILITIES_SECONDARY_PCIE*)HeaderAddress;
5242
5243 ShellPrintHiiEx(
5244 -1, -1, NULL,
5245 STRING_TOKEN (STR_PCI_EXT_CAP_SECONDARY),
5246 gShellDebug1HiiHandle,
5247 Header->LinkControl3,
5248 Header->LaneErrorStatus
5249 );
5250 DumpHex (
5251 8,
5252 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)Header->EqualizationControl - (UINT8*)HeadersBaseAddress),
5253 PCIE_CAP_MAX_LINK_WIDTH(PciExpressCapPtr->LinkCap),
5254 (VOID *)Header->EqualizationControl
5255 );
5256
5257 DumpHex (
5258 4,
5259 EFI_PCIE_CAPABILITY_BASE_OFFSET + ((UINT8*)HeaderAddress - (UINT8*)HeadersBaseAddress),
5260 sizeof(PCI_EXPRESS_EXTENDED_CAPABILITIES_TPH) - sizeof(Header->EqualizationControl) + PCIE_CAP_MAX_LINK_WIDTH(PciExpressCapPtr->LinkCap),
5261 (VOID *) (HeaderAddress)
5262 );
5263
5264 return (EFI_SUCCESS);
5265 }
5266
5267 /**
5268 Display Pcie extended capability details
5269
5270 @param[in] HeadersBaseAddress The address of all the extended capability headers.
5271 @param[in] HeaderAddress The address of this capability header.
5272 @param[in] PciExpressCapPtr The address of the PCIe capabilities structure.
5273 **/
5274 EFI_STATUS
5275 EFIAPI
5276 PrintPciExtendedCapabilityDetails(
5277 IN CONST PCI_EXP_EXT_HDR *HeadersBaseAddress,
5278 IN CONST PCI_EXP_EXT_HDR *HeaderAddress,
5279 IN CONST PCIE_CAP_STURCTURE *PciExpressCapPtr
5280 )
5281 {
5282 switch (HeaderAddress->CapabilityId){
5283 case PCI_EXPRESS_EXTENDED_CAPABILITY_ADVANCED_ERROR_REPORTING_ID:
5284 return PrintInterpretedExtendedCompatibilityAer(HeaderAddress, HeadersBaseAddress);
5285 case PCI_EXPRESS_EXTENDED_CAPABILITY_LINK_CONTROL_ID:
5286 return PrintInterpretedExtendedCompatibilityLinkControl(HeaderAddress, HeadersBaseAddress);
5287 case PCI_EXPRESS_EXTENDED_CAPABILITY_LINK_DECLARATION_ID:
5288 return PrintInterpretedExtendedCompatibilityLinkDeclaration(HeaderAddress, HeadersBaseAddress);
5289 case PCI_EXPRESS_EXTENDED_CAPABILITY_SERIAL_NUMBER_ID:
5290 return PrintInterpretedExtendedCompatibilitySerialNumber(HeaderAddress, HeadersBaseAddress);
5291 case PCI_EXPRESS_EXTENDED_CAPABILITY_POWER_BUDGETING_ID:
5292 return PrintInterpretedExtendedCompatibilityPowerBudgeting(HeaderAddress, HeadersBaseAddress);
5293 case PCI_EXPRESS_EXTENDED_CAPABILITY_ACS_EXTENDED_ID:
5294 return PrintInterpretedExtendedCompatibilityAcs(HeaderAddress, HeadersBaseAddress);
5295 case PCI_EXPRESS_EXTENDED_CAPABILITY_LATENCE_TOLERANCE_REPORTING_ID:
5296 return PrintInterpretedExtendedCompatibilityLatencyToleranceReporting(HeaderAddress, HeadersBaseAddress);
5297 case PCI_EXPRESS_EXTENDED_CAPABILITY_ARI_CAPABILITY_ID:
5298 return PrintInterpretedExtendedCompatibilityAri(HeaderAddress, HeadersBaseAddress);
5299 case PCI_EXPRESS_EXTENDED_CAPABILITY_RCRB_HEADER_ID:
5300 return PrintInterpretedExtendedCompatibilityRcrb(HeaderAddress, HeadersBaseAddress);
5301 case PCI_EXPRESS_EXTENDED_CAPABILITY_VENDOR_SPECIFIC_ID:
5302 return PrintInterpretedExtendedCompatibilityVendorSpecific(HeaderAddress, HeadersBaseAddress);
5303 case PCI_EXPRESS_EXTENDED_CAPABILITY_DYNAMIC_POWER_ALLOCATION_ID:
5304 return PrintInterpretedExtendedCompatibilityDynamicPowerAllocation(HeaderAddress, HeadersBaseAddress);
5305 case PCI_EXPRESS_EXTENDED_CAPABILITY_EVENT_COLLECTOR_ENDPOINT_ASSOCIATION_ID:
5306 return PrintInterpretedExtendedCompatibilityECEA(HeaderAddress, HeadersBaseAddress);
5307 case PCI_EXPRESS_EXTENDED_CAPABILITY_VIRTUAL_CHANNEL_ID:
5308 case PCI_EXPRESS_EXTENDED_CAPABILITY_MULTI_FUNCTION_VIRTUAL_CHANNEL_ID:
5309 return PrintInterpretedExtendedCompatibilityVirtualChannel(HeaderAddress, HeadersBaseAddress);
5310 case PCI_EXPRESS_EXTENDED_CAPABILITY_MULTICAST_ID:
5311 //
5312 // should only be present if PCIE_CAP_DEVICEPORT_TYPE(PciExpressCapPtr->PcieCapReg) == 0100b, 0101b, or 0110b
5313 //
5314 return PrintInterpretedExtendedCompatibilityMulticast(HeaderAddress, HeadersBaseAddress, PciExpressCapPtr);
5315 case PCI_EXPRESS_EXTENDED_CAPABILITY_RESIZABLE_BAR_ID:
5316 return PrintInterpretedExtendedCompatibilityResizeableBar(HeaderAddress, HeadersBaseAddress);
5317 case PCI_EXPRESS_EXTENDED_CAPABILITY_TPH_ID:
5318 return PrintInterpretedExtendedCompatibilityTph(HeaderAddress, HeadersBaseAddress);
5319 case PCI_EXPRESS_EXTENDED_CAPABILITY_SECONDARY_PCIE_ID:
5320 return PrintInterpretedExtendedCompatibilitySecondary(HeaderAddress, HeadersBaseAddress, PciExpressCapPtr);
5321 default:
5322 ShellPrintEx (-1, -1,
5323 L"Unknown PCIe extended capability ID (%04xh). No interpretation available.\r\n",
5324 HeaderAddress->CapabilityId
5325 );
5326 return EFI_SUCCESS;
5327 };
5328
5329 }
5330
5331 /**
5332 Display Pcie device structure.
5333
5334 @param[in] IoDev The pointer to the root pci protocol.
5335 @param[in] Address The Address to start at.
5336 @param[in] CapabilityPtr The offset from the address to start.
5337 @param[in] EnhancedDump The print format for the dump data.
5338
5339 **/
5340 EFI_STATUS
5341 PciExplainPciExpress (
5342 IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *IoDev,
5343 IN UINT64 Address,
5344 IN UINT8 CapabilityPtr,
5345 IN CONST UINT16 EnhancedDump
5346 )
5347 {
5348
5349 PCIE_CAP_STURCTURE PciExpressCap;
5350 EFI_STATUS Status;
5351 UINT64 CapRegAddress;
5352 UINT8 Bus;
5353 UINT8 Dev;
5354 UINT8 Func;
5355 UINT8 *ExRegBuffer;
5356 UINTN ExtendRegSize;
5357 UINT64 Pciex_Address;
5358 UINT8 DevicePortType;
5359 UINTN Index;
5360 UINT8 *RegAddr;
5361 UINTN RegValue;
5362 PCI_EXP_EXT_HDR *ExtHdr;
5363
5364 CapRegAddress = Address + CapabilityPtr;
5365 IoDev->Pci.Read (
5366 IoDev,
5367 EfiPciWidthUint32,
5368 CapRegAddress,
5369 sizeof (PciExpressCap) / sizeof (UINT32),
5370 &PciExpressCap
5371 );
5372
5373 DevicePortType = (UINT8) PCIE_CAP_DEVICEPORT_TYPE (PciExpressCap.PcieCapReg);
5374
5375 ShellPrintEx (-1, -1, L"\r\nPci Express device capability structure:\r\n");
5376
5377 for (Index = 0; PcieExplainList[Index].Type < PcieExplainTypeMax; Index++) {
5378 if (ShellGetExecutionBreakFlag()) {
5379 goto Done;
5380 }
5381 RegAddr = ((UINT8 *) &PciExpressCap) + PcieExplainList[Index].Offset;
5382 switch (PcieExplainList[Index].Width) {
5383 case FieldWidthUINT8:
5384 RegValue = *(UINT8 *) RegAddr;
5385 break;
5386 case FieldWidthUINT16:
5387 RegValue = *(UINT16 *) RegAddr;
5388 break;
5389 case FieldWidthUINT32:
5390 RegValue = *(UINT32 *) RegAddr;
5391 break;
5392 default:
5393 RegValue = 0;
5394 break;
5395 }
5396 ShellPrintHiiEx(-1, -1, NULL,
5397 PcieExplainList[Index].Token,
5398 gShellDebug1HiiHandle,
5399 PcieExplainList[Index].Offset,
5400 RegValue
5401 );
5402 if (PcieExplainList[Index].Func == NULL) {
5403 continue;
5404 }
5405 switch (PcieExplainList[Index].Type) {
5406 case PcieExplainTypeLink:
5407 //
5408 // Link registers should not be used by
5409 // a) Root Complex Integrated Endpoint
5410 // b) Root Complex Event Collector
5411 //
5412 if (DevicePortType == PCIE_ROOT_COMPLEX_INTEGRATED_PORT ||
5413 DevicePortType == PCIE_ROOT_COMPLEX_EVENT_COLLECTOR) {
5414 continue;
5415 }
5416 break;
5417 case PcieExplainTypeSlot:
5418 //
5419 // Slot registers are only valid for
5420 // a) Root Port of PCI Express Root Complex
5421 // b) Downstream Port of PCI Express Switch
5422 // and when SlotImplemented bit is set in PCIE cap register.
5423 //
5424 if ((DevicePortType != PCIE_ROOT_COMPLEX_ROOT_PORT &&
5425 DevicePortType != PCIE_SWITCH_DOWNSTREAM_PORT) ||
5426 !PCIE_CAP_SLOT_IMPLEMENTED (PciExpressCap.PcieCapReg)) {
5427 continue;
5428 }
5429 break;
5430 case PcieExplainTypeRoot:
5431 //
5432 // Root registers are only valid for
5433 // Root Port of PCI Express Root Complex
5434 //
5435 if (DevicePortType != PCIE_ROOT_COMPLEX_ROOT_PORT) {
5436 continue;
5437 }
5438 break;
5439 default:
5440 break;
5441 }
5442 PcieExplainList[Index].Func (&PciExpressCap);
5443 }
5444
5445 Bus = (UINT8) (RShiftU64 (Address, 24));
5446 Dev = (UINT8) (RShiftU64 (Address, 16));
5447 Func = (UINT8) (RShiftU64 (Address, 8));
5448
5449 Pciex_Address = CALC_EFI_PCIEX_ADDRESS (Bus, Dev, Func, EFI_PCIE_CAPABILITY_BASE_OFFSET);
5450
5451 ExtendRegSize = 0x1000 - EFI_PCIE_CAPABILITY_BASE_OFFSET;
5452
5453 ExRegBuffer = (UINT8 *) AllocateZeroPool (ExtendRegSize);
5454
5455 //
5456 // PciRootBridgeIo protocol should support pci express extend space IO
5457 // (Begins at offset EFI_PCIE_CAPABILITY_BASE_OFFSET)
5458 //
5459 Status = IoDev->Pci.Read (
5460 IoDev,
5461 EfiPciWidthUint32,
5462 Pciex_Address,
5463 (ExtendRegSize) / sizeof (UINT32),
5464 (VOID *) (ExRegBuffer)
5465 );
5466 if (EFI_ERROR (Status) || ExRegBuffer == NULL) {
5467 SHELL_FREE_NON_NULL(ExRegBuffer);
5468 return EFI_UNSUPPORTED;
5469 }
5470
5471 if (EnhancedDump == 0) {
5472 //
5473 // Print the PciEx extend space in raw bytes ( 0xFF-0xFFF)
5474 //
5475 ShellPrintEx (-1, -1, L"\r\n%HStart dumping PCIex extended configuration space (0x100 - 0xFFF).%N\r\n\r\n");
5476
5477 DumpHex (
5478 2,
5479 EFI_PCIE_CAPABILITY_BASE_OFFSET,
5480 ExtendRegSize,
5481 (VOID *) (ExRegBuffer)
5482 );
5483 } else {
5484 ExtHdr = (PCI_EXP_EXT_HDR*)ExRegBuffer;
5485 while (ExtHdr->CapabilityId != 0 && ExtHdr->CapabilityVersion != 0) {
5486 //
5487 // Process this item
5488 //
5489 if (EnhancedDump == 0xFFFF || EnhancedDump == ExtHdr->CapabilityId) {
5490 //
5491 // Print this item
5492 //
5493 PrintPciExtendedCapabilityDetails((PCI_EXP_EXT_HDR*)ExRegBuffer, ExtHdr, &PciExpressCap);
5494 }
5495
5496 //
5497 // Advance to the next item if it exists
5498 //
5499 if (ExtHdr->NextCapabilityOffset != 0) {
5500 ExtHdr = (PCI_EXP_EXT_HDR*)((UINT8*)ExRegBuffer + ExtHdr->NextCapabilityOffset);
5501 } else {
5502 break;
5503 }
5504 }
5505 }
5506 SHELL_FREE_NON_NULL(ExRegBuffer);
5507
5508 Done:
5509 return EFI_SUCCESS;
5510 }