#define PCI_CAP_ID_CHSWP 0x06 /* CompactPCI HotSwap */
#define PCI_CAP_ID_PCIX 0x07 /* PCI-X */
#define PCI_CAP_ID_HT 0x08 /* HyperTransport */
+#define PCI_CAP_ID_VNDR 0x09 /* Vendor specific */
+#define PCI_CAP_ID_DBG 0x0A /* Debug port */
+#define PCI_CAP_ID_CCRC 0x0B /* CompactPCI Central Resource Control */
+#define PCI_CAP_ID_AGP3 0x0E /* AGP 8x */
+#define PCI_CAP_ID_EXP 0x10 /* PCI Express */
+#define PCI_CAP_ID_MSIX 0x11 /* MSI-X */
#define PCI_CAP_LIST_NEXT 1 /* Next capability in the list */
#define PCI_CAP_FLAGS 2 /* Capability defined flags (16 bits) */
#define PCI_CAP_SIZEOF 4
+/* Capabilities residing in the PCI Express extended configuration space */
+
+#define PCI_EXT_CAP_ID_AER 0x01 /* Advanced Error Reporting */
+#define PCI_EXT_CAP_ID_VC 0x02 /* Virtual Channel */
+#define PCI_EXT_CAP_ID_DSN 0x03 /* Device Serial Number */
+#define PCI_EXT_CAP_ID_PB 0x04 /* Power Budgeting */
+
/* Power Management Registers */
#define PCI_PM_CAP_VER_MASK 0x0007 /* Version (2=PM1.1) */
#define PCI_HT_RM_CNT1 10 /* Retry Count 1 Register */
#define PCI_HT_RM_SIZEOF 12
+/* PCI Express */
+#define PCI_EXP_FLAGS 0x2 /* Capabilities register */
+#define PCI_EXP_FLAGS_VERS 0x000f /* Capability version */
+#define PCI_EXP_FLAGS_TYPE 0x00f0 /* Device/Port type */
+#define PCI_EXP_TYPE_ENDPOINT 0x0 /* Express Endpoint */
+#define PCI_EXP_TYPE_LEG_END 0x1 /* Legacy Endpoint */
+#define PCI_EXP_TYPE_ROOT_PORT 0x4 /* Root Port */
+#define PCI_EXP_TYPE_UPSTREAM 0x5 /* Upstream Port */
+#define PCI_EXP_TYPE_DOWNSTREAM 0x6 /* Downstream Port */
+#define PCI_EXP_TYPE_PCI_BRIDGE 0x7 /* PCI/PCI-X Bridge */
+#define PCI_EXP_FLAGS_SLOT 0x0100 /* Slot implemented */
+#define PCI_EXP_FLAGS_IRQ 0x3e00 /* Interrupt message number */
+#define PCI_EXP_DEVCAP 0x4 /* Device capabilities */
+#define PCI_EXP_DEVCAP_PAYLOAD 0x07 /* Max_Payload_Size */
+#define PCI_EXP_DEVCAP_PHANTOM 0x18 /* Phantom functions */
+#define PCI_EXP_DEVCAP_EXT_TAG 0x20 /* Extended tags */
+#define PCI_EXP_DEVCAP_L0S 0x1c0 /* L0s Acceptable Latency */
+#define PCI_EXP_DEVCAP_L1 0xe00 /* L1 Acceptable Latency */
+#define PCI_EXP_DEVCAP_ATN_BUT 0x1000 /* Attention Button Present */
+#define PCI_EXP_DEVCAP_ATN_IND 0x2000 /* Attention Indicator Present */
+#define PCI_EXP_DEVCAP_PWR_IND 0x4000 /* Power Indicator Present */
+#define PCI_EXP_DEVCAP_READRQ 0x38000 /* Max_Read_Request_Size */
+#define PCI_EXP_DEVCAP_PWR_VAL 0x3fc0000 /* Slot Power Limit Value */
+#define PCI_EXP_DEVCAP_PWR_SCL 0xc000000 /* Slot Power Limit Scale */
+#define PCI_EXP_DEVCTL 0x8 /* Device Control */
+#define PCI_EXP_DEVCTL_CERE 0x0001 /* Correctable Error Reporting En. */
+#define PCI_EXP_DEVCTL_NFERE 0x0002 /* Non-Fatal Error Reporting Enable */
+#define PCI_EXP_DEVCTL_FERE 0x0004 /* Fatal Error Reporting Enable */
+#define PCI_EXP_DEVCTL_URRE 0x0008 /* Unsupported Request Reporting En. */
+#define PCI_EXP_DEVCTL_URS 0x0010 /* Unsupported Request Severity */
+#define PCI_EXP_DEVCTL_PAYLOAD 0x00e0 /* Max_Payload_Size */
+#define PCI_EXP_DEVCTL_EXT_TAG 0x0100 /* Extended Tag Field Enable */
+#define PCI_EXP_DEVCTL_PHANTOM 0x0200 /* Phantom Functions Enable */
+#define PCI_EXP_DEVCTL_AUX_PME 0x0400 /* Auxiliary Power PM Enable */
+#define PCI_EXP_DEVCTL_STOP 0x0800 /* Complete Pending Transactions */
+#define PCI_EXP_DEVCTL_READRQ 0x7000 /* Max_Read_Request_Size */
+#define PCI_EXP_DEVSTA 0xa /* Device Status */
+#define PCI_EXP_DEVSTA_CED 0x01 /* Correctable Error Detected */
+#define PCI_EXP_DEVSTA_NFED 0x02 /* Non-Fatal Error Detected */
+#define PCI_EXP_DEVSTA_FED 0x04 /* Fatal Error Detected */
+#define PCI_EXP_DEVSTA_URD 0x08 /* Unsupported Request Detected */
+#define PCI_EXP_DEVSTA_AUXPD 0x10 /* AUX Power Detected */
+#define PCI_EXP_DEVSTA_TRPND 0x20 /* Transactions Pending */
+#define PCI_EXP_LNKCAP 0xc /* Link Capabilities */
+#define PCI_EXP_LNKCTL 0x10 /* Link Control */
+#define PCI_EXP_LNKSTA 0x12 /* Link Status */
+#define PCI_EXP_SLTCAP 0x14 /* Slot Capabilities */
+#define PCI_EXP_SLTCTL 0x18 /* Slot Control */
+#define PCI_EXP_SLTSTA 0x1a /* Slot Status */
+#define PCI_EXP_RTCTL 0x1c /* Root Control */
+#define PCI_EXP_RTSTA 0x20 /* Root Status */
+
+/* MSI-X */
+#define PCI_MSIX_ENABLE 0x8000
+#define PCI_MSIX_MASK 0x4000
+#define PCI_MSIX_TABSIZE 0x03ff
+#define PCI_MSIX_TABLE 4
+#define PCI_MSIX_PBA 8
+#define PCI_MSIX_BIR 0x7
+
/*
* The PCI interface treats multi-function devices as independent
* devices. The slot/function address of each device is encoded
FLAG(cmd, PCI_HT_PRI_CMD_MH),
FLAG(cmd, PCI_HT_PRI_CMD_DD),
FLAG(cmd, PCI_HT_PRI_CMD_DUL));
- config_fetch(d, where + PCI_HT_PRI_LCTR0, PCI_HT_PRI_SIZEOF - PCI_HT_PRI_LCTR0);
+ if (!config_fetch(d, where + PCI_HT_PRI_LCTR0, PCI_HT_PRI_SIZEOF - PCI_HT_PRI_LCTR0))
+ return;
lctr0 = get_conf_word(d, where + PCI_HT_PRI_LCTR0);
printf("\t\tLink Control 0: CFlE%c CST%c CFE%c <LkFail%c Init%c EOC%c TXO%c <CRCErr=%x IsocEn%c LSEn%c ExtCTL%c 64b%c\n",
FLAG(lctr0, PCI_HT_LCTR_CFLE),
FLAG(cmd, PCI_HT_SEC_CMD_AS),
FLAG(cmd, PCI_HT_SEC_CMD_HIECE),
FLAG(cmd, PCI_HT_SEC_CMD_DUL));
- config_fetch(d, where + PCI_HT_SEC_LCTR, PCI_HT_SEC_SIZEOF - PCI_HT_SEC_LCTR);
+ if (!config_fetch(d, where + PCI_HT_SEC_LCTR, PCI_HT_SEC_SIZEOF - PCI_HT_SEC_LCTR))
+ return;
lctr = get_conf_word(d, where + PCI_HT_SEC_LCTR);
printf("\t\tLink Control: CFlE%c CST%c CFE%c <LkFail%c Init%c EOC%c TXO%c <CRCErr=%x IsocEn%c LSEn%c ExtCTL%c 64b%c\n",
FLAG(lctr, PCI_HT_LCTR_CFLE),
printf("%08x Data: %04x\n", t, w);
}
+static void show_vendor(void)
+{
+ printf("Vendor Specific Information\n");
+}
+
+static void show_debug(void)
+{
+ printf("Debug port\n");
+}
+
+static float power_limit(int value, int scale)
+{
+ float scales[4] = { 1.0, 0.1, 0.01, 0.001 };
+ return value * scales[scale];
+}
+
+static void
+show_express(struct device *d, int where, int cap)
+{
+ u32 t;
+ u16 w;
+ int type = (cap & PCI_EXP_FLAGS_TYPE) >> 4;
+
+ printf("Express ");
+ switch (type)
+ {
+ case PCI_EXP_TYPE_ENDPOINT:
+ printf("Endpoint");
+ break;
+ case PCI_EXP_TYPE_LEG_END:
+ printf("Legacy Endpoint");
+ break;
+ case PCI_EXP_TYPE_ROOT_PORT:
+ printf("Root Port (Slot%c)", FLAG(cap, PCI_EXP_FLAGS_SLOT));
+ break;
+ case PCI_EXP_TYPE_UPSTREAM:
+ printf("Upstream Port");
+ break;
+ case PCI_EXP_TYPE_DOWNSTREAM:
+ printf("Downstream Port (Slot%c)", FLAG(cap, PCI_EXP_FLAGS_SLOT));
+ break;
+ case PCI_EXP_TYPE_PCI_BRIDGE:
+ printf("PCI Bridge");
+ break;
+ default:
+ printf("Unknown type");
+ }
+ printf(" IRQ %d\n", (cap & PCI_EXP_FLAGS_IRQ) >> 9);
+ if (verbose < 2)
+ return;
+
+ t = get_conf_long(d, where + PCI_EXP_DEVCAP);
+ printf("\t\tMaxPayloadSizeSupported %d\n", 128 << (t & PCI_EXP_DEVCAP_PAYLOAD));
+ printf("\t\tPhantomFunctions %d\n", 1 << ((t & PCI_EXP_DEVCAP_PHANTOM) >> 3));
+ printf("\t\tExtendedTags%c\n", FLAG(t, PCI_EXP_DEVCAP_EXT_TAG));
+ printf("\t\tL0sLatency <%dns\n", 64 << ((t & PCI_EXP_DEVCAP_L0S) >> 6));
+ printf("\t\tL1Latency <%dus\n", 1 << ((t & PCI_EXP_DEVCAP_L1) >> 9));
+ if ((type == PCI_EXP_TYPE_ENDPOINT) || (type == PCI_EXP_TYPE_LEG_END))
+ printf("\t\tAtnBtn%c AtnInd%c PwrInd%c\n", FLAG(t, PCI_EXP_DEVCAP_ATN_BUT),
+ FLAG(t, PCI_EXP_DEVCAP_ATN_IND), FLAG(t, PCI_EXP_DEVCAP_PWR_IND));
+ if (type == PCI_EXP_TYPE_ROOT_PORT)
+ printf("\t\tMaxReadRequestSizeSupported %d\n", 128 << ((t & PCI_EXP_DEVCAP_READRQ) >> 15));
+ if (type == PCI_EXP_TYPE_UPSTREAM)
+ printf("\t\tSlotPowerLimit %f\n",
+ power_limit((t & PCI_EXP_DEVCAP_PWR_VAL) >> 18,
+ (t & PCI_EXP_DEVCAP_PWR_SCL) >> 26));
+
+ w = get_conf_word(d, where + PCI_EXP_DEVCTL);
+ printf("\t\tError Reporting: Correctable%c Non-Fatal%c Fatal%c Unsupported%c\n",
+ FLAG(w, PCI_EXP_DEVCTL_CERE),
+ FLAG(w, PCI_EXP_DEVCTL_NFERE),
+ FLAG(w, PCI_EXP_DEVCTL_FERE),
+ FLAG(w, PCI_EXP_DEVCTL_URRE));
+}
+
+static void
+show_msix(struct device *d, int where, int cap)
+{
+ u32 off;
+
+ printf("MSI-X: Enable%c Mask%c TabSize=%d\n",
+ FLAG(cap, PCI_MSIX_ENABLE),
+ FLAG(cap, PCI_MSIX_MASK),
+ (cap & PCI_MSIX_TABSIZE) + 1);
+ if (verbose < 2 || !config_fetch(d, where + PCI_MSIX_TABLE, 8))
+ return;
+
+ off = get_conf_long(d, where + PCI_MSIX_TABLE);
+ printf("\t\tVector table: BAR=%d offset=%08x\n",
+ off & PCI_MSIX_BIR, off & ~PCI_MSIX_BIR);
+ off = get_conf_long(d, where + PCI_MSIX_PBA);
+ printf("\t\tPBA: BAR=%d offset=%08x\n",
+ off & PCI_MSIX_BIR, off & ~PCI_MSIX_BIR);
+}
+
static void
show_slotid(int cap)
{
case PCI_CAP_ID_HT:
show_ht(d, where, cap);
break;
+ case PCI_CAP_ID_VNDR:
+ show_vendor();
+ break;
+ case PCI_CAP_ID_DBG:
+ show_debug();
+ break;
+ case PCI_CAP_ID_EXP:
+ show_express(d, where, cap);
+ break;
+ case PCI_CAP_ID_MSIX:
+ show_msix(d, where, cap);
+ break;
default:
printf("#%02x [%04x]\n", id, cap);
}