mirror of
https://github.com/projectacrn/acrn-hypervisor.git
synced 2025-06-22 13:37:10 +00:00
board_inspector: parse SR-IOV capability structure properly
This patch adds the logic needed to fully parse an SR-IOV extended capability structure. Such information will later be used to extract all information about physical and virtual functions. Tracked-On: #7301 Signed-off-by: Junjie Mao <junjie.mao@intel.com>
This commit is contained in:
parent
0a77891f1c
commit
93ccc0f473
@ -6,6 +6,9 @@
|
|||||||
import ctypes
|
import ctypes
|
||||||
import copy
|
import copy
|
||||||
import inspectorlib.cdata as cdata
|
import inspectorlib.cdata as cdata
|
||||||
|
from .header import MemoryBar32, MemoryBar64, IOBar, \
|
||||||
|
PCIE_BAR_SPACE_MASK, PCIE_BAR_MEMORY_SPACE, PCIE_BAR_IO_SPACE, \
|
||||||
|
PCIE_BAR_TYPE_MASK, PCIE_BAR_TYPE_32_BIT, PCIE_BAR_TYPE_64_BIT
|
||||||
|
|
||||||
class ExtendedCapability:
|
class ExtendedCapability:
|
||||||
# Capability names from PCI Express Base Specification, mostly Table 9-23
|
# Capability names from PCI Express Base Specification, mostly Table 9-23
|
||||||
@ -62,6 +65,11 @@ class ExtendedCapability:
|
|||||||
else:
|
else:
|
||||||
return f"Reserved Extended ({hex(self.id)})"
|
return f"Reserved Extended ({hex(self.id)})"
|
||||||
|
|
||||||
|
@property
|
||||||
|
def next_cap_ptr(self):
|
||||||
|
# Classes inherit ExtendedCapability must implement the attribute next_cap_ptr_raw
|
||||||
|
return self.next_cap_ptr_raw & 0xffc
|
||||||
|
|
||||||
class ExtendedCapabilityListRegister(cdata.Struct, ExtendedCapability):
|
class ExtendedCapabilityListRegister(cdata.Struct, ExtendedCapability):
|
||||||
_pack_ = 1
|
_pack_ = 1
|
||||||
_fields_ = [
|
_fields_ = [
|
||||||
@ -70,12 +78,90 @@ class ExtendedCapabilityListRegister(cdata.Struct, ExtendedCapability):
|
|||||||
('next_cap_ptr_raw', ctypes.c_uint32, 12),
|
('next_cap_ptr_raw', ctypes.c_uint32, 12),
|
||||||
]
|
]
|
||||||
|
|
||||||
@property
|
# SR-IOV (0x10)
|
||||||
def next_cap_ptr(self):
|
|
||||||
return self.next_cap_ptr_raw & 0xffc
|
class SRIOVBase(cdata.Struct, ExtendedCapability):
|
||||||
|
_pack_ = 1
|
||||||
|
_fields_ = copy.copy(ExtendedCapabilityListRegister._fields_) + [
|
||||||
|
# SR-IOV Capabilities Register
|
||||||
|
('vf_migration_capable', ctypes.c_uint32, 1),
|
||||||
|
('ari_capable_hierarchy_preserved', ctypes.c_uint32, 1),
|
||||||
|
('vf_10_bit_tag_requester_supported', ctypes.c_uint32, 1),
|
||||||
|
('reserved1', ctypes.c_uint32, 18),
|
||||||
|
('vf_migration_interrupt_message_number', ctypes.c_uint32, 11),
|
||||||
|
|
||||||
|
# SR-IOV Control Register
|
||||||
|
('vf_enable', ctypes.c_uint32, 1),
|
||||||
|
('vf_migration_enable', ctypes.c_uint32, 1),
|
||||||
|
('vf_migration_interrupt_enable', ctypes.c_uint32, 1),
|
||||||
|
('vf_mse', ctypes.c_uint32, 1),
|
||||||
|
('ari_capable_hierarchy', ctypes.c_uint32, 1),
|
||||||
|
('vf_10_bit_tag_requester_enable', ctypes.c_uint32, 1),
|
||||||
|
('reserved2', ctypes.c_uint32, 10),
|
||||||
|
|
||||||
|
# SR-IOV Status Register
|
||||||
|
('vf_migration_status', ctypes.c_uint32, 1),
|
||||||
|
('reserved3', ctypes.c_uint32, 15),
|
||||||
|
|
||||||
|
('initial_vfs', ctypes.c_uint16),
|
||||||
|
('total_vfs', ctypes.c_uint16),
|
||||||
|
('num_vfs', ctypes.c_uint16),
|
||||||
|
('function_dependency_link', ctypes.c_uint8),
|
||||||
|
('reserved4', ctypes.c_uint8),
|
||||||
|
('first_vf_offset', ctypes.c_uint16),
|
||||||
|
('vf_stride', ctypes.c_uint16),
|
||||||
|
('reserved5', ctypes.c_uint16),
|
||||||
|
('vf_device_id', ctypes.c_uint16),
|
||||||
|
|
||||||
|
('supported_page_sizes', ctypes.c_uint32),
|
||||||
|
('system_page_size', ctypes.c_uint32),
|
||||||
|
]
|
||||||
|
|
||||||
|
def SRIOV_factory(addr):
|
||||||
|
vf_bars_list = list()
|
||||||
|
bar_base = addr + ctypes.sizeof(SRIOVBase)
|
||||||
|
bar_addr = bar_base
|
||||||
|
bar_end = bar_base + 0x18
|
||||||
|
while bar_addr < bar_end:
|
||||||
|
bar = ctypes.c_uint32.from_address(bar_addr).value
|
||||||
|
idx = int((bar_addr - bar_base) / 4)
|
||||||
|
if (bar & PCIE_BAR_SPACE_MASK) == PCIE_BAR_MEMORY_SPACE:
|
||||||
|
if (bar & PCIE_BAR_TYPE_MASK) == PCIE_BAR_TYPE_64_BIT:
|
||||||
|
vf_bars_list.append((f"vf_bar{idx}", MemoryBar64))
|
||||||
|
bar_addr += 0x8
|
||||||
|
else:
|
||||||
|
vf_bars_list.append((f"vf_bar{idx}", MemoryBar32))
|
||||||
|
bar_addr += 0x4
|
||||||
|
else:
|
||||||
|
vf_bars_list.append((f"vf_bar{idx}", IOBar))
|
||||||
|
bar_addr += 0x4
|
||||||
|
|
||||||
|
class SRIOV(cdata.Struct, ExtendedCapability):
|
||||||
|
class VFBars(cdata.Struct):
|
||||||
|
_pack_ = 1
|
||||||
|
_fields_ = vf_bars_list
|
||||||
|
|
||||||
|
def __iter__(self):
|
||||||
|
for f in self._fields_:
|
||||||
|
yield getattr(self, f[0])
|
||||||
|
|
||||||
|
_pack_ = 1
|
||||||
|
_fields_ = copy.copy(SRIOVBase._fields_) + [
|
||||||
|
('vf_bars', VFBars),
|
||||||
|
('vf_migration_state_array_offset', ctypes.c_uint32),
|
||||||
|
]
|
||||||
|
|
||||||
|
return SRIOV
|
||||||
|
|
||||||
|
def parse_sriov(buf, cap_ptr):
|
||||||
|
return SRIOV_factory(ctypes.addressof(buf) + cap_ptr).from_buffer_copy(buf, cap_ptr)
|
||||||
|
|
||||||
# Module API
|
# Module API
|
||||||
|
|
||||||
|
capability_parsers = {
|
||||||
|
0x10: parse_sriov,
|
||||||
|
}
|
||||||
|
|
||||||
def extended_capabilities(data):
|
def extended_capabilities(data):
|
||||||
buf = ctypes.create_string_buffer(data, len(data))
|
buf = ctypes.create_string_buffer(data, len(data))
|
||||||
cap_ptr = 0x100
|
cap_ptr = 0x100
|
||||||
@ -83,7 +169,9 @@ def extended_capabilities(data):
|
|||||||
acc = list()
|
acc = list()
|
||||||
while cap_ptr != 0:
|
while cap_ptr != 0:
|
||||||
caplist = ExtendedCapabilityListRegister.from_buffer_copy(buf, cap_ptr)
|
caplist = ExtendedCapabilityListRegister.from_buffer_copy(buf, cap_ptr)
|
||||||
if caplist.id != 0:
|
if caplist.id in capability_parsers.keys():
|
||||||
|
acc.append(capability_parsers[caplist.id](buf, cap_ptr))
|
||||||
|
elif caplist.id != 0:
|
||||||
acc.append(caplist)
|
acc.append(caplist)
|
||||||
cap_ptr = caplist.next_cap_ptr
|
cap_ptr = caplist.next_cap_ptr
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user