从 BLF 文件中解码 J1939 数据
此示例说明如何在 MATLAB® 中从 BLF 文件中导入和解码 J1939 数据进行分析。
此示例中使用的 BLF 文件是使用 Vector 的 CANoe 基于 System Configuration (J1939) 采样生成的。此示例还使用 Vector 采样配置提供的 CAN 数据库文件 Powertrain_J1939_BLF.dbc
。
调查 BLF 文件
检索和查看有关 BLF 文件的信息。函数 blfinfo
解析有关 Vector 二进制记录格式 BLF 文件的格式和内容的一般信息,并将信息以结构体形式返回。
binf = blfinfo("LoggingBLF_J1939.blf")
binf = struct with fields:
Name: "LoggingBLF_J1939.blf"
Path: "C:\Users\michellw\OneDrive - MathWorks\Documents\MATLAB\Examples\vnt-ex52809946\LoggingBLF_J1939.blf"
Application: "CANoe"
ApplicationVersion: "12.0.167"
Objects: 131119
StartTime: 21-Apr-2021 10:05:13.232
EndTime: 21-Apr-2021 10:09:14.344
ChannelList: [2×3 table]
请注意,ChannelList 属性表示在 BLF 文件中引用 2 个通道,ChannelID 值为 1 和 2。感兴趣的 J1939 动力总成系统数据是从 CAN2 网络记录的,因此此示例重点关注 ChannelID 2。
binf.ChannelList
ans=2×3 table
ChannelID Protocol Objects
_________ ________ _______
1 "CAN" 92720
2 "CAN" 26054
J1939 是基于 CAN 协议构建的协议。参数组 (PG) 是属于同一主题并共享相同传输速率的一组参数,例如 ET1_EMS PG 的 EngCoolantTemp、EngFuelTemp、EngTurboOilTemp 等(请参阅下面的 signalTimetables 中的 ET1_EMS PG)。 每个参数组都通过一个称为参数组编号 (PGN) 的唯一编号进行寻址。J1939 PG 是作为 CAN 帧传输的。
从 BLF 文件中读取 J1939 CAN 数据帧
使用 blfread
函数将来自通道 2 的所有数据读入一个时间表。该时间表的每行均表示来自总线的一个原始 CAN 帧。
canData = blfread("LoggingBLF_J1939.blf", 2)
canData=26054×8 timetable
Time ID Extended Name Data Length Signals Error Remote
____________ _________ ________ __________ ___________________________________ ______ ____________ _____ ______
0.000568 sec 418316262 true {0×0 char} {[ 105 52 169 232 0 131 0 16]} 8 {0×0 struct} false false
0.27057 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
0.29057 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
0.30058 sec 418382822 true {0×0 char} {[ 255 0 255 255 255 255 255 255]} 8 {0×0 struct} false false
0.30116 sec 419327206 true {0×0 char} {[255 255 255 255 255 255 255 255]} 8 {0×0 struct} false false
0.31057 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
0.33057 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
0.35058 sec 418382822 true {0×0 char} {[ 255 0 255 255 255 255 255 255]} 8 {0×0 struct} false false
0.35115 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
0.35173 sec 419327206 true {0×0 char} {[255 255 255 255 255 255 255 255]} 8 {0×0 struct} false false
0.3523 sec 419361254 true {0×0 char} {[ 255 0 0 12 255 255 224 255]} 8 {0×0 struct} false false
0.37057 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
0.39057 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
0.40058 sec 418382822 true {0×0 char} {[ 255 0 255 255 255 255 255 255]} 8 {0×0 struct} false false
0.40116 sec 419327206 true {0×0 char} {[255 255 255 255 255 255 255 255]} 8 {0×0 struct} false false
0.41057 sec 418383078 true {0×0 char} {[ 255 255 255 208 7 255 255 255]} 8 {0×0 struct} false false
⋮
使用 DBC 文件解码 J1939 参数组
使用 canDatabase
函数打开数据库文件。
canDB = canDatabase("Powertrain_J1939_BLF.dbc")
canDB = Database with properties: Name: 'Powertrain_J1939_BLF' Path: 'C:\Users\michellw\OneDrive - MathWorks\Documents\MATLAB\Examples\vnt-ex52809946\Powertrain_J1939_BLF.dbc' Nodes: {12×1 cell} NodeInfo: [12×1 struct] Messages: {93×1 cell} MessageInfo: [93×1 struct] Attributes: {3×1 cell} AttributeInfo: [3×1 struct] UserData: []
j1939ParameterGroupTimetable
函数使用数据库将原始 CAN 数据解码为 PG、PGN 和信号。将二进制记录格式数据的时间表转换为 Vehicle Network Toolbox™ J1939 参数组时间表。
j1939PGTimetable = j1939ParameterGroupTimetable(canData, canDB)
j1939PGTimetable=26030×8 timetable
Time Name PGN Priority PDUFormatType SourceAddress DestinationAddress Data Signals
____________ ________ _____ ________ _____________________ _____________ __________________ ___________________________________ ____________
0.000568 sec ACL 60928 6 Peer-to-Peer (Type 1) 230 255 {[ 105 52 169 232 0 131 0 16]} {1×1 struct}
0.27057 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
0.29057 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
0.30058 sec EEC2_EMS 61443 6 Broadcast (Type 2) 230 255 {[ 255 0 255 255 255 255 255 255]} {1×1 struct}
0.30116 sec TCO1_TCO 65132 6 Broadcast (Type 2) 230 255 {[255 255 255 255 255 255 255 255]} {1×1 struct}
0.31057 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
0.33057 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
0.35058 sec EEC2_EMS 61443 6 Broadcast (Type 2) 230 255 {[ 255 0 255 255 255 255 255 255]} {1×1 struct}
0.35115 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
0.35173 sec TCO1_TCO 65132 6 Broadcast (Type 2) 230 255 {[255 255 255 255 255 255 255 255]} {1×1 struct}
0.3523 sec CCVS_EMS 65265 6 Broadcast (Type 2) 230 255 {[ 255 0 0 12 255 255 224 255]} {1×1 struct}
0.37057 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
0.39057 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
0.40058 sec EEC2_EMS 61443 6 Broadcast (Type 2) 230 255 {[ 255 0 255 255 255 255 255 255]} {1×1 struct}
0.40116 sec TCO1_TCO 65132 6 Broadcast (Type 2) 230 255 {[255 255 255 255 255 255 255 255]} {1×1 struct}
0.41057 sec EEC1_EMS 61444 6 Broadcast (Type 2) 230 255 {[ 255 255 255 208 7 255 255 255]} {1×1 struct}
⋮
查看时间表的第三个 PG 中存储的信号数据,这是“EEC1_EMS”PG 的一个实例。
signalData = j1939PGTimetable.Signals{3}
signalData = struct with fields:
EngDemandPercentTorque: 130
EngStarterMode: 15
SrcAddrssOfCtrllngDvcForEngCtrl: 255
EngSpeed: 250
ActualEngPercentTorque: 130
DriversDemandEngPercentTorque: 130
EngTorqueMode: 15
重新打包并可视化感兴趣的信号值
使用 j1939SignalTimetable
函数将来自总线上每个唯一 PGN 的信号数据重新打包到一个信号时间表中。此示例根据 J1939 PG 时间表为两个感兴趣的 PG(“EEC1_EMS”和“TCO1_TCO”)创建两个单独的信号时间表。
signalTimetable1 = j1939SignalTimetable(j1939PGTimetable, "ParameterGroups", "EEC1_EMS")
signalTimetable1=12043×7 timetable
Time EngDemandPercentTorque EngStarterMode SrcAddrssOfCtrllngDvcForEngCtrl EngSpeed ActualEngPercentTorque DriversDemandEngPercentTorque EngTorqueMode
___________ ______________________ ______________ _______________________________ ________ ______________________ _____________________________ _____________
0.27057 sec 130 15 255 250 130 130 15
0.29057 sec 130 15 255 250 130 130 15
0.31057 sec 130 15 255 250 130 130 15
0.33057 sec 130 15 255 250 130 130 15
0.35115 sec 130 15 255 250 130 130 15
0.37057 sec 130 15 255 250 130 130 15
0.39057 sec 130 15 255 250 130 130 15
0.41057 sec 130 15 255 250 130 130 15
0.43057 sec 130 15 255 250 130 130 15
0.45115 sec 130 15 255 250 130 130 15
0.47057 sec 130 15 255 250 130 130 15
0.49057 sec 130 15 255 250 130 130 15
0.51057 sec 130 15 255 250 130 130 15
0.53057 sec 130 15 255 250 130 130 15
0.55115 sec 130 15 255 250 130 130 15
0.57057 sec 130 15 255 250 130 130 15
⋮
signalTimetable2 = j1939SignalTimetable(j1939PGTimetable, "ParameterGroups", "TCO1_TCO")
signalTimetable2=4817×14 timetable
Time TachographVehicleSpeed TachographOutputShaftSpeed DirectionIndicator TachographPerformance HandlingInformation SystemEvent DriverCardDriver2 Driver2TimeRelatedStates Overspeed DriverCardDriver1 Driver1TimeRelatedStates DriveRecognize Driver2WorkingState Driver1WorkingState
___________ ______________________ __________________________ __________________ _____________________ ___________________ ___________ _________________ ________________________ _________ _________________ ________________________ ______________ ___________________ ___________________
0.30116 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.35173 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.40116 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.45173 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.50116 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.55173 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.60116 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.65173 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.70116 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.75173 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.80116 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.85173 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.90116 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
0.95173 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
1.0012 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
1.0517 sec 256 8191.9 3 3 3 3 3 15 3 3 15 3 7 7
⋮
您也可以选择将整个 J1939 PG 时间表转换为一个结构体,该结构体包含每个单独 PG 的多个 J1939 信号时间表,并对其进行索引以获取特定 PG 的数据。
signalTimetables = j1939SignalTimetable(j1939PGTimetable)
signalTimetables = struct with fields:
ACL: [1×14 timetable]
CCVS_EMS: [2408×19 timetable]
DD: [240×5 timetable]
EEC1_EMS: [12043×7 timetable]
EEC2_EMS: [4817×10 timetable]
ET1_EMS: [240×6 timetable]
HOURS_EMS: [240×2 timetable]
LFC_EMS: [480×2 timetable]
SERV: [240×6 timetable]
TCO1_TCO: [4817×14 timetable]
VDHR_EMS: [240×2 timetable]
VI_EMS: [24×1 timetable]
VW_SSC: [240×4 timetable]
signalTimetables.EEC1_EMS
ans=12043×7 timetable
Time EngDemandPercentTorque EngStarterMode SrcAddrssOfCtrllngDvcForEngCtrl EngSpeed ActualEngPercentTorque DriversDemandEngPercentTorque EngTorqueMode
___________ ______________________ ______________ _______________________________ ________ ______________________ _____________________________ _____________
0.27057 sec 130 15 255 250 130 130 15
0.29057 sec 130 15 255 250 130 130 15
0.31057 sec 130 15 255 250 130 130 15
0.33057 sec 130 15 255 250 130 130 15
0.35115 sec 130 15 255 250 130 130 15
0.37057 sec 130 15 255 250 130 130 15
0.39057 sec 130 15 255 250 130 130 15
0.41057 sec 130 15 255 250 130 130 15
0.43057 sec 130 15 255 250 130 130 15
0.45115 sec 130 15 255 250 130 130 15
0.47057 sec 130 15 255 250 130 130 15
0.49057 sec 130 15 255 250 130 130 15
0.51057 sec 130 15 255 250 130 130 15
0.53057 sec 130 15 255 250 130 130 15
0.55115 sec 130 15 255 250 130 130 15
0.57057 sec 130 15 255 250 130 130 15
⋮
为了可视化感兴趣的信号,可以绘制信号时间表中的变量随时间变化的图,以便进一步分析。对于此示例,请查看来自 EEC1_EMS PG 的 EngineSpeed 信号。
plot(signalTimetable1.Time, signalTimetable1.EngSpeed, "r") title("{\itEngineSpeed} signal from {\itEEC1\_EMS} PG", "FontWeight", "bold") xlabel("Timestamp") ylabel("Engine Speed")
关闭文件
通过从工作区中清除 DBC 文件的变量,关闭对该 DBC 文件的访问。
clear canDB