文章包含了AUTOSAR基础软件(BSW)中DEM模块相关的内容详解。本文从ISO标准,AUTOSAR规范解析,ISOLAR-AB配置以及模块相关代码分析四个维度来帮读者清晰的认识和了解DEM这一基础软件模块。文中涉及的ISOLAR-AB配置以及模块相关代码都是依托于ETAS提供的工具链来配置与生成的,与AUTOSAR规范之间可能会有些许的出入,但总体的功能要点与处理流程都应该是一致的。
DEM模块是汽车诊断的一个部分,这个部分主要包含了诊断中的故障管理功能。模块面对应用组件以及BSW模块上报的故障信息,能够提供故障去抖以及跨上/下电周期的故障状态管理功能,并让集成商自由定义故障以及相关快照和扩展数据,提供了不同的存储策略。本文首先介绍了关于诊断故障管理的一些基础知识,其次以ISO-14229为基础介绍了DEM涉及的部分标准,再次解析了AUTOSAR规范DEM部分内容,然后基于ISOLAR讲述了完整的DEM配置过程,最后介绍了DEM相关的代码。
目录
诊断概述
DEM(Diagnostic Event Manager)名为诊断事件管理模块,它是AUTOSAR诊断服务模块的重要组成部分,主要负责ECU故障的全声明周期管理,包括:
- 提供给SW-C对应Port口通过RTE上报的故障事件,提供给BSW标准接口上报故障事件。
- 采取配置的Debounce策略,判断故障是否有效。
- 故障有效时,把故障相关的信息进行存储。
- 根据故障老化策略以及存储策略,对有效故障进行管理。
- 将故障信息通知到FIM模块,对系统功能进行必要的降级。
DEM模块主要的作用:
- 功能降级/禁止依据:故障信息作为影响ECU运行的关键数据,当发生故障时,ECU应依据故障类型对牵扯的功能进行降级/禁止处理。
- 功能禁止:当高边驱动芯片上报对地短路故障的时候,应该禁止对此高边通道的进一步控制。
- 功能降级:当检测到电机运行过载的时候,应降低驱动PWM驱动占空比,避免电机损坏。
- 下线检测:整车涉及的众多的零部件开发,集成,组装,为了最终整车的质量,在产线电检的流程中,会读取整车的故障码,确保各零部件配合正常。
- 车辆检修:汽车在检修的时候会通过诊断仪读取故障码以及相关扩展数据以及冻结帧等。根据这些信息可以判断具体出故障的汽车部件。
- 故障仪表显示:对于影响继续安全行驶的故障,需要在仪表盘对驾驶员进行及时的警示。
ISO-14229
缩写与术语
- UDS:Unified Diagnostic Services,在国际标准ISO 14229-1中定义,它是一种通用的汽车诊断协议,它提供了一个诊断服务的基本框架,定义了一系列的诊断服务和通用化的诊断流程,主机厂和零部件供应商可以根据实际情况选择实现其中的一部分或是自定义出一些私有化的诊断服务,用于对当前ECU状态查询以及故障检查。
- DTC:Diagnostic Trouble Code,诊断故障码,它是一种通用的故障标识符,汽车检修人员可以根据标识符快速锁定故障发生位置。
- 故障检测样本(Test Sample):故障检测样本代表SW-C或者BSW模块通知的单次的故障检测结果,因此通常不会得到一个成熟/合格的故障测试结果,只有在达到特定的次数或满足特定的条件时,才会得到一个故障结果。对于支持故障检测计数器的电子控制单元,代表故障的故障检测样本将使故障检测计数器增加特定量,代表无故障的测试样本将使故障检测计数器减少特定量。
- 故障检测结果(Test results):在故障检测完成之后,可以向内部故障处理程序通知以下结果。
- PreFailed:ECU中的故障检测可使用此状态来表示目前正处于失效状态。此信息的一个用例是在制造过程中,以加快优化工作流程的故障检测,同时在现场保持容错能力。
- Failed:此状态在故障检测运行到完成后可用,并表示完全成熟的故障产生状态。
- Passed:此状态在故障检测运行到完成后可用,并表示系统或组件没有故障。
- 监视器(Monitor):监视器由一个或多个用于确定组件或系统是否正常运行的故障检测组成。
- 监控周期(Monitoring cycle):指的是检测一次具体故障的开始和结束条件,当检测条件满足时,比如高边的开路故障,需要满足在打开这个通道的时候才能检测到这个故障。监控周期可以在一个Operation Cycle执行多次,也可以跨Operation Cycle执行。
- 操作周期(Operation Cycle):定义要运行检测的开始和结束条件,Operation Cycle开始时开始检测故障,结束时停止检测。开始条件一般为上电/唤醒,结束条件为掉电/休眠。
- 确认阈值(Confirmation Threshold):确认故障存在的Operation Clycle数,即在连续的Operation Clycle中都存在故障(记录在TripCounter),大于确认阈值之后,会将DTC的confirmed bit由0置为1,故障消除之后DTC被认定为历史DTC,在老化(aging)或手动清除前confirmed bit位之前会一直存储在EEPOM。通常对于非OBD用例,操作周期的值被定义为1。
- 老化计数器(Aging Counter):连续报告没有故障的Operation Cycle(排放相关为Driving cycle,在与排放有关的ECU中,只应支持一个运行周期Driving cycle,该运行周期与立法规定的驱动周期相同)数。未报告故障是否存在的Operation Cycle不参与计数。
- 老化阈值(Aging Threshold):Aging Counter达到次数之后,DTC的Confirmed状态位将会被清除。
- 错误检测计数器(FDC, Fault Detection Counter):滤波用的参数,记录当前检测到的故障次数,单次故障步长与向上自增和向下自减均可配置,还可以设置jump down在故障消失的时候,跳转到0或者其他数。
- 扩展数据(Extended):扩展数据包含一些DEM等模块内部信息,常见的用法是记录故障发生Operation Cycle次数和老化计数器,该数据在Pending置位之后会保存在非易失性存储单元中。
- 冻结帧(Freeze Frame):也被成为快照数据(SnapShot),由一系列DID组成,记录故障发生时的一些环境信息,例如环境温度、供电电压、与故障相关的一些数据,帮助技术人员分析故障原因。当DTC状态Confirmed位由0置为1时将记录snapShot。
故障码(DTC)组成
故障码DTC(Diagnostic Trouble Code)就像故障类型的“身份ID”,用于对汽车检修时对故障进行排查。它在ISO-14229中定义为三字节,SAE-J1979(OBD)为两个字节。它包含了故障所属系统(底盘域、动力域、车身域或者网络)、故障定义类型(ISO、OEM)、故障具体部件(如车窗电机等)、故障错误类型(开路、短路或者信号错误等)。下面介绍三字节DTC的具体结构组成。
三个字节我们按照字节顺序分别命名为DTCHighByte,DTCMiddleByte以及DTCLowByte(Hex),DTCHighByte、DTCMiddleByte这两个字节表示故障内码,对应5个标准故障码(第一个是字母,后面四个是数字),如下图所示。例如“C111C07”故障码其中“C111C”为五个标准故障码。
其中前两位与字母的对应关系如下。
后边不同码域的值与故障码的对应关系可以通过下图获得, DTCLowByte与DTCMiddleByte一样直接由Hex值表示对应的码值。
最后我们举个例子, 假如一个故障码的值为0x012BF0,则可根据上边的说明得到故障码“P012BF0”。
故障状态
每一个故障都有一个Byte的故障状态来记录当前故障状态,其中每个Bit都有自己的含义:
- Bit0(TestFailed):当存在一个故障检测样本为Failed时,该Bit会被置位。当DEM初始化或者故障检测结果位Passed时,或收到0x14服务请求时,该Bit会被清零。
- Bit1(TestFailedThisOperationCycle):该Bit表示当前Operation Cycle周期内是否发生过这个故障样本,即使后边该故障不复存在了,该位依然被置位。
- Bit2(PendingDTC):该Bit表示当前或上一个Operation Cycle周期内发生了故障样本,Bit1会在当前Operation Cycle周期结束时被清除,而Bit2位为至少在故障检测结果为Passed的前提下经历过一个完整的Operation Cycle周期才会被清除。
- Bit3(ConfirmedDTC):当PendingDTC置位多次达到可以确定failed标准后即成为ConfirmedDTC,注意当Bit3置位时,并不代表当前故障存在,如果此时Bit0为0,则为一个历史故障。在发生ClearDiagnosticInformation或故障老化之后,重置为逻辑“0”。此外,根据车辆制造商特定的故障存储要求,因为当前存储的事件数超过最大的内存条目,故障码被优先级更高的故障诊断码覆盖时,将重置此位。
- Bit4(TestNotCompletedSinceLastClear):自从上次清除DTC状态之后,若没有任何故障诊断样本通知过来(即SW-C与BSW模块没有通知过故障状态,有故障或者没有故障),该位置位,若有故障诊断样本通知到DEM,则清零。
- Bit5(TestFailedSinceLastClear):自从上次清除DTC状态后该DTC有故障发生。
- Bit6(TestNotCompletedThisOperationCycle):表示该DTC在当前Operation Cycle仍未有诊断样本结果送过来。
- Bit7(WarningIndicator):对应某些影响驾驶安全、影响排放等较重要DTC会与仪表上的危险警报灯、故障灯等相关联,当这类故障出现时。其Bit7将置位,而对于不关联的DTC该Bit将不会使用,保持为零。
故障码老化机制
诊断故障码的状态Confirmed一旦置位,故障信息将会一直保留,直到诊断仪通过发送诊断指令清除,或者通过故障码的老化机制确定故障不再存在。下图展示了故障从产生,到确认,再到老化的整个生命周期,两个Operation Cycle才确认故障。针对老化机制,简而言之就是无故障的Operation Cycle周期数大于了老化阈值,则该故障老化。
应用服务
85服务
ControlDTcsetting服务,DTC控制,它涉及的子服务如下。
正常情况下,DEM初始化完成之后,会根据SW-C和BSW模块通知的故障检测结果实时更新每个DTC的状态,我们可以用这个服务来停止DTC状态的更新,简单来说就是不对通知的故障做任何行为,原来记录的DTC则冻结。这个服务主要用在临时调试ECU状态或者当我们更新某个ECU的程序时。我们需要通过物理寻址将总线上其余的ECU停止故障DTC更新,因为更新程序或者我们调试的ECU经常会无法正常工作,可能会导致其他ECU记录通信故障等错误。下图为一个85服务实例,先进入了扩展会话,然后使用02子服务冻结了DTC。
下图是85服务的NRC。
14服务
ClearDiagnosticInformation,清除故障码服务。他没有子服务,下面这个应用实例清除了故障码为0xFF FF FF的故障相关数据。
19服务
ReadDTCInformation,这个服务是读取DTC的服务,它的子服务很多,如下图所示。
我们先说01子服务,所谓状态掩码就是我们前面介绍过的故障状态,下面这个实例用于读取当前故障发生了的DTC数量。
下个实例展示的是02子服务,读取的是满足故障已经被确认了的DTC,ECU回复的89为ECU支持的所有DTC状态,如果存在DTC状态bit3置位的故障,后边会依照DTCHighByte,DTCMiddleByte,DTCLowByte,statusOfDTC顺序来依次回复每个符合状态要求的DTC,下边的例子为没有符合DTC读取请求状态要求的DTC。
04子服务是读取指定故障码的快照信息,分析故障原因。下面的示例读取了DTC为00 00 01的DTC,SnapshotRecordNumber为01的SnapshotRecord,ECU回复了由DID为0x0107与0x0108两个DID组成的快照信息,具体的回复格式如下:
59|04|DTCHighByte|DTCMiddleByte|DTCLowByte|StausOfDTC |DTCSnapshotRecordNumber|DTCSnapshotRecordNumberOfIdentifiers(快照包含的DID个数,0x00表示一个未定义的未知个数或者异常个数)[DataIdentifier#n byte#1 (MSB)|DataIdentifier#n byte#2 (LSB)|SnapshotData#n byte#1 |...|SnapshotData#n byte#m]。
06子服务是会把DTC相关的扩展数据读取出来,下面这个示例把91 17 16的DTC对应的扩展记录号为FF(FF代表全部记录)的扩展数据读取出来。ECU回复了两个DID,其中01为02,02为02。扩展数据会记录当前DTC的已老化与故障发生周期数(这个周期数是DEM内部的一个计数器,区别于FDC,它会记录故障产生的Operation Cycle数),ECU回复的0A表示故障是一个历史故障。
0A子服务回复它支持的DTC状态以及所有支持的DTC和他们当前的状态,实例如下。
AUTOSAR规范解析
AUTOSAR规范定义了本软件模块诊断事件管理器(Dem)的功能、API和配置,Dem规范文件的基本目标是为汽车制造商和零部件供应商定义一种通用的“诊断故障管理存储”的实现。
软件组件(SW-C)和基础软件(BSW)模块通过Dem_SetEventStatus函数通知Dem故障事件(故障发生与否)。
诊断事件管理器(Dem)管理和存储软件组件(SW-C)和基础软件(BSW)模块中的监视器检测到的故障事件。Dem_SetEventStatus设置的故障信息会预存在Buffer中,并最终存储到Event Memory。
下图为一种Event Memory的示例。
诊断事件管理器(Dem)作为服务组件负责处理和存储诊断事件(错误)及相关数据。Dem向Dcm提供故障信息(例如从存储器读取所有存储的DTC相关信息,并且Dem提供了与应用层和其他BSW模块的关于故障管理函数),下图展示了Dem_GetstatusOfDTC函数的动态行为。
下图展示了DEM的顶层配置,DemGeneral包含关于DEM的全局配置,DemConfigSet包含各个子模块的配置。
故障的去抖(Debounce)策略
诊断monitor是软件组件的常规实体。monitor可识别监视路径的特定故障类型(例如短路、开路等)。监视路径表示被监视的物理系统或电路(例如传感器输入),每个监视路径都与一个诊断事件相关联。
monitor可以自己实现去抖功能,但是我们建议使用DEM内部的Debounce机制来实现去抖,这样monitor每次进行故障检测的时候就可以直接将结果通知到DEM模块中,这样更加高效。
一般来说,ECU可以实现几种类型的去抖策略来提高故障信号质量。Dem内部提供了两种不同的的去抖策略来实现故障成熟策略。当然,故障的去抖策略也可以在SWC中实现。如果在SWC中,Dem_SetEventStatus()函数传给Dem的状态为passed或failed,如果z在Dem,Dem_SetEventStatus()函数传给Dem的状态为prepassed或prefailed。
基于计数器的去抖策略
Dem基于FDC(fault detection counter)计数器判断故障是否成熟。当Dem_SetEventStatus通知的为prefailed时,计数器会按配置的步长增加,当达到设定限值则故障状态会变成failed。当Dem_SetEventStatus通知的为prepassed时,计数器按步长减少,当达到设定限值时,故障状态变为passed。下面是去抖涉及的一些重要参数。
- FDC(fault detection counter):错误样本计数器,-128~127。
- DemDebounceCounterIncrementStepSize:定义内部去抖计数器增量的步长(prefailed)。
- DemDebounceCounterDecrementStepSize:定义内部去抖计数器递减的步长大小(prepassed)。
- DemDebounceCounterFailedThreshold:定义内部去抖计数器的阈值,该阈值指示failed状态。
- DemDebounceCounterPassedThreshold:定义内部去抖计数器的阈值,该阈值指示passed状态。
- DemDebounceCounterJumpDownValue:内部去抖计数器的Jump-Down值,当相应Jump-Down发生时,该值被作为计数器的跳转值。(Jump-Down功能使能时,若在prefailed的前序状态下,故障上报了prepassed,则去抖计数器重置为此值)。
- DemDebounceCounterJumpUpValue::内部去抖计数器的Jump-UP值,当相应Jump-UP发生时,该值被作为计数器的跳转值。(Jump-UP功能使能时,若在prepassed的前序状态下,故障上报了prefailed,则去抖计数器重置为此值)。
下图为一个包含Jump功能的基于Timer的去抖策略示例,图中的红字为帮助读者理解的批注。
基于时间的去抖策略
在这种模式中,时间计数器初始值为0,其范围为-128~127,当Dem_SetEventStatus通知Dem的时候开始计数,计数的方向由Dem_SetEventStatus通知的故障状态决定,当达到阈值之后,即可以得到故障的成熟结果。
下面时几个重要的参数。
- DemDebounceTimeFailedThreshold:定义“Event Failed”时间阈值。AUTOSAR配置标准是使用SI单位,因此该参数定义为以秒为单位的浮点值。Dem配置工具必须将此浮点值转换为适当的值格式,以便在Dem的软件实现中使用。
- DemDebounceTimePassedThreshold:定义“Event Passed”时间阈值。AUTOSAR配置标准是使用SI单位,因此该参数定义为以秒为单位的浮点值。Dem配置工具必须将此浮点值转换为适当的值格式,以便在Dem的软件实现中使用。
下图为一个基于时间的去抖策略示例,图上的红字为笔者的批注帮助读者理解。
故障存储
下图为诊断事件存储的一般过程,读者可以通过下图看到由Dem_SetEventStatus引发的故障DTC信息存储前的判决过程。
下图为上图标红的事件存储的过程。
在事件存储的过程中如果存储已经满了,涉及到了故障替换的操作。Dem提供了下面三种不同的替换策略。
- DEM_DISPLACEMENT_FULL:比较故障优先级(Priority),故障发生时间(Occurrence),故障状态(Active/Passive status)来进行比较,来进行故障替换动作。
- DEM_DISPLACEMENT_NONE:故障替换被禁止。
- DEM_DISPLACEMENT_PRIO_OCC:比较比较故障优先级(Priority),故障发生时间(Occurrence)来进行故障替换动作。
下图为故障替换的过程示意。
ISOLAR-AB配置
DEM
DEM中有很多配置都有相互引用的关系,为了读者能够更好的理解后边的配置,我们先把一些包含引用关系用下图展示出来。
DemGeneral
DemGeneral这个容器中包含了Dem模块涉及的全局配置项,下面是其中比较重要的配置说明:
- DemAgingRequieresTestedCycle:老化计数器是否在所有Operation Cycle进行增加,还是只在使用Dem_SetEventStatus通知故障状态的Operation Cycle才进行增加。
- DemAvailabilitysupport:是否开启对事件有效性控制的机制。
- DemBswErrorBufferSize:处理BSW错误的Buffer大小。
- DemClearDTCBehavior:定义14服务具体清理的DTC内容位置以及正响应的时机。
- DemDataElementDefaultEndianness:Dem数据的字节序。
- DemDebounceCounterBasedsupport:是否支持基于计数器的去抖策略。
- DemDebounceTimeBasedSupport:是否支持基于时间的去抖策略。
- DemDevErrorDetect:是否支持DET错误报告。
- DemDtcStatusAvailabilityMask:DEM支持的DTC状态。
- DemEnvironmentDataCapture:故障时间的捕获是同步的还是异步的。
- DemEventCombinationSupport:DEM支持的故障事件组合方式。
- DemEventDisplacementStrategy:故障替换策略选择。
- DemEventMemoryEntryStorageTrigger:事件存储的触发条件。
- DemGeneralinterfacesupport:使能提供GeneralEvtInfo,GeneralCallbackEventDataChanged,GeneralCallbackMonitorStatusChanged and GeneralCallbackEventUdsStatusChange接口。
- DemMaxNumberEventEntryPermanent:可存储在永久介质的条目最大数。
- DemMaxNumberPrestoredFF:最大的预存快照数据。
- DemOBDsupport:支持的OBD类型。
- DemOccurrencecounterProcessing:定义故障发生计数器触发的确认过程,对于OBD和混动系统,它只有通过TestFailed bit触发。
- DemOperationCycleStatusStorage:定义是否允许在power cycle期间对 operation cycle访问。
- DemResetconfirmedBitOnOverflow:定义故障在存储中被替换之后是否重置confirmed bit。
- DemStatusBitStorageTestFailed:激活/停用状态位的存储功能。如果激活该状态会持续保持到下一个上电周期。
- DemSuppressionSupport:是否支持诊断抑制正响应。
- DemTaskTime:Dem调用周期,应该与OS调度周期一致。
- DemTriggerDcmReports:是否使能在处理ROE时通知DCM。
- DemTriggerDltReports:是否使能诊断Log和trace功能。
- DemTriggerFiMReports:是否使能FIM(功能降级管理)通知功能。
- DemTriggerMonitorlnitBeforeClearOk:定义monitor是否在Dem回复DEM_CLEAR_OK时被触发重新初始化。
- DemTypeOfDTcsupported:Dem_DcmGetTranslationType函数回复的DTC码格式。
- DemTypeOfFreezeFrameRecordNumeration:定义故障对应冻结帧的record numbers是配置的还是由Dem从0排序生成的。
- DemVersionInfoApi:是否使能版本信息API。
- DemHeaderFileInclusion:模块包含的头文件列表,可以添加用户自定义头文件。
DemOperationCycle
定义基于电源上下电的Operation Cycle。
DemDataElementClass
为了不同DTC的快照和扩展数据,建立四个示例的DemDataElement。两个为了快照建立的DemDataElement使用的是DemInternalDataElementClass类型,如下图,第一个为老化周期,用作DTC的扩展数据。
第二个为故障发生周期数,用作DTC的扩展数据。
第三和第四个是两个DID数据,用作快照,集成商需要实现DemDataElementReadFnc配置下函数定义。
DemDidClass
建立两个DidClass,引用上面定义的两个DataElement。
DemFreezeFrameRecordClass
快照数据存储相关参数定义,包括快照的Number以及快照何时触发存储以及何时更新(更新总是触发存储)。
DemFreezeFrameRecNumClass
快照记录存储参数集合,它可以包含多个不同Number的快照存储参数数据,这里引用了DemFreezeFrameRecordClass,只包含了一个快照数据存储参数。
DemFreezeFrameClass
快照记录数据集合,包含的具体DID集合,它引用之前定义的DemDidClass 。
DemExtendedDataRecordClass
扩展数据的存储参数以及具体DataElement的引用,示例配置如下。
DemExtendedDataClass
扩展数据与存储参数的集合,它可以引用多个刚才定义的DemExtendedDataRecordClass。
DemNvRamBlockld
此处定义对Nvm存储块的引用以及存储块的替换优先级,Dem模块必需两个存储块,第一个存储块用于存储一些Dem模块通用的数据,第二个存储故障事件的状态信息。除了以上必须的,还有针对每个故障DTC的EventMemory。
存储故障事件的状态信息以及每个故障DTC的EventMemory这两个Block的大小需要根据Dem配置生成的结构体情况决定,具体确定方法在NVM小节介绍。这几个Block的名字必须是固定的。
DemPrimaryMemory
容器包含DemMaxNumberEventEntryPrimary配置项,定义故障事件的总存储条目。示例只包含一个DTC,所以为1。
DemRbGeneral
这个容器包含了大量的Dem模块涉及的配置参数,下面介绍几个比较重要的。
- DemRbAgingCounterType:老化计数器的类型。
- DemRbDebLimitRelevantForJumping:滤波Jump是否只有在超过阈值时有效。
- DemRbDebugData:调试数据类型。
- DemRbDisturbanceMemorysupported:替换故障是否使能。
- DemRbOccurrencecounterType:定义Occurrence counter类型。
DemComponent
Dem中的DTC组件配置,包括以下重要配置:
- DemComponentlgnoresPriority:是否忽略组件内DTC优先级。
- DemRbComponentAllowedRecoveries:在单次上电期间允许的恢复次数。为了限制不稳定的系统反复触发。
DemDTCAttributes
这个容器包含了一个DTC的具体属性,包含以下重要配置:
- DemAgingAllowed:故障是否启用老化功能。
- DemAgingCycleCounterThreshold:老化完成阈值。
- DemDTCPriority:DTC优先级。
- DemDTCSignificance:故障的附加信息,标注故障影响。
- DemlmmediateNvStorage:如果配置为真,则occurrence counter的每次变化都会引起Event memory的立即存储。
- DemMaxNumberFreezeFrameRecords:当前DTC最大快照数。
- DemAgingCycleRef:当前DTC的老化周期引用。
- DemExtendedDataClassRef:当前DTC的ExtendedDataClass引用。
- DemFreezeFrameClassRef:当前DTC的FreezeFrameClass引用。
- DemFreezeFrameRecNumClassRef:当前DTC的FreezeFrameRecNumClass引用。
- DemMemoryDestinationRef:DTC的存储目标,若无则对于Dcm不可见。
DemDTC
这个容器包含DemUdsDTC的配置信息,主要包含:
- DemDtcValue:DTC值。
- DemDTCAttributesRef:DTC的属性引用。
DemDebounceCounterBasedClass
该容器包含基于计数器的去抖参数,主要有:
- DemDebounceBehavior:该参数定义在未满足DTC相关条件或禁用了DTC相关设置时,事件进行滤波的行为。
- DemDebounceCounterDecrementStepSize:PrePassed减量步长。
- DemDebounceCounterFailedThreshold:故障发生成熟阈值。
- DemDebouncecounterlncrementStepSize:PreFailed增量步长。
- DemDebounceCounterJumpDownValue:JumpDown功能使能时,发生JumpDown时DebounceCounter值。
- DemDebouncecounterJumpUpValue:JumpUp功能使能时,发生JumpUp时DebounceCounter值。
- DemDebouncecounterPassedThreshold:故障未发生成熟阈值。
- DemDebounceCounterStorage:是否存储DebounceCounter到非易失存储器。
DemEventParameter
该容器包含故障事件配置参数,比较重要的参数有:
- DemEventAvailable:故障是否可用。
- DemEventFailureCycleCounterThreshold:故障确认周期数。
- DemEventKind:故障来源,是从SWC还是BSW。
- DemFFPrestoragesupported:是否支持预存快照数据。
- DemReportBehavior:配置SW-C或者BSW模块通知故障状态是否可以在Dem初始化之前。
- DemComponentClassRef:DemComponentClass的引用。
- DemDTCRef:DemDTC的引用。
- DemOperationCycleRef:操作周期的引用。
- DemDebounceAlgorithmClass:DemDebounceCounterBasedClassRef:基于计时器去抖策略引用。
NvM
在NVM模块定义三个NvM Blocks如下图所示,NvMBlockDescriptor的具体参数我们在讲解存储栈的时候再逐一介绍,我们这里先关注NvMNvBlockLength。
NvMNvBlockLength为Block的大小参数,单位为字节。因为他们的大小在由Dem生成的代码中对应结构体大小定义来定义。他们的对应关系需要在DemNvRamBlockld配置好,才能正确生成DEM的相关文件。
其中,DEM_NVM_ID_DEM_GENERIC_NV_DATA的NVBlock大小对应的是结构体Dem_GenericNvData的大小,DEM_NVM_ID_EVT_STATUSBYTE的NVBlock大小对应的结构体是Dem_AllEventsStatusByte,DEM_NVM_ID_EVMEM_LOC_x的NVBlock大小对应的结构体是Dem_EvMemEventMemoryType。这些结构体内容会根据用户在ISOLAR的配置改动而变化。
Dem生成的Dem_Cfg_AssertionChk.h会自动获取引用的NvM模块对应Block配置的块大小,并在预编译阶段进行Assert判断,保证NvM配置的块大小与Dem需要的相一致。
CANSM
在CANSM这个容器下的CanSMDemEventParameterRefs子容器中,可以配置当CAN控制出现BUS-OFF错误通知DEM的故障事件。因为我们只配了一个故障事件,所以就选择了它。
Components
生成BSW会自动建立Dem的服务组件,如下图。
我们还是在Test1中建立一个C/S接口DiagnosticMonitor的RPort。如下图。
建立一个Runnables,添加对刚才建立的Port口下的SetEventStatus方法访问。
最后增加一个0.01s的TimingEvent,引用刚才建立的Runnables。
System
将Dem增加到部件中。
再次增加Dem服务组件到ECU中。
最后完成组件间的连接。
RTE
将涉及的周期运行函数映射到任务上。
代码解析
动态配置代码
Dem模块生成的动态代码如下所示。
我们针对一些常用的进行说明:
- Dem_Cfg.h:包含Dem模块顶层的配置宏定义,诸如下边等配置。
/* *********************************************************************************************************************** * * Product Info * Isolar version: ISOLAR-AB 4.0.2 * Product release version: RTA-BSW 3.1.0 * *********************************************************************************************************************** */ /********************************************************************************************************************/ /* */ /* TOOL-GENERATED SOURCECODE, DO NOT CHANGE */ /* */ /********************************************************************************************************************/ #ifndef DEM_CFG_H #define DEM_CFG_H /* ---------------------------------------- */ /* OBD and BFM switches included for RTA-BSW Configuration */ /* ---------------------------------------- */ /* ---------------------------------------------------------------------------- OBD switch ---------------------------------------------------------------------------- */ #define DEM_CFG_OBD_OFF 0 /* OBD not supported */ #define DEM_CFG_OBD_ON 1 /* OBD supported */ #define DEM_CFG_OBD DEM_CFG_OBD_OFF /* ---------------------------------------------------------------------------- J1939DCM switch ---------------------------------------------------------------------------- */ #define DEM_CFG_J1939DCM_OFF 0 /* J1939DCM not supported */ #define DEM_CFG_J1939DCM_ON 1 /* J1939DCM supported */ #define DEM_CFG_J1939DCM DEM_CFG_J1939DCM_OFF #define DEM_CFG_J1939DCM_CLEAR_SUPPORT DEM_CFG_J1939DCM_OFF /* ---------------------------------------------------------------------------- BFM switch ---------------------------------------------------------------------------- */ #ifndef DEM_BFM_ON #define DEM_BFM_ON 1 /* BFM supported */ #endif #ifndef DEM_BFM_OFF /* BFM not supported */ #define DEM_BFM_OFF 0 #endif #ifndef DEM_CATPRIO_ON #define DEM_CATPRIO_ON 1 /*Event category priority supported*/ #endif #ifndef DEM_CATPRIO_OFF #define DEM_CATPRIO_OFF 0 /*Event category priority not supported*/ #endif #define DEM_BFM_ENABLED DEM_BFM_OFF #ifndef DEM_BFM_ENABLED #define DEM_BFM_ENABLED DEM_BFM_OFF #endif /* ---------------------------------------- */ /* Dem API Features */ /* ---------------------------------------- */ /* Only define switches here that enable or disable the availability of an API */ #define DEM_CFG_TRIGGER_TO_STORE_NVM_SUPPORTED FALSE #define DEM_CFG_SUSPICIOUS_SUPPORT FALSE #define DEM_CFG_DEBTIMEBASED_CONFIGURED_CYCLICTASKTIME FALSE #define DEM_CFG_EVMEMGENERIC_SUPPORTED TRUE #define DEM_CFG_VERSION_INFO_API_OFF STD_OFF #define DEM_CFG_VERSION_INFO_API_ON STD_ON #define DEM_CFG_VERSION_INFO_API DEM_CFG_VERSION_INFO_API_OFF #define DEM_CFG_ALTERNATIVEDTC_OFF STD_OFF #define DEM_CFG_ALTERNATIVEDTC_ON STD_ON #define DEM_CFG_ALTERNATIVEDTC DEM_CFG_ALTERNATIVEDTC_OFF #define DEM_CFG_ERASE_ALL_OFF 0u #define DEM_CFG_ERASE_ALL_WITHOUT_HASHID_CHECK 1u #define DEM_CFG_ERASE_ALL_WITH_HASHID_CHECK 2u #define DEM_CFG_ERASE_ALL_DATA_SUPPORTED DEM_CFG_ERASE_ALL_OFF #define DEM_CFG_DEPENDENCY_OFF STD_OFF #define DEM_CFG_DEPENDENCY_ON STD_ON #define DEM_CFG_DEPENDENCY DEM_CFG_DEPENDENCY_OFF #define DEM_CFG_TESTMODE_SUPPORT_ON STD_ON #define DEM_CFG_TESTMODE_SUPPORT_OFF STD_OFF #define DEM_CFG_TESTMODE_SUPPORT DEM_CFG_TESTMODE_SUPPORT_OFF /* ---------------------------------------- */ /* Check Consistency between RTE and C API */ /* ---------------------------------------- */ #define DEM_CFG_CHECKAPICONSISTENCY TRUE /* ---------------------------------------- */ /* DEM_CFG_DEBUGDATA */ /* ---------------------------------------- */ #define DEM_CFG_DEBUGDATA_OFF 0 #define DEM_CFG_DEBUGDATA_8BIT (0+1) #define DEM_CFG_DEBUGDATA_32BIT (0+4) #define DEM_CFG_DEBUGDATA DEM_CFG_DEBUGDATA_32BIT #if (DEM_CFG_DEBUGDATA != DEM_CFG_DEBUGDATA_OFF) /* MR12 RULE 20.7 VIOLATION: Macro parameter may not be enclosed in (). */ #define DEM_DEBUGDATA_PARAM(A,B) ,A,B #else #define DEM_DEBUGDATA_PARAM(A,B) #endif #endif
- Dem_Cfg_NvmCallbacks.c:NvM Block读写的Callback。
/* *********************************************************************************************************************** * * Product Info * Isolar version: ISOLAR-AB 4.0.2 * Product release version: RTA-BSW 3.1.0 * *********************************************************************************************************************** */ /********************************************************************************************************************/ /* */ /* TOOL-GENERATED SOURCECODE, DO NOT CHANGE */ /* */ /********************************************************************************************************************/ #include "Dem_Cfg_NvmCallbacks.h" #include "Dem_NvmCallbacks.h" #define DEM_START_SEC_ROM_CODE #include "Dem_Cfg_MemMap.h" /* EvMem: Nvm Explicit Synchronization: NvMWriteRamBlockToNvCallback(s) */ Std_ReturnType Dem_EvMemNvMWriteRamBlockToNvCallback0(void* NvMBuffer) { return Dem_EvMemNvMWriteRamBlockToNvCallback(NvMBuffer, 0); } /* EvMem: Nvm Explicit Synchronization: NvMReadRamBlockFromNvCallback(s) */ Std_ReturnType Dem_EvMemNvmReadRamBlockFromNvCallback0(void* NvMBuffer) { return Dem_EvMemNvmReadRamBlockFromNvCallback(NvMBuffer, 0); } #define DEM_STOP_SEC_ROM_CODE #include "Dem_Cfg_MemMap.h"
- Dem_Cfg_AssertionChk.h:Dem模块涉及的NvM Block大小以及用作断言的Assert宏定义。
/* *********************************************************************************************************************** * * Product Info * Isolar version: ISOLAR-AB 4.0.2 * Product release version: RTA-BSW 3.1.0 * *********************************************************************************************************************** */ /********************************************************************************************************************/ /* */ /* TOOL-GENERATED SOURCECODE, DO NOT CHANGE */ /* */ /********************************************************************************************************************/ #ifndef DEM_CFG_ASSERTIONCHK_H #define DEM_CFG_ASSERTIONCHK_H #include "Dem_Lib.h" #include "Dem_EventStatus.h" #include "Dem_GenericNvData.h" #include "Dem_DisturbanceMemory.h" #include "Dem_Obd.h" /* -------------------------------------------------- */ /* DEM_CFG_STATIC_ASSERTION_FOR_NVM_BLOCKLENGTH */ /* -------------------------------------------------- */ #define DEM_CFG_STATIC_ASSERTION_FOR_NVM_BLOCKLENGTH_ON STD_ON #define DEM_CFG_STATIC_ASSERTION_FOR_NVM_BLOCKLENGTH_OFF STD_OFF #define DEM_CFG_STATIC_ASSERTION_FOR_NVM_BLOCKLENGTH DEM_CFG_STATIC_ASSERTION_FOR_NVM_BLOCKLENGTH_ON #if(DEM_CFG_STATIC_ASSERTION_FOR_NVM_BLOCKLENGTH == DEM_CFG_STATIC_ASSERTION_FOR_NVM_BLOCKLENGTH_ON) /* Macros which defines the block size of each configured NvM Block */ #define DEM_NVM_ID_DEM_GENERIC_NV_DATA_SIZE 16 #define DEM_NVM_ID_EVMEM_LOC_0_SIZE 60 #define DEM_NVM_ID_EVT_STATUSBYTE_SIZE 193 DEM_STATIC_ASSERT((DEM_SIZEOF_VAR(Dem_GenericNvData)==DEM_NVM_ID_DEM_GENERIC_NV_DATA_SIZE),DEM_NVM_ID_DEM_GENERIC_NV_DATA_BlockLengthIsInvalid); DEM_STATIC_ASSERT((DEM_SIZEOF_TYPE(Dem_EvMemEventMemoryType)==DEM_NVM_ID_EVMEM_LOC_0_SIZE),DEM_NVM_ID_EVMEM_LOC_0_BlockLengthIsInvalid); DEM_STATIC_ASSERT((DEM_SIZEOF_VAR(Dem_AllEventsStatusByte)==DEM_NVM_ID_EVT_STATUSBYTE_SIZE),DEM_NVM_ID_EVT_STATUSBYTE_BlockLengthIsInvalid); #endif #endif
集成代码
MemMap与SchM就不在这里赘述了。Dem跟Dcm一样,预留了很多桩给集成商添加自己项目特殊的代码逻辑,比如在Dem_PrjEventStatus.h的Dem_EvtSt_HandleImmediateAging函数内可以写某些故障在老化时执行的操作,这里的集成函数模板一般不需要添加什么逻辑。
还有刚才建立好的函数RE_DEM_Report_func中写相关的故障检测逻辑,把检测的结果通知到Dcm中,下面是函数生成的模板,可以看出通过RTE提供的Rte_Call_RPDiagEvent_P12D2_SetEventStatus来通知Dcm故障状态。
/* *****************************************************************************
* BEGIN: Banner
*-----------------------------------------------------------------------------
* ETAS GmbH
* D-70469 Stuttgart, Borsigstr. 14
*-----------------------------------------------------------------------------
* Administrative Information (automatically filled in by ISOLAR)
*-----------------------------------------------------------------------------
* Name:
* Description:
* Version: 1.0
*-----------------------------------------------------------------------------
* END: Banner
******************************************************************************
* Project : TestCsdn
* Component: /Base_SWC/Test1
* Runnable : RE_DEM_Report
*****************************************************************************
* Tool Version: ISOLAR-AB 4.0.2
* Author: geekl
* Date : ������ ���� 28 17:18:33 2024
****************************************************************************/
#include "Rte_Test1.h"
/*PROTECTED REGION ID(FileHeaderUserDefinedIncludes :RE_DEM_Report_func) ENABLED START */
/* Start of user defined includes - Do not remove this comment */
/* End of user defined includes - Do not remove this comment */
/*PROTECTED REGION END */
/*PROTECTED REGION ID(FileHeaderUserDefinedConstants :RE_DEM_Report_func) ENABLED START */
/* Start of user defined constant definitions - Do not remove this comment */
/* End of user defined constant definitions - Do not remove this comment */
/*PROTECTED REGION END */
/*PROTECTED REGION ID(FileHeaderUserDefinedVariables :RE_DEM_Report_func) ENABLED START */
/* Start of user variable defintions - Do not remove this comment */
/* End of user variable defintions - Do not remove this comment */
/*PROTECTED REGION END */
#define Test1_START_SEC_CODE
#include "Test1_MemMap.h"
FUNC (void, Test1_CODE) RE_DEM_Report_func/* return value & FctID */
(
void
)
{
Dem_EventStatusType EventStatus1;
Std_ReturnType syncCall1;
/* Local Data Declaration */
/*PROTECTED REGION ID(UserVariables :RE_DEM_Report_func) ENABLED START */
/* Start of user variable defintions - Do not remove this comment */
/* End of user variable defintions - Do not remove this comment */
/*PROTECTED REGION END */
Std_ReturnType retValue = RTE_E_OK;
/* -------------------------------------- Data Read ----------------------------------------- */
/* -------------------------------------- Server Call Point -------------------------------- */
syncCall1 = Rte_Call_RPDiagEvent_P12D2_SetEventStatus(EventStatus1);
/* -------------------------------------- CDATA --------------------------------------------- */
/* -------------------------------------- Data Write ---------------------------------------- */
/* -------------------------------------- Trigger Interface --------------------------------- */
/* -------------------------------------- Mode Management ----------------------------------- */
/* -------------------------------------- Port Handling ------------------------------------- */
/* -------------------------------------- Exclusive Area ------------------------------------ */
/* -------------------------------------- Multiple Instantiation ---------------------------- */
/*PROTECTED REGION ID(User Logic :RE_DEM_Report_func) ENABLED START */
/* Start of user code - Do not remove this comment */
/* End of user code - Do not remove this comment */
/*PROTECTED REGION END */
}
#define Test1_STOP_SEC_CODE
#include "Test1_MemMap.h"
最后,还需要提供之前配置提到的快照数据DID的获取函数, 下面的示例展示了将AD读取出来的供电电压过去示例。
/******************************************************************************
Function name :
Description :C002
Parameter (in) :
Parameter (inout) :
*****************************************************************************/
FUNC(Std_ReturnType,DCM_APPL_CODE) GetSnapShot_C002 (P2VAR(uint8,AUTOMATIC,DCM_INTERN_DATA) Data)
{
Data[0] = (uint8)((uint16)AD_READ_Battery_VOLT >> 8U);
Data[1] = (uint8)((uint16)AD_READ_Battery_VOLT );
return FALSE;
}
静态代码
主要介绍常见的静态代码涉及API说明,具体详细完整的介绍读者可以参考《AUTOSAR_SWS_DiagnosticEventManager.pdf》以及《RTA-BSWReferenceGuide.pdf》。
- Dem_MainFunction:Dem周期调用主函数。
- Dem_Init:EcuM与Dem之间的API,完成Dem初始化。
- Dem_Shutdown:EcuM与Dem之间的API,完成Dem关闭。
- Dem_SetEventStatus:BSW 模块和SW-C 与DEM之间的API,设置故障事件状态。
- Dem_DisableDTCRecordUpdate:DCM与DEM之间的API,禁用特定故障诊断码的事件内存更新(一次只能更新一个)。
十六宿舍 原创作品,转载必须标注原文链接。
©2023 Yang Li. All rights reserved.
欢迎关注 『十六宿舍』,大家喜欢的话,给个👍,更多关于嵌入式相关技术的内容持续更新中。