微软公司宣布不再支持你正在使用的 IE浏览器,这会严重影响浏览网页,请使用微软最新的Edge浏览器
厂商专区
产品/技术
应用分类

详解嵌入式软件易错区域 到底怎么办看这里!

2017-05-22 10:21 来源:互联网 编辑:电源网

嵌入式软件的最大特点是以控制为主,软硬结合的较多,功能性的操作较多,模块相互间调用的较多,外部工作环境复杂容易受到干扰或干扰别的设备。需要注意的是,执行错误的后果不仅仅是数据错误,而是有可能导致不可估量的灾难!我们如何才能更好的设计嵌入式软件呢?

所以总结起来,嵌入式软件可靠性设计需注意的问题有四个方面:

1、软件接口

软件接口调用一般会有数据的赋值,赋值变量的数据类型可能会存在强制的数据转换;需加以检查。如果为了防范出问题的话,可以添加对数据范围和数据类型的检查。赋值数据的数量不对路,多了少了的都不好,会出现意外的赋值结果,不过还好,这项错误比较好检查。

软件编程中,会有对某一功能操作代码的复用,比如对某个端口的数据检查和控制,在整个程序中只会发生两次,为了图省事,可能就直接把该段代码直接插入实际程序模块中去了,这样,在源程序代码中,就出现了两段完全相同,完成相同功能,只是服务于不同模块的代码,按道理来说,这样设计其实也没啥问题,是的,你没错,但你的行为会使别人无意中犯错。

那如何做呢?方法不难,把这段功能单独做成一个模块即可,对此端口的读取和控制赋值均由此独立模块完成,如果数据的正确性影响大的话,还需要对端口数据的正确性进行检查和判断。嵌入式软件可靠性编程方法的四个目的是防错、判错、纠错、容错。对端口数据的判断属于判错的内容,如果数据有错的话,纠错和容错的设计方法应该不用我深入讲解了吧?

2、软硬件接

对读进来的硬件接口的数据要判断其真伪;

对输出的数据的执行效果要检测;

对输出的数据的可能后果要进行预防性设计,数据输出的过程,我们从设计上要做一个分析,分析的思路是一般容易局限在稳态过程,忽视了过渡过程。举例说明,比如我们控制一个支路的供电,从软件控制来说,直接给继电器一个启动信号,让开状态的触点闭合就可以了,非“关”即“开”,是受控继电器的两个稳态状态,但事实上,在从开到闭合的过程中,支路供电的电压并不是一个简单0V—24V(24V为示例而已)的跳变状态,而是一个抖动,有冲击信号的过程,这种情况在硬件上的防护是必不可少的,但在软件上也不是可以事不关己、高高挂起的。

另外在逻辑上,宜将容易被干扰和容易产生的干扰控制动作从时序上控制好,予以分开隔离。比如,控制继电器的过程是容易产生抖动尖峰脉冲而干扰数据总线和控制信号总线的,这时候从控制上,不宜同时实施数据的发送和接收工作,不宜作出其他的控制动作,惹不起咱躲得起,躲过这一阵干扰的时候总可以了吧?

3、软件代码

软件的可靠性是随着时间的推移,可靠性逐渐增加的,这一点区别于电子可靠性、机械可靠性。电子可靠性服从指数分布,在整个生命周期内,其失效率为一个常数;机械可靠性因为磨损、腐蚀、运动等因素的存在,随时间推移可靠度会下降。因此也就有了软件可靠性设计的一个特定规律和注意事项。

既然需要通过时间推移,通过不断改进,软件可靠性得到提升。那么软件的可维护性就是一个大问题了。这也是为什么软件工程管理方面特别关注软件文档、注释的原因了。但做这些要求的人只是人云亦云,并不理解如此做法的真正动机。至于注释如何去做、变量如何命名、软件配置管理如何操作,这里面既有很常规的方法,也有一些我们司空见惯然而是错误的做法。信手举上几个值得注意的细节供参考。

变量定义时宜将变量类型的变量名程中体现于其中;如AD_result_int、Cal_result_float等。这样为的好检查,防止数据类型的强制转换或强制赋值时出现数据类型的错误;

注释要充分;

代码的布局风格宜统一,便于阅读查找;

