pci: change offset type to uint16 in config space API.
* The config space is larger than 255, we need to use an uint16 to access offsets superior or equal to 256. The current API only proposes an uint8 for this. This change switches the offset parameter to the uint16 type. Axel hinted that the used values are the same with such a change (the doc says sign extended to 2 or 4 bytes). I checked with GCC2 and it's indeed the case when inspecting the memory. With GCC4, instructions are the same on function call. * prints info about extended capabilities. * struct pci_module_info and struct pci_device_module_info are extended with pci_find_extended_capability().
This commit is contained in:
+18
-10
@@ -131,18 +131,18 @@ struct pci_module_info {
|
||||
pci_info *info /* caller-supplied buffer for info */
|
||||
);
|
||||
uint32 (*read_pci_config) (
|
||||
uchar bus, /* bus number */
|
||||
uchar device, /* device # on bus */
|
||||
uchar function, /* function # in device */
|
||||
uchar offset, /* offset in configuration space */
|
||||
uchar size /* # bytes to read (1, 2 or 4) */
|
||||
uint8 bus, /* bus number */
|
||||
uint8 device, /* device # on bus */
|
||||
uint8 function, /* function # in device */
|
||||
uint16 offset, /* offset in configuration space */
|
||||
uint8 size /* # bytes to read (1, 2 or 4) */
|
||||
);
|
||||
void (*write_pci_config) (
|
||||
uchar bus, /* bus number */
|
||||
uchar device, /* device # on bus */
|
||||
uchar function, /* function # in device */
|
||||
uchar offset, /* offset in configuration space */
|
||||
uchar size, /* # bytes to write (1, 2 or 4) */
|
||||
uint8 bus, /* bus number */
|
||||
uint8 device, /* device # on bus */
|
||||
uint8 function, /* function # in device */
|
||||
uint16 offset, /* offset in configuration space */
|
||||
uint8 size, /* # bytes to write (1, 2 or 4) */
|
||||
uint32 value /* value to write */
|
||||
);
|
||||
|
||||
@@ -174,6 +174,14 @@ struct pci_module_info {
|
||||
uchar device,
|
||||
uchar function,
|
||||
uchar newInterruptLineValue);
|
||||
|
||||
status_t (*find_pci_extended_capability) (
|
||||
uint8 bus,
|
||||
uint8 device,
|
||||
uint8 function,
|
||||
uint16 cap_id,
|
||||
uint16 *offset
|
||||
);
|
||||
};
|
||||
|
||||
#define B_PCI_MODULE_NAME "bus_managers/pci/v1"
|
||||
|
||||
@@ -27,13 +27,15 @@ typedef struct pci_device_module_info {
|
||||
|
||||
void *(*ram_address)(pci_device *device, const void *physicalAddress);
|
||||
|
||||
uint32 (*read_pci_config)(pci_device *device, uint8 offset,
|
||||
uint32 (*read_pci_config)(pci_device *device, uint16 offset,
|
||||
uint8 size);
|
||||
void (*write_pci_config)(pci_device *device, uint8 offset,
|
||||
void (*write_pci_config)(pci_device *device, uint16 offset,
|
||||
uint8 size, uint32 value);
|
||||
status_t (*find_pci_capability)(pci_device *device, uint8 capID,
|
||||
uint8 *offset);
|
||||
void (*get_pci_info)(pci_device *device, struct pci_info *info);
|
||||
status_t (*find_pci_extended_capability)(pci_device *device, uint16 capID,
|
||||
uint16 *offset);
|
||||
} pci_device_module_info;
|
||||
|
||||
|
||||
|
||||
@@ -43,7 +43,7 @@ pci_get_nth_pci_info(long index, pci_info *outInfo)
|
||||
|
||||
|
||||
uint32
|
||||
pci_read_config(uint8 virtualBus, uint8 device, uint8 function, uint8 offset,
|
||||
pci_read_config(uint8 virtualBus, uint8 device, uint8 function, uint16 offset,
|
||||
uint8 size)
|
||||
{
|
||||
uint8 bus;
|
||||
@@ -62,7 +62,7 @@ pci_read_config(uint8 virtualBus, uint8 device, uint8 function, uint8 offset,
|
||||
|
||||
|
||||
void
|
||||
pci_write_config(uint8 virtualBus, uint8 device, uint8 function, uint8 offset,
|
||||
pci_write_config(uint8 virtualBus, uint8 device, uint8 function, uint16 offset,
|
||||
uint8 size, uint32 value)
|
||||
{
|
||||
uint8 bus;
|
||||
|
||||
@@ -186,9 +186,9 @@ void pci_uninit(void);
|
||||
long pci_get_nth_pci_info(long index, pci_info *outInfo);
|
||||
|
||||
uint32 pci_read_config(uint8 virtualBus, uint8 device, uint8 function,
|
||||
uint8 offset, uint8 size);
|
||||
uint16 offset, uint8 size);
|
||||
void pci_write_config(uint8 virtualBus, uint8 device, uint8 function,
|
||||
uint8 offset, uint8 size, uint32 value);
|
||||
uint16 offset, uint8 size, uint32 value);
|
||||
|
||||
void __pci_resolve_virtual_bus(uint8 virtualBus, uint8 *domain, uint8 *bus);
|
||||
|
||||
|
||||
@@ -66,14 +66,14 @@ pci_device_write_io_32(pci_device* device, addr_t mappedIOAddress, uint32 value)
|
||||
|
||||
|
||||
static uint32
|
||||
pci_device_read_pci_config(pci_device* device, uint8 offset, uint8 size)
|
||||
pci_device_read_pci_config(pci_device* device, uint16 offset, uint8 size)
|
||||
{
|
||||
return gPCI->ReadConfig(device->device, offset, size);
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
pci_device_write_pci_config(pci_device* device, uint8 offset, uint8 size,
|
||||
pci_device_write_pci_config(pci_device* device, uint16 offset, uint8 size,
|
||||
uint32 value)
|
||||
{
|
||||
gPCI->WriteConfig(device->device, offset, size, value);
|
||||
@@ -94,6 +94,14 @@ pci_device_find_capability(pci_device* device, uint8 capID, uint8* offset)
|
||||
}
|
||||
|
||||
|
||||
static status_t
|
||||
pci_device_find_extended_capability(pci_device* device, uint16 capID,
|
||||
uint16* offset)
|
||||
{
|
||||
return gPCI->FindExtendedCapability(device->device, capID, offset);
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
pci_device_get_pci_info(pci_device* device, struct pci_info* info)
|
||||
{
|
||||
@@ -187,5 +195,6 @@ pci_device_module_info gPCIDeviceModule = {
|
||||
pci_device_read_pci_config,
|
||||
pci_device_write_pci_config,
|
||||
pci_device_find_capability,
|
||||
pci_device_get_pci_info
|
||||
pci_device_get_pci_info,
|
||||
pci_device_find_extended_capability
|
||||
};
|
||||
|
||||
@@ -26,6 +26,7 @@
|
||||
#endif
|
||||
|
||||
const char *get_capability_name(uint8 cap_id);
|
||||
const char *get_extended_capability_name(uint16 cap_id);
|
||||
|
||||
|
||||
static void
|
||||
@@ -176,6 +177,45 @@ print_capabilities(const pci_info *info)
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
print_extended_capabilities(const pci_info *info)
|
||||
{
|
||||
if (pci_find_capability(info->bus, info->device, info->function,
|
||||
PCI_cap_id_pcie, NULL) != B_OK)
|
||||
return;
|
||||
|
||||
uint16 capPointer = PCI_extended_capability;
|
||||
uint32 capability = pci_read_config(info->bus, info->device,
|
||||
info->function, capPointer, 4);
|
||||
TRACE(("PCI: Extended capabilities: "));
|
||||
if (capability == 0 || capability == 0xffffffff) {
|
||||
TRACE(("(empty list)\n"));
|
||||
return;
|
||||
}
|
||||
|
||||
for (int i = 0; i < 48; i++) {
|
||||
if (i) {
|
||||
TRACE((", "));
|
||||
}
|
||||
const char *name = get_extended_capability_name(
|
||||
PCI_extcap_id(capability));
|
||||
if (name) {
|
||||
TRACE(("%s", name));
|
||||
} else {
|
||||
TRACE(("0x%04" B_PRIx32, PCI_extcap_id(capability)));
|
||||
}
|
||||
|
||||
capPointer = PCI_extcap_next_ptr(capability) & ~3;
|
||||
if (capPointer < PCI_extended_capability)
|
||||
break;
|
||||
capability = pci_read_config(info->bus, info->device, info->function,
|
||||
capPointer, 4);
|
||||
}
|
||||
|
||||
TRACE(("\n"));
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
print_info_basic(const pci_info *info, bool verbose)
|
||||
{
|
||||
@@ -236,6 +276,7 @@ print_info_basic(const pci_info *info, bool verbose)
|
||||
}
|
||||
|
||||
print_capabilities(info);
|
||||
print_extended_capabilities(info);
|
||||
}
|
||||
|
||||
|
||||
@@ -298,3 +339,71 @@ get_capability_name(uint8 cap_id)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
const char *
|
||||
get_extended_capability_name(uint16 cap_id)
|
||||
{
|
||||
switch (cap_id) {
|
||||
case PCI_extcap_id_aer:
|
||||
return "Advanced Error Reporting";
|
||||
case PCI_extcap_id_vc:
|
||||
return "Virtual Channel";
|
||||
case PCI_extcap_id_serial:
|
||||
return "Serial Number";
|
||||
case PCI_extcap_id_power_budget:
|
||||
return "Power Budgeting";
|
||||
case PCI_extcap_id_rcl_decl:
|
||||
return "Root Complex Link Declaration";
|
||||
case PCI_extcap_id_rcil_ctl:
|
||||
return "Root Complex Internal Link Control";
|
||||
case PCI_extcap_id_rcec_assoc:
|
||||
return "Root Complex Event Collector Association";
|
||||
case PCI_extcap_id_mfvc:
|
||||
return "MultiFunction Virtual Channel";
|
||||
case PCI_extcap_id_vc2:
|
||||
return "Virtual Channel 2";
|
||||
case PCI_extcap_id_rcrb_header:
|
||||
return "RCRB Header";
|
||||
case PCI_extcap_id_vendor:
|
||||
return "Vendor Unique";
|
||||
case PCI_extcap_id_acs:
|
||||
return "Access Control Services";
|
||||
case PCI_extcap_id_ari:
|
||||
return "Alternative Routing Id Interpretation";
|
||||
case PCI_extcap_id_ats:
|
||||
return "Address Translation Services";
|
||||
case PCI_extcap_id_srio_virtual:
|
||||
return "Single Root I/O Virtualization";
|
||||
case PCI_extcap_id_mrio_virtual:
|
||||
return "Multiple Root I/O Virtual";
|
||||
case PCI_extcap_id_multicast:
|
||||
return "Multicast";
|
||||
case PCI_extcap_id_page_request:
|
||||
return "Page Request";
|
||||
case PCI_extcap_id_amd:
|
||||
return "AMD Reserved";
|
||||
case PCI_extcap_id_resizable_bar:
|
||||
return "Resizable Bar";
|
||||
case PCI_extcap_id_dyn_power_alloc:
|
||||
return "Dynamic Power Allocation";
|
||||
case PCI_extcap_id_tph_requester:
|
||||
return "TPH Requester";
|
||||
case PCI_extcap_id_latency_tolerance:
|
||||
return "Latency Tolerance Reporting";
|
||||
case PCI_extcap_id_2ndpcie:
|
||||
return "Secondary PCIe";
|
||||
case PCI_extcap_id_pmux:
|
||||
return "Protocol Multiplexing";
|
||||
case PCI_extcap_id_pasid:
|
||||
return "Process Address Space Id";
|
||||
case PCI_extcap_id_ln_requester:
|
||||
return "LN Requester";
|
||||
case PCI_extcap_id_dpc:
|
||||
return "Downstream Porto Containment";
|
||||
case PCI_extcap_id_l1pm:
|
||||
return "L1 Power Management Substates";
|
||||
default:
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -67,7 +67,8 @@ static struct pci_module_info sOldPCIModule = {
|
||||
&pci_find_capability,
|
||||
&pci_reserve_device,
|
||||
&pci_unreserve_device,
|
||||
&pci_update_interrupt_line
|
||||
&pci_update_interrupt_line,
|
||||
&pci_find_extended_capability
|
||||
};
|
||||
|
||||
module_dependency module_dependencies[] = {
|
||||
|
||||
@@ -29,11 +29,11 @@ typedef struct pci_root_module_info {
|
||||
|
||||
// read PCI config space
|
||||
uint32 (*read_pci_config)(uint8 bus, uint8 device, uint8 function,
|
||||
uint8 offset, uint8 size);
|
||||
uint16 offset, uint8 size);
|
||||
|
||||
// write PCI config space
|
||||
void (*write_pci_config)(uint8 bus, uint8 device, uint8 function,
|
||||
uint8 offset, uint8 size, uint32 value);
|
||||
uint16 offset, uint8 size, uint32 value);
|
||||
} pci_root_module_info;
|
||||
|
||||
extern pci_root_module_info gPCIRootModule;
|
||||
|
||||
Reference in New Issue
Block a user