1
0
mirror of https://github.com/corundum/corundum.git synced 2025-01-30 08:32:52 +08:00

Consolidate MSI capability objects

This commit is contained in:
Alex Forencich 2018-10-15 00:05:37 -07:00
parent 2b9e4ccb78
commit 76dccafe0e
2 changed files with 40 additions and 110 deletions

View File

@ -1207,18 +1207,22 @@ class PCIECapability(object):
pass pass
class MSI32Capability(object): class MSICapability(object):
def __init__(self, *args, **kwargs): def __init__(self, *args, **kwargs):
super(MSI32Capability, self).__init__(*args, **kwargs) super(MSICapability, self).__init__(*args, **kwargs)
# MSI Capability Registes # MSI Capability Registers
self.msi_enable = False
self.msi_multiple_message_capable = 0 self.msi_multiple_message_capable = 0
self.msi_multiple_message_enable = 0 self.msi_multiple_message_enable = 0
self.msi_enable = False self.msi_64bit_address_capable = 0
self.msi_per_vector_mask_capable = 0
self.msi_message_address = 0 self.msi_message_address = 0
self.msi_message_data = 0 self.msi_message_data = 0
self.msi_mask_bits = 0
self.msi_pending_bits = 0
self.register_capability(MSI_CAP_ID, 3, self.read_msi_cap_register, self.write_msi_cap_register) self.register_capability(MSI_CAP_ID, 6, self.read_msi_cap_register, self.write_msi_cap_register)
""" """
MSI Capability (32 bit) MSI Capability (32 bit)
@ -1231,50 +1235,7 @@ class MSI32Capability(object):
+---------------------------------+---------------------------------+ +---------------------------------+---------------------------------+
| | Message Data | 2 0x08 | | Message Data | 2 0x08
+---------------------------------+---------------------------------+ +---------------------------------+---------------------------------+
"""
def read_msi_cap_register(self, reg):
if reg == 0:
# Message control
val = 0x00000000
if self.msi_enable: val |= 1 << 16
val |= (self.msi_multiple_message_capable & 0x7) << 17
val |= (self.msi_multiple_message_enable & 0x7) << 20
return val
elif reg == 1:
# Message address
return self.msi_message_address & 0xfffffffc
elif reg == 2:
# Message data
return self.msi_message_data & 0xffff
def write_msi_cap_register(self, reg, write, offset=None):
if reg == 0:
# Message control
if mask & 0x4: self.msi_enable = (data & 1 << 16 != 0)
if mask & 0x4: self.msi_multiple_message_enable = (data >> 20) & 0x7
elif reg == 1:
# Message address
self.msi_message_address = byte_mask_update(self.msi_message_address, mask, data) & 0xfffffffc
elif reg == 2:
# Message data
self.msi_message_data = byte_mask_update(self.msi_message_data, mask & 0x3, data) & 0xffff
class MSI64Capability(object):
def __init__(self, *args, **kwargs):
super(MSI64Capability, self).__init__(*args, **kwargs)
# MSI Capability Registes
self.msi_multiple_message_capable = 0
self.msi_multiple_message_enable = 0
self.msi_enable = False
self.msi_message_address = 0
self.msi_message_upper_address = 0
self.msi_message_data = 0
self.register_capability(MSI_CAP_ID, 4, self.read_msi_cap_register, self.write_msi_cap_register)
"""
MSI Capability (64 bit) MSI Capability (64 bit)
31 0 31 0
@ -1287,58 +1248,22 @@ class MSI64Capability(object):
+---------------------------------+---------------------------------+ +---------------------------------+---------------------------------+
| | Message Data | 3 0x0C | | Message Data | 3 0x0C
+---------------------------------+---------------------------------+ +---------------------------------+---------------------------------+
"""
def read_msi_cap_register(self, reg):
if reg == 0:
# Message control
val = 0x00800000
if self.msi_enable: val |= 1 << 16
val |= (self.msi_multiple_message_capable & 0x7) << 17
val |= (self.msi_multiple_message_enable & 0x7) << 20
return val
elif reg == 1:
# Message address
return self.msi_message_address & 0xfffffffc
elif reg == 2:
# Message upper address
return self.msi_message_upper_address & 0xffffffff
elif reg == 3:
# Message data
return self.msi_message_data & 0xffff
def write_msi_cap_register(self, reg, write, offset=None): MSI Capability (32 bit with per-vector masking)
if reg == 0:
# Message control
if mask & 0x4: self.msi_enable = (data & 1 << 16 != 0)
if mask & 0x4: self.msi_multiple_message_enable = (data >> 20) & 0x7
elif reg == 1:
# Message address
self.msi_message_address = byte_mask_update(self.msi_message_address, mask, data) & 0xfffffffc
elif reg == 2:
# Message upper address
self.msi_message_upper_address = byte_mask_update(self.msi_message_upper_address, mask, data) & 0xffffffff
elif reg == 3:
# Message data
self.msi_message_data = byte_mask_update(self.msi_message_data, mask & 0x3, data) & 0xffff
31 0
+---------------------------------+----------------+----------------+
| Message Control | Next Cap | Cap ID | 0 0x00
+---------------------------------+----------------+----------------+
| Message Address | 1 0x04
+-------------------------------------------------------------------+
| | Message Data | 2 0x08
+---------------------------------+---------------------------------+
| Mask Bits | 3 0x0C
+-------------------------------------------------------------------+
| Pending Bits | 4 0x10
+-------------------------------------------------------------------+
class MSI64MaskCapability(object):
def __init__(self, *args, **kwargs):
super(MSI64MaskCapability, self).__init__(*args, **kwargs)
# MSI Capability Registes
self.msi_enable = False
self.msi_multiple_message_capable = 0
self.msi_multiple_message_enable = 0
self.msi_message_address = 0
self.msi_message_upper_address = 0
self.msi_message_data = 0
self.msi_mask_bits = 0
self.msi_pending_bits = 0
self.register_capability(MSI_CAP_ID, 6, self.read_msi_cap_register, self.write_msi_cap_register)
"""
MSI Capability (64 bit with per-vector masking) MSI Capability (64 bit with per-vector masking)
31 0 31 0
@ -1359,42 +1284,44 @@ class MSI64MaskCapability(object):
def read_msi_cap_register(self, reg): def read_msi_cap_register(self, reg):
if reg == 0: if reg == 0:
# Message control # Message control
val = 0x01800000 val = 0x00000000
if self.msi_enable: val |= 1 << 16 if self.msi_enable: val |= 1 << 16
val |= (self.msi_multiple_message_capable & 0x7) << 17 val |= (self.msi_multiple_message_capable & 0x7) << 17
val |= (self.msi_multiple_message_enable & 0x7) << 20 val |= (self.msi_multiple_message_enable & 0x7) << 20
if self.msi_64bit_address_capable: val |= 1 << 23
if self.msi_per_vector_mask_capable: val |= 1 << 24
return val return val
elif reg == 1: elif reg == 1:
# Message address # Message address
return self.msi_message_address & 0xfffffffc return self.msi_message_address & 0xfffffffc
elif reg == 2: elif reg == 2 and self.msi_64bit_address_capable:
# Message upper address # Message upper address
return self.msi_message_upper_address & 0xffffffff return (self.msi_message_address >> 32) & 0xffffffff
elif reg == 3: elif reg == (3 if self.msi_64bit_address_capable else 2):
# Message data # Message data
return self.msi_message_data & 0xffff return self.msi_message_data & 0xffff
elif reg == 4: elif reg == (4 if self.msi_64bit_address_capable else 3) and self.msi_per_vector_mask_capable:
# Mask bits # Mask bits
return self.msi_mask_bits & 0xffffffff return self.msi_mask_bits & 0xffffffff
elif reg == 5: elif reg == (5 if self.msi_64bit_address_capable else 4) and self.msi_per_vector_mask_capable:
# Pending bits # Pending bits
return self.msi_pending_bits & 0xffffffff return self.msi_pending_bits & 0xffffffff
def write_msi_cap_register(self, reg, write, offset=None): def write_msi_cap_register(self, reg, data, mask):
if reg == 0: if reg == 0:
# Message control # Message control
if mask & 0x4: self.msi_enable = (data & 1 << 16 != 0) if mask & 0x4: self.msi_enable = (data & 1 << 16 != 0)
if mask & 0x4: self.msi_multiple_message_enable = (data >> 20) & 0x7 if mask & 0x4: self.msi_multiple_message_enable = (data >> 20) & 0x7
elif reg == 1: elif reg == 1:
# Message address # Message address
self.msi_message_address = byte_mask_update(self.msi_message_address, mask, data) & 0xfffffffc self.msi_message_address = byte_mask_update(self.msi_message_address, mask, data) & 0xfffffffffffffffc
elif reg == 2: elif reg == 2 and self.msi_64bit_address_capable:
# Message upper address # Message upper address
self.msi_message_upper_address = byte_mask_update(self.msi_message_upper_address, mask, data) & 0xffffffff self.msi_message_address = byte_mask_update(self.msi_message_address, mask << 4, data << 32) & 0xfffffffffffffffc
elif reg == 3: elif reg == (3 if self.msi_64bit_address_capable else 2):
# Message data # Message data
self.msi_message_data = byte_mask_update(self.msi_message_data, mask & 0x3, data) & 0xffff self.msi_message_data = byte_mask_update(self.msi_message_data, mask & 0x3, data) & 0xffff
elif reg == 4: elif reg == (4 if self.msi_64bit_address_capable else 3) and self.msi_per_vector_mask_capable:
# Mask bits # Mask bits
self.msi_mask_bits = byte_mask_update(self.msi_mask_bits, mask, data) & 0xffffffff self.msi_mask_bits = byte_mask_update(self.msi_mask_bits, mask, data) & 0xffffffff

View File

@ -643,10 +643,13 @@ class TLP_us(TLP):
) )
class UltrascalePCIeFunction(Endpoint, MSI64MaskCapability, MSIXCapability): class UltrascalePCIeFunction(Endpoint, MSICapability, MSIXCapability):
def __init__(self): def __init__(self):
super(UltrascalePCIeFunction, self).__init__() super(UltrascalePCIeFunction, self).__init__()
self.msi_64bit_address_capable = 1
self.msi_per_vector_mask_capable = 0
self.register_capability(PCIE_CAP_ID, offset=48) self.register_capability(PCIE_CAP_ID, offset=48)
self.register_capability(MSIX_CAP_ID, offset=44) self.register_capability(MSIX_CAP_ID, offset=44)
self.register_capability(PM_CAP_ID, offset=32) self.register_capability(PM_CAP_ID, offset=32)