不可出现非受控的default流程,所有数值和变量,不论是调用函数时赋予的、读取接口读进来的、还是中间变量计算出来的,在应用前都宜作数据有效性的判断,并对判定的所有可能结果均做受控的对应处理。

直接给出解决方法吧,就是每隔一段程序代码或控制区域,就人为放置上几个NOP指令,在NOP指令后放置一个长跳转的ERR处理程序。注意NOP最少放置3个,这样任何的跑飞最多只能占用2个NOP,第三个NOP一样还是能把程序代码揪回来,揪回来后就执行ERR处理程序。

4、数据、变量

变量的定义是为的避免各种混淆,同一程序内数据和数据的混淆、不同人读程序时对变量理解上出现的二义性、视觉效果上容易出现的错误(字母的“o”和数字的“0”,字母的“l”和数字的“1”)。这里要遵循一个“要么相同,要么迥异”的基本规则,这条规则在很多的领域都有应用,用的最绝的是朱元璋,对待贪官,要么不理你,自觉点您贪差不多了就收手吧,您自己不收手的话,做的过了直接就杀,株连几族,所以在明朝,朱元璋是杀人最多的皇帝;在结构的防呆性设计上,接插件的选型也是如此,如果一个乳白色和一个浅灰色的同类接插件,最好的选择是有很直观的视觉差异或结构的差异,或者干脆就是相同的,相同须基于一个前提,互换性要好。

用显意的符号来命名变量和语句标号。标识符的命名有明确含义,且是完整单词或易理解的缩写。短单词通过去掉“元音”形成缩写;长单词取头几个字母形成缩写;一些单词有公认的缩写。如:

Temp — tmp;

Flag — flg;

StaTIsTIc — stat;

Increment — inc;

Message — msg。

特殊约定或缩写,要有注释说明。在源文件开始处,对使用的缩写或约定注释说明。自己特有的命名风格,要自始至终保持一致。对于变量命名,禁止取单个字符(如i、j、k.。。);含义+变量类型、数据类型等,i、j、k作局部循环变量是允许的,但容易混淆的字母慎用。如int Liv_Width,L代表局部变量(Local)(g全局变量Global)、i代表数据类型(Interger)、 v代表 变量(Variable)(c常量Const)、Width代表变量的含义,这种命名方式可防止局部变量与全局变量重名。

禁用易混淆的标识符(R1和Rl,DO和D0等)来表示不同的变量、文件名和语句标号。

除了编译开关/头文件等特殊应用,避免使用_EXAMPLE_TEST_之类以下划线开始和结尾的定义。

全局变量是战略性资源,它决定了模块和模块间的耦合度,需在项目上提升到一个足够高的高度,慎用全局变量,不得不用的时候,要单独为每一个全局变量编写独立的操作模块或函数,在修改全局变量的时候,要检查是否有别的函数在调用它并且需要此数值保持稳定。

对变量代表某个特定含义的时候,尽量不要仅仅用位来代表什么,比如用某变量的第零位代表某个状态(0000 0001,其中仅用1代表某个内容,这样01H、03H、05H… 会有很多个组合都能代表这个状态);位容易受干扰被修改,信息出现错误的几率大很多。

也不要用00H、FFH等数据代表,就像我们面试一群人一样,第一个被面试人和最后一个被面试人容易被记住,00H和FFH亦然,系统默认状态是00和FF的时候较多,他们容易被复位或置位成这类数值。推荐以四位的二进制码的某个中间值为状态变量,如1001。

变量数据在应用之前宜作数据类型和数值范围的判断。

标签: 嵌入式软件

声明:本内容为作者独立观点,不代表电源网。本网站原创内容,如需转载,请注明出处;本网站转载的内容(文章、图片、视频)等资料版权归原作者所有。如我们采用了您不宜公开的文章或图片,未能及时和您确认,避免给双方造成不必要的经济损失,请电邮联系我们,以便迅速采取适当处理措施;欢迎投稿,邮箱∶editor@netbroad.com。

微信关注
技术专题 更多>>
研发工程师的工具箱
智慧生活 创新未来

头条推荐

电子行业原创技术内容推荐
客服热线
服务时间:周一至周五9:00-18:00
微信关注
获取一手干货分享
免费技术研讨会
editor@netbroad.com
400-003-2006