部件管理框架设计文档
框架名称为devmon,使用C语言实现。整个模块运行在arm64架构,给予Linux系统运行。基于libmcpp的C++开发框架进行开发, 比如使用如下模块;
- 使用 mc::variant 和 mc::dict 替代 std::map<std::string, std::string>
- 使用 mc::signal 实现设备和接口的事件通知
- 使用 mc::application 实现设备管理器
1. 模块类图
devmon 采用模块化、插件化的架构设计,支持动态加载设备驱动。主要包含以下核心组件:device_manager, device_driver, device_topo三个模块。
模块之前类图关系如下:
@startuml
class device_manager {
m_devices
m_drivers
add_device()
remove_device()
register_device()
get_device()
get_all_devices()
parse_config()
load_driver()
}
class task {
condation
filter()
handler()
}
class executor {
run()
post(task)
}
class device_driver_base {
m_name
m_object
m_childs
probe()
remove()
get_path()
get_name()
probe_child()
get_childs()
add_child()
}
class property {
m_value
set_value()
get_value()
}
class device_object {
m_path
init_from_config()
init_path()
}
package pice_nic_card {
class PCIeNicCard {
m_object
probe_child()
create_device_object()
}
class NetworkPort {
m_object
probe_child()
create_device_object()
}
class OpticalModule {
m_object
create_device_object()
}
class PCIeNicCardObject {
m_object
init_from_config()
init_path()
}
class NetworkPortObject {
m_object
init_from_config()
init_path()
}
class OpticalModuleObject {
m_object
init_from_config()
init_path()
}
}
class device_topo {
topo
add_topo()
delete_topo()
}
class mellanox_cx5 {
}
device_manager ..> device_driver_base
device_manager .right.> device_topo
device_driver_base "1" *.right. "1" device_object
device_object "1" *-right- "n" property
PCIeNicCard -up-|> device_driver_base
NetworkPort -up-|> device_driver_base
OpticalModule -up-|> device_driver_base
PCIeNicCard "1" *-right- "n" NetworkPort
NetworkPort "1" *-right- "1" OpticalModule
PCIeNicCard "1" *-- "1" PCIeNicCardObject
NetworkPort "1" *-- NetworkPortObject
OpticalModule "1" *-- OpticalModuleObject
mellanox_cx5 "1" *-- "1" PCIeNicCard
device_manager .left.> mellanox_cx5
@enduml
devmon 时序图
@startuml
hwdiscory -> devmon: 分发csr,conn
create csr
devmon -> csr: 获取Unit信息
devmon -> adapters: 查找adapters
devmon -> adapters: 获取dds信息
@enduml
2 模块实现
2.1 device_manager模块
作为核心模块主要实现device_manager类,通过add_device()接口添加设备,参数为适配配置文件,格式为json,配置名称为csr_cfg。
- 通过csr_cfg中的compatible属性找到对应的device_driver的so文件实现运行时动态加载
- 调用device_driver中的probe()函数实例化设备
- 调用device_topo模块的add_topo方法将配置文件中的硬件topo信息添加到topo属性中。
2.1.1 配置文件解析
device_manager模块的parse_config方法必须严格按照3.1节中定义的CSR数据配置格式进行解析。具体要求如下:
-
配置文件格式必须为JSON格式
-
解析过程需要提取以下关键信息:
- Unit.Type: 设备类型
- Unit.Name: 设备名称
- Unit.Compatible: 兼容驱动列表, 用于查找对应的驱动
- Objects: 包含设备及其子设备的配置信息
-
解析后的配置数据应当保留层级关系,使用明确的标识来区分对象、接口和属性.
-
device_manager根据csr中的配置, 新建一个运行时dict, 将数据csr中的实际值更新进去, 交给device_driver。
2.1.2 驱动加载与配置传递
device_manager模块的load_driver方法负责根据配置中的Compatible属性加载对应的驱动。驱动加载和配置传递的具体要求如下:
-
驱动加载规则:
- 根据Compatible属性中的第一个值确定驱动名称,例如"Mellanox,CX5"对应的驱动名称为"Mellanox_CX5"
- 驱动文件名格式为"lib<驱动名称>.so",例如"libMellanox_CX5.so"
- 驱动文件应位于系统库路径或指定的驱动目录中
- 如果第一个值没找到到,再使用第二个值匹配;
- 另外如果当前驱动已经加载,不需要重复加载,也就是要先检查是否已经加载。
- 再固定目录查找驱动,而且已加载的驱动使用驱动名称保存。
-
配置传递:
- 解析后的配置数据应当完整传递给驱动的probe方法
-
设备添加流程:
- 解析配置文件,提取设备类型、名称和兼容驱动列表
- 根据兼容驱动列表加载对应的驱动
- 将解析后的配置数据传递给驱动的probe方法
- 驱动根据配置创建设备对象
- 驱动探测子设备,并创建子设备对象
- 设备管理器注册设备,并添加拓扑信息
通过这种方式,device_manager模块能够正确解析CSR数据配置,加载对应的驱动,并将配置数据传递给驱动,从而实现设备的动态加载和管理。
2.2 device_driver模块
设备用户态驱动实现,主要实现device_driver_base
- device_driver_base的probe函数实现device_driver的csr解析后的dict数据保存。
- interface_driver_base中实现probe()函数完成本对象实例化。
- interface_driver_base中实现remove函数完成对象删除。
- device_driver_base实现probe_child() 函数,实现子对象的创建,比如NetworkPort属于PCIeNicCard的子对象。一级一级完成子对象创建。通过子对象名在dict配置中找到子对象的配置。
2.2.1 对象父子关系实现
单个部件是存在多个子功能特性,之间存在关联关系。所有的子功能特性都是通过device_driver_base对象管理,通过childs属性来管理特性之前的父子关系。
例如,CX5NicCard驱动会创建NetworkPort子设备,NetworkPort驱动会创建OpticalModule子设备,形成一个三层的树状结构。
2.3 device_object模块
device_object模块保存设备的所有数据。csr配置解析后创建object对象。object对象完成设备驱动和对外接口的关联。设备驱动实现部件硬件管理业务,将数据更新到object。对外接口通过object对象来获取部件的硬件信息。比如object对象再关联到设备树,通过dbus对外提供交互接口。
2.3.1 device_object类设计
- 基本属性类 property类的vlaue都是mc::variant类型
class property {
vlaue
set_value()
}
- device_object类定义 device_object类的所有属性都是property类,并提供统一的初始化接口
class device_object {
property path
init_from_config(const mc::dict& config)
init_path(const mc::dict& parent)
}
device_object类是所有设备对象的基类,提供了统一的接口和基本属性。它采用以下设计:
-
统一接口:device_object类定义了两个纯虚函数,所有子类必须实现这些函数:
init_from_config(const mc::dict& config):通过CSR配置对象初始化设备对象的属性init_path(const mc::dict& parent):初始化设备对象的路径,从parent对象中获取必要的路径信息
-
基本属性:device_object类包含一个基本属性:
path:设备路径属性,用于标识设备在系统中的位置
-
多态性:通过使用虚函数,device_object类支持多态,可以通过基类指针调用子类的实现
这种设计使得所有设备对象类(如PCIeNicCardObject、NetworkPortObject和OpticalModuleObject)都使用相同的接口初始化路径和配置,提高了代码的一致性和可维护性。同时,通过在父类中声明这些函数,我们可以在父类中实现一些通用的功能,减少子类中的重复代码。
class device_object {
public:
/**
* @brief 析构函数
*/
virtual ~device_object() = default;
/**
* @brief 通过CSR配置对象初始化设备对象的属性
*
* @param config CSR配置对象,由device_manager解析后的dict数据
* @return bool 初始化是否成功
*/
virtual bool init_from_config(const mc::dict& config) = 0;
/**
* @brief 初始化设备对象的路径
*
* @param parent 父对象,包含必要的路径信息
* @return bool 初始化是否成功
*/
virtual bool init_path(const mc::dict& parent) = 0;
// 平铺的属性
property path; ///< 设备路径属性
};
这种设计使得所有设备对象类(如PCIeNicCardObject、NetworkPortObject和OpticalModuleObject)都使用相同的接口初始化路径和配置,提高了代码的一致性和可维护性。子类根据自己的需求实现这些接口,例如:
- PCIeNicCardObject的init_path函数从parent对象中获取SystemId和Id,然后构造设备路径
- NetworkPortObject的init_path函数从parent对象中获取ParentPath和Id,然后构造设备路径
- OpticalModuleObject的init_path函数从parent对象中获取ParentPath,然后构造设备路径
这种设计符合面向对象的原则,特别是"开闭原则"(对扩展开放,对修改关闭)和"里氏替换原则"(子类可以替换父类)。
2.4 device_topo模块
保存设备的topo结构,在device_manager模块的add_device()函数中调用,将csr中的topo配置通过add_topo()函数实现topo创建。保存在topo变量中。
3 PCIeNicCard 部件管理实现
3.1 csr数据配置
部件的csr配置文件,配置中没有定义的字段使用默认值。Unit描述当前部件的类型和compatible内容,使用Compatible类找到驱动。Objects中描述的是device_driver_base类,再下一级为device_driver_base类包含的接口配置数据,初始化在device_object对象中。
{
"FormatVersion" : "3.00",
"DataVersion": "3.00",
"Unit": {
"Type": "PCIeNicCard",
"Name": "PCIeNicCard_1",
"Compatible": ["Mellanox,CX5", "Mellanox,CXX"]
},
"Objects": {
"PCIeNicCard_1": {
"PCIeDevice" : {
"DeviceName": "PCIe Card ${Slot} (MCX515A-CCAT)",
"FunctionClass": 2,
"VendorId": "0x15b3",
"DeviceId": "0x1017",
"SubSystemVendorId": "0x15b3",
"SubSystemDeviceId": "0x0006",
"Location": "${Location}",
"Slot": "${Slot}",
"Segment": "${Segment}",
"SocketId": "${SocketId}",
"Bus": "${Bus}",
"Device": "${Device}",
"Function": "${Function}"
},
"PCIeCard": {
"Name": "MCX515A-CCAT",
"Model": "CX5",
"Manufacturer": "Mellanox",
"PartNumber": "06310149",
"Description": "1*100GE"
},
"NetworkAdapter" {
"Manufacturer": "Mellanox",
"ChipModel": "CX5",
"Description": "1*100GE",
"ChipVendor": "Mellanox",
"NetworkPortCount": 1,
"SupportedMctp": false,
"SupportedLldp": false,
"Type": 3
},
"Board": {
"Location" : "${Location}",
"Slot": "${Slot}",
"Description": "1*100GE",
"Type": "PCIeCard",
"PartNumber": "06310149",
},
"NetworkAdapter.Cooling": {
"TemperatureStatus": 2,
"MaxSFPTemperatureStatus": 2
},
"Fru": {
"FruId": 1,
"Name": "MCX515A-CCAT",
"PcbId": "#/Accessor_PcbId.Value",
"GroupId": "${GroupId}"
}
},
"NetworkPort_0": {
"NetworkPort": {
"PortId": 0,
"NetDevFuncType": 1,
"MediumType": "FiberOptic",
"MaxSpeedSupported": "25GE",
},
"NetworkPort.LinkInfo": {
"AutoSpeedNegotiation": false
}
},
"OpticalModule_0": {
}
}
}
3.2 实现详细说明
- PCIeNicCard的定义如下,其中interfaces里面的具体数据在csr配置中获取。比如PCIeDevice这个interface的数据在csr的PCIeDevice中获取。
{
"path": "/Systems/:SystemdId/PCIeNic/:ID",
"interfaces": [
"PCIeDevice",
"PCIeCard",
"PCIeDevice.Bandwidth",
"NetworkAdapter",
"NetworkAdapter.FaultStatus",
"NetworkAdapter.Cooling",
"NetworkAdapter.LogCollection",
"Board",
"Fru",
]
}
这里描述PCIeNicCard部件。PCIeNicCard的device_object实例化对象。path属性中存在动态参数,会在csr解析是进行动态填充。初始化PCIeNIcCard的device_object对象时,将interface对象属于自定义对象,只保存属性配置,不提供具体的交互接口。
忽略对象名中的bmc.dev字段。properties中描述了所有属性的信息,包括类型,读写,描述等
{
"bmc.dev.PCIeDevice": {
"properties": {
"DeviceName": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "设备资源名称"
},
"FunctionClass": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "功能分类(0:未知、1:RAID、2:网卡、3:GPU卡、4:存储卡(SSD卡/M.2卡)、5:SDI卡、6:加速卡、7:扩展卡(PCIe Riser)、8:FPGA卡、9:NPU卡、10:IB卡)"
},
"VendorId": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "制造商ID"
},
"DeviceId": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "设备ID"
},
"SubSystemVendorId": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "子厂商ID"
},
"SubSystemDeviceId": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "子设备ID"
},
"Location": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "当前PCIe的物理位置,如PCieRiser1,ExpBoard等"
},
"Slot": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "PCIe设备的物理槽位号"
},
"Segment": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "用于多PCI Bridge场景的编号,每一个Segment对应一个PCI Bus空间"
},
"SocketId": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "PCIe设备所属CPU ID"
},
"Bus": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "PCIe Root Port的总线号"
},
"Device": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "PCIe Root Port的设备号"
},
"Function": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "PCIe Root Port的功能号"
},
"DevBus": {
"baseType": "U8",
"readOnly": false,
"options": {
"emitsChangedSignal": "false"
},
"description": "设备的总线号"
},
"DevDevice": {
"baseType": "U8",
"readOnly": false,
"options": {
"emitsChangedSignal": "false"
},
"description": "设备的设备号"
},
"DevFunction": {
"baseType": "U8",
"readOnly": false,
"options": {
"emitsChangedSignal": "false"
},
"description": "设备的功能号"
}
}
},
"bmc.dev.PCIeCard": {
"properties": {
"Name": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "PCIE标卡产品名称"
},
"Model": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "PCIE标卡产品型号"
},
"Manufacturer": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "厂商"
},
"PartNumber": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "部件编码"
}
}
},
"bmc.dev.Board": {
"properties": {
"Location": {
"baseType": "String",
"readOnly": true,
"description": "所在板卡位置",
"options": {
"emitsChangedSignal": "const"
}
},
"Slot": {
"baseType": "U8",
"readOnly": true,
"description": "槽位号",
"options": {
"emitsChangedSignal": "const"
}
},
"Name": {
"baseType": "String",
"readOnly": true,
"description": "板名",
"options": {
"emitsChangedSignal": "const"
}
},
"Description": {
"baseType": "String",
"readOnly": true,
"description": "板卡具体描述",
"options": {
"emitsChangedSignal": "const"
}
},
"Id": {
"baseType": "U16",
"readOnly": true,
"description": "board id,天池组件为65535",
"options": {
"emitsChangedSignal": "const"
}
},
"Type": {
"baseType": "String",
"readOnly": true,
"description": "板卡类型全名,例如 EXpBoard CpuBoard",
"options": {
"emitsChangedSignal": "const"
}
},
"PartNumber": {
"baseType": "String",
"readOnly": true,
"description": "部件号",
"options": {
"emitsChangedSignal": "const"
}
},
"LogicRunningStatus": {
"baseType": "U8",
"readOnly": true,
"description": "板上逻辑状态, 0:正常运行,1状态异常",
"options": {
"emitsChangedSignal": "true"
}
},
"CurrentUpgradeStatus": {
"baseType": "U8",
"readOnly": true,
"description": "0表示未在升级,1:mcu正在升级,2cpld正在升级",
"options": {
"emitsChangedSignal": "true"
}
}
},
"methods": {}
},
"bmc.dev.NetworkAdapter": {
"properties": {
"ChipModel": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡芯片号"
},
"Description": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡描述信息"
},
"ChipVendor": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡芯片生产厂商"
},
"NetworkPortCount": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡下的网口数量"
},
"SupportedMctp": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡芯片是否支持mctp协议"
},
"SupportedLldp": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡芯片是否支持通过mctp接收lldp报文"
},
"FirmwareVersion": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡固件版本"
}
}
},
"bmc.dev.PCIeDevice.Bandwidth": {
"properties": {
"LinkWidthAbility": {
"baseType": "String",
"readOnly": true,
"description": "最大链路带宽"
},
"LinkWidth": {
"baseType": "String",
"readOnly": true,
"description": "链路带宽"
},
"LinkSpeedCapability": {
"baseType": "String",
"readOnly": true,
"description": "最大链路速率"
},
"LinkSpeed": {
"baseType": "String",
"readOnly": true,
"description": "链路速率"
}
}
},
"bmc.dev.NetworkAdapter.Cooling": {
"properties": {
"TemperatureCelsius": {
"baseType": "S16",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "网卡芯片温度"
},
"TemperatureStatus": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "网卡芯片温度获取状态"
},
"MaxSFPTemperatureCelsius": {
"baseType": "S16",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "网卡光模块温度最大值,供调速使用"
},
"MaxSFPTemperatureStatus": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "网卡光模块温度最大值获取状态,供调速使用"
}
}
},
"bmc.dev.NetworkAdapter.FaultStatus": {
"properties": {
"FaultCode": {
"baseType": "U16[]",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡故障码列表"
},
"FaultState": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡故障状态 0:正常;1:故障"
}
}
},
"bmc.dev.NetworkAdapter.LogCollection": {
"methods": {
"DumpErrorLog": {
"req": {
"Path": {
"baseType": "String",
"description": "Dump日志文件路径"
}
},
"rsp": {
"TaskId": {
"baseType": "U32",
"description": "DumpErrorLog Task Id"
}
}
},
"DumpLastWordLog": {
"req": {
"Path": {
"baseType": "String",
"description": "Dump日志文件路径"
}
},
"rsp": {
"TaskId": {
"baseType": "U32",
"description": "DumpLastWordLog Task Id"
}
}
},
"DumpRunningLog": {
"req": {
"Path": {
"baseType": "String",
"description": "Dump日志文件路径"
}
},
"rsp": {
"TaskId": {
"baseType": "U32",
"description": "DumpRunningLog Task Id"
}
}
}
}
}
}
- NetworkPort的object对象定义, 是PCIeNicCard的子对象,实现逻辑和PCIeNicCard一样的。
"NetworkPort": {
"path": "${prefix}/NetworkPort/:Id",
"Interfaces":[
"NetworkPort",
"NetworkPort.LinkInfo",
"NetworkPort.DataCenterBridging",
"NetworkPort.LLDPReceive",
"NetworkPort.Metrics"
]
}
- NetworkPort对象包含的interface对象
{
"bmc.dev.NetworkPort": {
"properties": {
"PortId": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "当前网卡上的网口ID"
},
"MACAddress": {
"baseType": "String",
"readOnly": false,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口的mac地址"
},
"PermanentMACAddress": {
"baseType": "String",
"readOnly": false,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口的初始mac地址(当前NIC卡是通过bios设置的)"
},
"BDF": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口的总线信息"
},
"NetDevFuncType": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网络设备功能类型 0:Disabled 1:Ethernet 2:FC 4:iSCSI 8:FCoE 16:OPA 32:IB,网口不能同时工作于两种模式"
},
"MediumType": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网络接口类型,电口:Copper;光口:FiberOptic"
},
"MaxSpeedSupported": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口支持的最大速率"
}
}
},
"bmc.dev.NetworkPort.LinkInfo": {
"properties": {
"LinkStatus": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口连接状态,0:nolink;1:linkup;2:linkdown"
},
"SpeedMbps": {
"baseType": "U32",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口链路速率 单位Mbps"
},
"FullDuplex": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口是否开启全双工"
},
"AutoSpeedNegotiation": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网口是否处于自协商模式"
}
}
},
"bmc.dev.NetworkPort.DataCenterBridging": {
"properties": {
"Up2cos": {
"baseType": "U8[]",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "DCB 信息中的 Up2cos(各优先级映射到的cos组)"
},
"Uppgid": {
"baseType": "U8[]",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "DCB 信息中的 Pgid(各优先级带宽组的ID)"
},
"Pgpct": {
"baseType": "U8[]",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "DCB 信息中的 PGPCT(各优先级带宽组的带宽比)"
},
"PgStrict": {
"baseType": "U8[]",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "DCB 信息中的PgStrict(严格优先级)"
},
"Pfcmap": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "DCB 信息中的 Pfcmap(priority-flow-control map)"
}
}
},
"bmc.dev.NetworkPort.LLDPReceive": {
"properties": {
"LLDPEnabled": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "端口LLDP使能模式 false - 未使能 true - 使能"
},
"ChassisId": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "从网络交换机接收到的Chassis ID"
},
"ChassisIdSubtype": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "从网络交换机接收到的Chassis ID类型"
},
"PortId": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "从网络交换机接收到的端口ID"
},
"PortIdSubtype": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "从网络交换机接收到的端口ID类型"
},
"SystemName": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网络交换机名称"
},
"ManagementVlanId": {
"baseType": "U16",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "从网络交换机接收到的VLAN ID"
}
}
},
"bmc.dev.NetworkPort.Metrics": {
"properties": {
"RXFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "获取报文统计信息"
},
"TXFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送的报文统计"
},
"RXUnicastFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "收到的单播报文数量"
},
"RXMulticastFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "收到的多播报文数量"
},
"RXBroadcastFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "收到的广播报文数量"
},
"TXUnicastFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送单播报文数量"
},
"TXMulticastFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送的多播报文数量"
},
"TXBroadcastFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送的广播报文数量"
},
"RXFCSErrors": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "接收到的 Frame Check Sequence 错误数量"
},
"RXUndersizeFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "接收到的超小帧数量"
},
"RXOversizeFrames": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "接收到的巨型帧(大于1518 字节)数量"
},
"TXSingleCollisions": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送的单碰撞帧数量"
},
"TXMultipleCollisions": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送的多碰撞帧数量"
},
"TXLateCollisions": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送的 late 碰撞帧数量"
},
"TXExcessiveCollisions": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "发送的 Excessive 碰撞帧数量"
},
"RXFrameAlignmentErrors": {
"baseType": "U64",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "一个数据帧尾没有形成一个完整的 Byte,即帧长非整数(不能被 8bit 整除),网管上计为接收(发送)对齐错误"
},
"BandwidthUsagePercent": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "网络带宽占用率"
}
}
}
}
- OpticalModule对象定义
OpticalModule是NetworkPort的子类,一一对应。实现逻辑和PCIeNicCard一致,定义如下:
"path": "${prefix}/OpticalModule",
"Interfaces":[
"OpticalModule",
"OpticalModule.Status",
"OpticalModule.Cooling"
]
OpticalModule包含的interface对象定义如下:
{
{
"bmc.dev.OpticalModule": {
"properties": {
"Manufacturer": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "厂商名称"
},
"PartNumber": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "厂商部件名称"
},
"SerialNumber": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "厂商序列号"
},
"ProductionDate": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "生产日期"
},
"TransceiverType": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "收发器类型"
},
"FiberConnectionType": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "传输模式"
},
"WaveLengthNanometer": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "波长"
},
"Type": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块类型"
},
"SupportedSpeedsMbps": {
"baseType": "Double[]",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "支持的速率"
},
"Health": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块健康状态,0:OK;1:Minor; 2:Major; 3:Critical"
},
"Identifier": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块的识别码"
},
"ConnectorType": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块的连接器类型"
},
"MediumType": {
"baseType": "String",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块的介质类型"
},
"TransmissionDistance": {
"baseType": "U16",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "传输距离"
},
"RxLossStatus": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块 Rx 端是否有信号"
},
"TxFaultStatus": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块 Tx 端是否故障"
},
"TypeMatch": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "类型是否匹配"
},
"SpeedMatch": {
"baseType": "Boolean",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "速率是否匹配"
},
"FaultState": {
"baseType": "U32",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "故障状态"
},
"PowerStatus": {
"baseType": "U16",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "功率异常标志位"
},
"SpeedSupported": {
"baseType": "U16",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "网卡支持速率与光模块速率不匹配标志位"
}
}
}
}
"bmc.dev.OpticalModule.Status": {
"properties": {
"SupplyVoltage": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "光模块供电电压"
},
"VoltageUpperThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "电压下限阈值"
},
"VoltageLowerThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "电压上限阈值"
},
"RxPowerMilliWatts": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Rx接收功率"
},
"RxPowerLowerThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Rx接收功率下限阈值"
},
"RXPowerUpperThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Rx接收功率上限阈值"
},
"TXPowerMilliWatts": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Tx发送功率"
},
"TXPowerLowerThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Tx发送功率下限阈值"
},
"TXPowerUpperThresholdCritical": {
"baseType": "Double[]",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Tx发送功率上限阈值"
},
"TXBiasCurrentMilliAmps": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Tx接收电流"
},
"TXBiasCurrentLowerThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Tx接收电流下限阈值"
},
"TXBiasCurrentUpperThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "false"
},
"description": "Tx接收电流上限阈值"
}
}
},
"bmc.dev.OpticalModule.Cooling": {
"properties": {
"TemperatureCelsius": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "光模块温度"
},
"TemperatureStatus": {
"baseType": "U8",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "光模块温度获取状态"
},
"TemperatureLowerThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "温度下限阈值"
},
"TemperatureUpperThresholdCritical": {
"baseType": "Double",
"readOnly": true,
"options": {
"emitsChangedSignal": "true"
},
"description": "温度上限阈值"
}
}
}
}
3.3 驱动类实现
在新的设计中,驱动类只负责设备的业务逻辑,而不需要关心数据的存储和管理。驱动类包括:
- PCIeNicCard:负责网卡的业务逻辑
- NetworkPort:负责网络端口的业务逻辑
- OpticalModule:负责光模块的业务逻辑
3.3.3 设备对象实现详细说明
设备对象(device_object)是承载设备配置和状态的核心类,采用嵌套结构设计,以更好地组织和管理设备的各个接口及其属性。以下是设备对象的实现详细说明:
3.3.3.1 嵌套结构设计
每个设备对象类(如PCIeNicCardObject、NetworkPortObject、OpticalModuleObject)都采用嵌套结构来表示不同的接口:
- 接口结构体:每个接口(如PCIeDevice、NetworkPort.LinkInfo等)都定义为一个独立的结构体,包含该接口的所有属性。
- 命名规范:接口结构体的命名采用小写加下划线的方式(snake_case),并添加"_s"后缀,如
pcie_device_s、network_port_link_info_s等。 - 属性命名:接口内的属性名称采用PascalCase命名方式,与CSR配置中的属性名保持一致,如
DeviceName、LinkStatus等。
3.3.3.2 路径初始化
每个设备对象都提供了路径初始化方法:
- init_path方法:负责根据设备标识(如ID、槽位号等)和父对象路径构造设备的路径。
- 路径模板:使用包含占位符的路径模板,如"NetworkPort/:Id",在运行时替换占位符。
- 动态参数:支持从配置中提取动态参数,如端口ID、设备位置等,填充到路径模板中。
- 父子关系:子对象的路径通过拼接父对象的路径和自身的路径模板来构建,确保路径层次结构反映对象的父子关系。例如,如果PCIeNicCard的路径是"/Systems/1/PCIeNic/2",那么其子对象NetworkPort的路径可能是"/Systems/1/PCIeNic/2/NetworkPort/0"。
3.3.3.3 配置初始化
设备对象通过init_from_config方法从CSR配置对象初始化其属性:
- 接口提取:使用辅助函数(如
get_network_port_interface_dict)从配置对象中提取特定接口的属性字典。 - 属性初始化:为每个接口定义专门的初始化函数(如
init_network_port、init_optical_module_status等),负责将配置值设置到对应的属性中。 - 错误处理:实现了完善的错误处理机制,包括空配置检查、类型检查和异常捕获,确保初始化过程的健壮性。
3.3.3.4 属性访问
设备对象的属性通过嵌套结构进行组织和访问:
- 接口实例:每个设备对象类包含多个接口实例,如
NetworkPort、NetworkPort_LinkInfo等。 - 属性访问:通过接口实例访问具体属性,如
NetworkPort.PortId、OpticalModule_Status.SupplyVoltage等。 - 属性设置:使用
set_value方法设置属性值,支持各种数据类型(如字符串、整数、浮点数、布尔值等)。
3.3.3.5 异常处理
设备对象实现了全面的异常处理机制:
- 初始化异常:捕获并记录初始化过程中的异常,包括配置解析错误、路径构造错误等。
- 属性访问异常:处理属性访问和设置过程中可能出现的类型不匹配、键不存在等异常。
- 日志记录:使用标准错误流(std::cerr)记录异常信息,便于问题诊断和调试。
通过这种设计,设备对象能够有效地组织和管理设备的各种属性,提供清晰的接口访问方式,并确保数据的一致性和完整性。同时,嵌套结构的设计也使得代码更加模块化和可维护,便于扩展和修改。
实现跨板依赖的实现 --------------------------- 依赖devmon实现统一的调度框架,有adapters来注册任务,由框架统一调度执行。 1、定义全局状态。adapters注册任务时包含全局condition,在条件满足时,devmon才调度具体的任务; 2、注册任务时,包含filter函数和task函数。devmon不关系具体的filter和task实现,只将filter的结果,作为task的输入,来运行task; filter函数用来过滤task执行时需要哪些依赖接口;
1、对象在adapters中是什么形态? 2、通过对象名来统一管理,提供查询接口,通过类名, position查询的接口; 3、通过devmon创建的对象如何关联到dbus对象树; 4、通用类对象如何管理,adapters中如何获取通用类对象,比如chip;PCIeNicCard卡依赖1822_chip来获取核温; 5、通用类对象关联部件对象如何实现,比如event,关联了PCIeNicCard的temp属性
讨论结果 1、对象有factory创建,有manager管理全量对象表;obj产生元表信息; 2、obj管理和dbus不耦合; 3、元表信息格式统一,有adapters实现;
1、devmon常见的obj和框架的对象管理如何关联? 2、obj的格式如何定义? 3、obj对象访问权限控制,devmon的都能获取到,进行查询
1、怎么找so 讨论内容: 1)一个CSR文件就是一个so; 2)使用compatible字段标识SO 3)compatible写在硬件CSR中 遗留问题 compatible怎么定义,规则怎么定义。避免重复
2、so放在那里: 路径命名和compatible之间要有关联关系 预加载通用期间so 遗留问题: 怎么定义so存放规则?
3、mdb_interface兼容 Devmon和driver so之间存在二进制兼容问题.