嵌入式软件动态运行时错误的检测

合集下载

嵌入式系统中的故障排查与维护方法

嵌入式系统中的故障排查与维护方法

嵌入式系统中的故障排查与维护方法嵌入式系统是应用于各种设备中的计算机系统,包括但不限于家电、汽车、医疗设备和工业控制系统。

这些系统在现代生活中扮演着重要角色,因此对于其正常运行的要求十分关键。

然而,嵌入式系统在使用过程中也会遇到各种故障和问题,因此了解故障排查与维护方法对于保证系统的持续稳定运行至关重要。

一、故障排查方法1. 确定故障现象:对于出现问题的嵌入式系统,首先需要详细记录故障现象。

这包括出现问题的频率、具体的错误信息以及导致系统故障的具体条件等。

通过详细记录,可以更好地分析问题的根源,并有针对性地进行故障排查。

2. 检查硬件连接:嵌入式系统中的硬件连接是故障的常见来源之一。

因此,在排查故障时,应仔细检查主板、插槽、电缆和接口等连接是否牢固,排除由于连接不良导致的故障。

3. 分析错误日志:嵌入式系统通常会生成错误日志,记录系统运行中的异常情况。

通过仔细分析错误日志中的信息,可以了解发生故障的原因和位置。

错误日志的分析可以通过查看日志文件或使用特定的工具来进行。

4. 软件调试工具:嵌入式系统的软件调试工具在故障排查中起着重要作用。

通过使用调试器、监视器、仿真器等工具,可以对软件进行详细的调试和分析。

调试工具可以帮助查找代码中的错误、检测内存泄漏、优化程序性能等。

5. 分析代码:代码是嵌入式系统故障排查的关键部分。

通过仔细分析代码中的错误和逻辑问题,可以找到导致系统故障的原因。

在进行代码分析时,可以使用调试工具、代码静态分析工具和代码剖析工具等来辅助。

二、系统维护方法1. 定期进行系统更新和升级:嵌入式系统的维护需要定期更新和升级系统软件和硬件。

更新系统可以修复已知的漏洞和问题,提供更稳定和安全的运行环境。

同时,升级系统可以获得更多的功能和性能改进。

2. 进行性能监控:嵌入式系统的性能监控是及时发现系统问题和优化系统性能的关键工作。

通过监控系统的CPU利用率、内存使用情况、网络流量等指标,可以追踪系统的运行状态。

嵌入式系统中的异常处理与故障排查技术

嵌入式系统中的异常处理与故障排查技术

嵌入式系统中的异常处理与故障排查技术嵌入式系统在现代社会中得到了广泛的应用,它们被用于控制和管理各种设备,从智能手机到航空航天系统。

然而,由于软硬件交互的复杂性和系统资源的有限性,嵌入式系统常常面临着各种异常和故障情况。

因此,为了确保系统的稳定性和可靠性,异常处理与故障排查技术成为嵌入式系统开发和维护中不可或缺的一部分。

一、异常处理技术1. 异常的类型在嵌入式系统中,异常可以分为两大类:硬件异常和软件异常。

硬件异常包括芯片失效、电路损坏、连接故障等,而软件异常则包括程序错误、内存溢出、死锁等。

在处理异常时,需要先确定异常类型,以便采取相应的处理方法。

2. 异常处理方式嵌入式系统中的异常处理方式通常包括以下几种:a. 收集异常信息:及时捕获异常发生的位置和原因,例如通过日志记录、硬件监控、断言等手段来收集异常信息。

这些信息对于后续排查和修复故障非常重要。

b. 异常处理器:嵌入式系统通常会配置一个专门的异常处理器,用于处理系统中的各种异常情况。

异常处理器可以根据不同的异常类型执行相应的操作,例如重新启动系统、恢复到安全状态、报警等。

c. 异常处理策略:根据异常的严重程度和影响范围,制定相应的异常处理策略。

例如,对于嵌入式系统中的软件异常,可以采用重启、恢复等策略来解决问题;而对于硬件异常,则可能需要更换故障部件。

二、故障排查技术1. 故障排查流程在嵌入式系统中,故障排查应该遵循一定的流程,以提高效率和准确性。

一般而言,故障排查流程可以分为以下几个步骤:a. 问题定义:明确故障的现象和表现形式,例如系统崩溃、功能失效、性能下降等。

同时收集相关信息,如异常日志、用户反馈等。

b. 系统调试:通过调试工具以及硬件/软件的监控来排查可能的问题源。

例如,使用示波器、逻辑分析仪等工具进行信号分析和跟踪,或者通过调试器对程序进行单步调试、设置断点等。

c. 故障定位:根据排查的结果,确定故障出现的位置和可能的原因。

这可能需要编写额外的测试代码,进行模块层面的功能验证和异常情况模拟。

基于执行序列的嵌入式软件时序异常检测探究

基于执行序列的嵌入式软件时序异常检测探究

基于执行序列的嵌入式软件时序异常检测探究摘要:时序特性是嵌入式软件的重要特性,实时嵌入式软件运行的正确性不仅依赖于任务执行结果,更依赖于任务执行时间.执行任务往往具有多个时间约束,且相互之间可能存在制约关系,对时间约束进行验证和确认是嵌入式软件测试过程中一个非常重要问题,因而在本文中提出了一种基于执行片段的检测方法,英文缩写为TBTDD,简单地说,即是通过执行片段对软件的时序进行特性检测。

一方面,基于扩展语义接口自动机(ESIA)模型,刻画嵌入式软件时序特性需求,分析不同时间约束间存在的相关关系类型,并提出基于相关矩阵的相关时间约束识别算法;另一方面,在目标软件运行环境中提取包含时间信息的执行片段,通过执行片段与时间约束模型的匹配,依据预先制定的时序特性检测准则,检验执行序列是否满足模型中各项独立和相关时间约束的要求,进而发现被测软件中存在的时序缺陷.关键词:执行片段; 时序缺陷检测;软件测试;嵌入式软件时序特性是否满足设计要求将对实时嵌入式软件的正常运行有着至关重要的影响,因为时序异常极有可能会造成任务执行地失败,甚至在很多时候还会造成系统的极大破坏,因此正确的嵌入式软件时序的设计不仅是软件开发的重中之重,更是软件正常实现的关键。

一、研究背景欲准确地掌握目标系统的时序特征、合理地对时序序列缺陷进行检测都是要建立在精确、完整建模的基础上。

接口自动机(IA)作为一种轻量级的形式模型,其主要是通过状态机的相关接口去实现对构件间通信以及交互过程的描述,并且还可以进行对构件内部结构的隐藏,实现对外部环境有关行为特性的刻画,同时在这个环境下,还可以自动地进行相容性检测和精化检验,因而是一种可组合的、非常适合软件系统建模的常用工具。

定义1:把接口自动机(IA)定义为P=(VP,VoPn,AIP,AOP,APH ,ΔP),式中:VP是自动机所包含的所有状态的集合;而VoPn则是自动机所包含的相关初始状态集合,VoPn包含于VP,若VoPn空集,则称P空;AIP、AOP和AHP分别为输入、输出和内部行为集合,AIP∩AOP=AIP∩APH=AOP∩APH=空集;A表示全部行为的集合;ΔPVP×AP×VP是自动机包含的P=AIP∪AOP∪AHP状态迁移集合.定义2:扩展语义接口自动机ESIA.嵌入式软件ESIA定义为P=(VP,VoP式中:VP是自动机所包含的所有状态的集合;而VoPn则n,XP,AP, ΨP,E,ΔP),是自动机所包含的相关初始状态集合,VoPn包含于VP,若VoPn=空集,则P为空;XRP被叫做行为参数,而XHP则是内部变量的集合,并且XRP∩XHP=空集;XP=XRP∪XPH表示全部变量的集合AIP、AOP和AHP分别为输入、输出和内部行为集合,AIP∩AOP=AIP∩APH=AOP∩APH=空集;AP=AIP∪AOP∪AHP,表示的是所有行为的集合;而ΨP是行为执行约束条件的集合;a∈AP表示一种行为,ψ(a)∈ΨP则是行为a的一组执行约束,用ψ(a)=(PreCon(a),PostCon(a))进行表示,其中PreCon(a)和PostCon(a)分别表示行为a的前、后置条件,E是所有触发事件的集合,e∈E表示触发事件P 中的某些特定行为的执行;ΔP包含于VP×AP×VP是自动机包含的状态迁移集合,δ∈ΔP表示一个状态迁移过程.二、时序缺陷检测关于相关性的分析在对时序进行缺陷检测的时候,需要借助ESIA模型和执行路径在时间约束方面的相关性进行分析,因此需要对执行片段中预先提取的各类信息进行自动检测,以排查软件在执行过程中各种时序错误,并借此检查软件相关的异常处理机制是否符合设计需求。

软件运行时错误测试工具评析

软件运行时错误测试工具评析

软件运行时错误测试工具评析摘要:从减少软件开发成本和缩短软件开发周期的角度考虑,尽可能的在软件编码时期发现软件缺陷无疑是最佳选择,但软件运行时错误是所有的软件缺陷中最具风险的,发现该类错误最有效的手段就是专用测试工具。

通过对几种主流的软件运行时错误测试工具的对比分析,探讨了各个工具的优缺点及选择的诸多因素,对于软件测试人员如何选择合适的该类测试工具,具有实际参考价值。

关键词:软件测试;运行时错误;语义分析技术中图分类号:tp311 文献标识码:a 文章编号:1009-3044(2013)07-1575-03随着软件规模越发庞大,软件中存在的缺陷也越来越多,软件测试工作所肩负的责任日趋繁重。

通常我们通过软件测试来确保软件的可靠性,通过软件测试我们可以在软件交付用户之前尽量找到软件中存在的bug,而在所有类型的软件bug中运行时错误的危害性是最大的。

欧洲航天局阿里亚纳501号火箭的爆炸,就是因为在其控制飞行姿态的一段代码中蕴含有一个变量溢出的运行错误。

正是这个错误的溢出变量控制着火箭急速转向而过载。

根据ibm-berkeley调查统计:在每一千行的代码中大约就会发现一个运行时错误,而且在软件的维护阶段所检测到的错误中有30%-40%是运行时错误,可见运行时错误对软件质量的影响是多么大。

该文对几种常用的可以发现软件运行时错误的测试工具进行评析。

1 什么是软件运行时错误(run-time errors)运行时错误(run-time errors)是所有的软件错误中最具风险的错误。

它主要发生在软件动态运行的过程中。

我们在日常家庭用的windows操作系统或者其他软件工具时也会时常出现运行时错误,一般情况下出现运行时错误后无论怎么操作,程序都会关闭。

上述软件出现问题并不会产生太大的影响,但是对于对安全等级要求很高的系统,比如汽车、航天、军用领域,发生这种错误所从带来的负面影响或许是十分巨大的。

由ansi c定义的运行时错误是指那些能导致预定义之外的不正确结果或者处理器停机的错误,它的风险等级在所有软件错误中是最高的,由它引起的后果可能为:数据崩溃、安全保密被破坏、处理器停机等;它也可能导致给外部设备发送非受控命令,引起不可预测、不确定的行为。

嵌入式系统中的异常处理与错误检测方法

嵌入式系统中的异常处理与错误检测方法

嵌入式系统中的异常处理与错误检测方法嵌入式系统是一种专门设计用于控制和驱动各种设备或系统的计算机系统。

由于嵌入式系统通常在一些关键的应用领域中运行,例如航空航天、医疗设备和汽车等,因此其可靠性和稳定性至关重要。

然而,在复杂的硬件和软件环境下,异常和错误不可避免地会发生。

因此,在嵌入式系统中,异常处理与错误检测方法是至关重要的组成部分。

异常处理是指对于嵌入式系统中出现的异常情况进行相应的处理和恢复。

异常可以是由于硬件故障、软件错误、通信异常或外部干扰等原因引起的系统中断或异常情况。

对于这些异常情况,嵌入式系统需要具备相应的机制来进行处理,以保证系统的正常运行和稳定性。

首先,嵌入式系统可以利用异常处理机制来对硬件故障进行检测和处理。

例如,当嵌入式系统中的硬件组件出现故障或错误时,例如存储器错误、时钟故障或信号丢失等,系统可以通过使用硬件监控器和故障检测电路来检测和分析这些异常情况。

一旦检测到异常情况,系统可以通过适当的措施来进行错误处理和恢复,例如重新启动、重置或切换备份系统等。

其次,嵌入式系统还可以利用软件异常处理来对软件错误进行检测和处理。

软件错误可能包括程序错误、数据异常或算法错误等。

为了检测和处理这些软件错误,嵌入式系统可以采用软件调试和异常处理技术。

例如,系统可以通过在程序中插入断言语句、错误检测代码和异常处理函数来实现对软件错误的检测和处理。

当软件错误发生时,系统可以根据错误类型和严重程度采取相应的措施,例如记录错误信息、打印错误日志或进行错误恢复等。

此外,嵌入式系统还可以利用通信异常处理来对外部通信异常进行检测和处理。

在嵌入式系统中,与外部设备或系统的通信是常见的操作。

当外部通信发生故障或异常时,系统可以通过使用适当的通信异常处理机制来检测和分析这些问题。

例如,系统可以通过检测通信时延、校验和错误码等指标来判断通信是否正常。

一旦检测到通信异常,系统可以采取相应的措施,例如重新发送消息、切换通信通道或通知用户等。

嵌入式系统的故障排除技巧

嵌入式系统的故障排除技巧

嵌入式系统的故障排除技巧故障排除是嵌入式系统开发中的一个重要环节。

嵌入式系统的故障可能是由硬件和软件的问题导致的,因此,作为嵌入式系统开发人员,我们需要掌握一些故障排除的技巧。

本文将介绍一些常用的嵌入式系统故障排除技巧。

1. 软件故障排除技巧软件故障是嵌入式系统中最常见的问题之一。

以下是一些排除嵌入式软件故障的技巧:a) 日志记录:在嵌入式系统中,我们可以通过添加日志记录来帮助我们追踪软件故障。

可以通过在代码中插入日志输出语句或者使用专门的日志记录工具来记录系统状态和错误信息。

通过分析日志,我们可以更容易地定位和解决软件故障。

b) 软件调试工具:嵌入式开发工具通常提供了一些调试功能,如断点调试、变量监视等。

通过使用这些调试工具,我们可以逐步执行代码,观察变量的值和程序的执行流程,从而找到软件故障的原因。

c) 内存管理和异常处理:内存管理是嵌入式系统中的一个重要问题。

在开发过程中,我们需要确保内存的正确分配和释放,以避免由于内存问题导致的软件故障。

此外,合理地处理异常情况,如空指针引用、溢出等,也是排除软件故障的关键。

2. 硬件故障排除技巧除了软件故障,嵌入式系统中的硬件故障也可能导致系统不稳定或无法正常工作。

以下是一些排除嵌入式硬件故障的技巧:a) 硬件调试工具:与软件调试一样,硬件调试工具可以帮助我们检测硬件问题并找到故障的原因。

例如,使用示波器、逻辑分析仪等设备可以观察信号波形和时序,以帮助我们发现硬件故障。

b) 逐个排除法:当嵌入式系统出现问题时,我们可以逐个排除硬件模块,以确定哪个模块是引起问题的原因。

通过逐个排除,我们可以快速定位到故障模块,并采取相应的修复措施。

c) 供电和地线问题:在设计和调试嵌入式系统时,供电和地线问题是常见的硬件故障原因之一。

我们需要检查供电电源和电压的稳定性,以及地线的连接是否良好,以避免由于供电和地线问题引起的故障。

3. 系统级故障排除技巧除了软件和硬件故障外,嵌入式系统中可能还存在一些系统级故障,如通信故障、时钟问题等。

嵌入式软件测试与验证方法

嵌入式软件测试与验证方法嵌入式软件是指嵌入到硬件系统中的软件,它在现代科技中扮演着至关重要的角色。

嵌入式软件的质量和稳定性对于设备的正常运行至关重要,因此嵌入式软件测试与验证方法的研究和应用显得尤为重要。

嵌入式软件测试的目标是发现软件中的缺陷和错误,以确保软件在各种条件下的正确运行。

在传统的软件测试中,通常采用黑盒测试和白盒测试的方法。

黑盒测试是基于软件的功能需求,通过输入一系列的测试用例,观察软件的输出是否符合预期。

而白盒测试则是基于软件的内部结构,通过检查代码的执行路径和逻辑分支,发现潜在的错误。

然而,嵌入式软件的特殊性导致传统的测试方法无法完全适用。

首先,嵌入式软件通常运行在资源有限的环境中,例如嵌入式系统中的微控制器。

这就意味着测试用例的设计必须考虑到资源的限制,以避免测试过程过于消耗资源。

其次,嵌入式软件通常与硬件紧密结合,因此测试过程需要考虑硬件和软件的交互。

最后,嵌入式软件通常需要满足实时性的要求,即对于某些任务,必须在规定的时间内完成。

这就要求测试方法需要考虑软件的响应时间和实时性。

一种常用的嵌入式软件测试方法是模拟器测试。

模拟器是一种软件工具,可以模拟目标硬件的行为,从而在计算机上运行嵌入式软件。

通过模拟器测试,可以在不依赖实际硬件的情况下进行软件测试,大大提高了测试的效率和灵活性。

同时,模拟器测试还可以模拟各种场景和环境,以验证软件在不同条件下的正确性和稳定性。

另一种常用的嵌入式软件测试方法是硬件测试。

硬件测试是通过连接实际硬件设备,对嵌入式软件进行测试。

硬件测试可以更真实地模拟软件在实际硬件上的运行情况,发现潜在的硬件和软件交互问题。

硬件测试通常需要使用专门的硬件测试设备,例如逻辑分析仪和示波器等。

这些设备可以监控软件的执行过程,以及与硬件之间的通信和交互,从而发现潜在的问题。

除了测试方法的选择,嵌入式软件的验证方法也是不可忽视的。

验证是指通过形式化的方法来证明软件的正确性。

嵌入式系统测试工具

嵌入式系统测试工具引言在当今的技术环境中,嵌入式系统扮演着至关重要的角色。

从家用电器到工业自动化,再到汽车电子和航空航天,嵌入式系统的应用广泛且关键。

因此,确保这些系统的可靠性和性能至关重要,这就需要使用专门的测试工具进行严格的测试。

本文将介绍几种常用的嵌入式系统测试工具,帮助开发者提高产品质量。

静态代码分析工具CtagsCtags是一个源代码索引和代码高亮工具,它可以为C、C++、Java等多种语言生成标签文件,帮助开发者快速定位函数和变量定义。

CppcheckCppcheck是一个针对C/C++代码的静态分析工具,用于检测内存泄漏、错误的数组边界等问题,有助于提前发现潜在的错误。

动态测试工具ValgrindValgrind是一款强大的动态内存调试工具,它能够检测内存泄漏、内存访问错误等运行时问题,对于维护内存安全非常有帮助。

GDBGNU调试器(GDB)是Linux下的一款功能强大的调试工具,支持多种编程语言,可以对程序进行断点设置、单步执行、查看变量值等操作。

性能分析工具PerfPerf是Linux内核提供的性能分析工具,可以监控系统级别的性能数据,如CPU占用率、缓存命中率等,帮助开发者优化系统性能。

LatteLatte是一个轻量级的性能分析工具,专为嵌入式系统设计,可以在不干扰系统正常运行的情况下收集性能数据。

仿真与模拟工具QEMUQEMU是一款开源的硬件模拟器和虚拟化工具,可以模拟多种处理器架构,用于嵌入式系统的开发和测试。

ProteusProteus是一个电子电路仿真和PCB设计软件,支持模拟微控制器和外围设备,非常适合进行嵌入式系统的原型设计和测试。

结论选择合适的测试工具对于嵌入式系统的开发至关重要。

从静态代码分析到动态测试,再到性能分析和仿真模拟,每一种工具都有其独特的优势和应用场合。

开发者应根据项目需求和系统特点,合理选择和使用这些工具,以确保嵌入式系统的质量和性能。

通过这些工具的综合运用,可以大大提高产品的可靠性,减少后期维护成本,最终实现项目的顺利交付。

嵌入式智能控制系统中的误差分析和校正研究

嵌入式智能控制系统中的误差分析和校正研究随着科技的高速发展,人们对于计算机和控制技术的应用越来越广泛和深入,嵌入式智能控制系统成为了现代工业生产和科研的必备工具。

然而,这些系统在实际应用中难免会因为外部环境的干扰和内部组件的耗损等原因发生一定程度的误差,如何对这些误差进行分析和校正,以提高系统的精度和可靠性,成为了当前嵌入式智能控制领域的研究热点之一。

一、误差分析的基本概念对于嵌入式智能控制系统而言,误差分析是指通过对系统的输入和输出数据进行分析,得出系统的误差来源和误差大小等信息的过程。

在实际应用中,误差分析可以对控制系统的性能进行评估和改进,同时也是校正误差的重要基础。

误差分析主要包括以下几个方面:1、量测误差分析:量测误差是指由于检测器、传感器等量测设备本身的精度限制或环境因素干扰所产生的误差。

对于嵌入式智能控制系统而言,量测误差是影响系统精度的一个主要因素,因此必须认真进行分析和消除。

2、处理误差分析:处理误差是指由于系统软硬件部件的响应速度、算法精度等方面的限制所引起的误差。

在误差分析中,处理误差通常是难以避免的,但可以通过合理的系统设计和参数优化等方式来减小误差的影响。

3、噪声误差分析:噪声误差是指由于外部环境噪声、电磁干扰等对控制信号和数据的干扰所引起的误差。

在实际应用中,噪声误差也是影响系统稳定性和精度的一个主要因素,需要进行有效的分析和抑制。

二、误差校正的方法误差校正是指通过对误差进行定位和量化,采取相应的校正措施,使得控制系统的精度得到进一步提高和稳定。

基于误差分析得到的信息,通常有以下几种误差校正方法:1、传感器校正:传感器是控制系统中常见的量测设备,其精度的高低直接影响系统的控制精度。

因此,在系统运行前或者运行中,需要对传感器进行定期的校准和检验。

传感器校准的方法包括零点校准、满量程校准和非线性校准等。

2、系统参数校正:系统参数校正是指对于嵌入式智能控制系统中涉及到的关键参数进行校正,如调节增益、滤波器带宽、控制周期等。

嵌入式系统测试方法

嵌入式系统测试方法1.静态测试方法:-代码静态分析:通过对源代码或目标代码进行分析,检测是否存在潜在的程序错误、性能问题、可移植性问题等。

-代码审查:由开发人员对代码进行检查,查找逻辑错误、潜在的缺陷和不规范的代码。

-配置文件检查:对配置文件进行检查,确保配置参数正确、缺陷或冲突消除。

2.黑盒测试方法:-界面测试:对嵌入式系统的图形界面、命令行界面等进行测试,包括用户交互的各种功能。

-功能测试:对嵌入式系统的各个功能进行测试,验证是否满足需求规格说明书中的功能要求。

-兼容性测试:测试嵌入式系统与硬件、软件、操作系统或其他设备的兼容性,确保系统在各种环境下都能正常工作。

-安全测试:测试嵌入式系统的安全性,包括抗攻击能力、数据保护能力等。

-性能测试:测试嵌入式系统对各种负载情况下的性能表现,包括响应时间、并发能力、吞吐量等。

3.白盒测试方法:-单元测试:对嵌入式系统中的每个模块进行独立测试,验证其功能的正确性。

-集成测试:对嵌入式系统中各个模块的集成进行测试,验证模块之间的接口和数据交互是否正确。

-内存测试:通过测试程序的内存使用情况,检测内存泄漏、内存溢出等问题。

-代码覆盖率测试:通过分析测试过程中覆盖的代码行数,评估测试的完整性,并查找测试中遗漏的代码。

4.回归测试方法:-自动化测试:用自动化测试工具执行各种测试用例,提高测试效率和准确性。

-故障注入测试:有目的地在系统中注入故障,测试系统在异常条件下的反应和恢复能力。

-长时间运行测试:模拟系统在长时间运行状态下的使用情况,检测系统是否存在内存泄漏、资源不释放等问题。

-恢复测试:测试系统在异常情况下的恢复能力,包括系统的自动恢复和手动恢复。

5.安全测试方法:-渗透测试:通过模拟黑客攻击系统,查找系统的漏洞和安全隐患。

-加密测试:测试系统的加密算法和密钥管理机制,确保系统的数据安全性。

-防护测试:测试系统的防护机制,包括入侵检测、防火墙等,确保系统能有效地抵御攻击和恶意行为。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

嵌入式软件动态运行时错误的检测刘艳会1 概述嵌入式软件是世界上重要应用软件的核心,目前已经广泛应用于国防、航空航天、医疗等重要行业中,确保它的稳定可靠是极为重要的任务。

随着当前应用系统规模的增大和复杂度的增加,嵌入式软件测试的成本也直线上升,同时也突出了当前所用测试工具和测试方法的局限性。

和桌面系统不同,对于嵌入式软件系统,软件测试主要是发现以下类型的错误:功能错误主要依靠测试人员依据项目需求说明,编写功能测试用例并运行测试用例,从而验证软件的功能性能错误一般需要放到真实的环境中,借助于硬件级别的工具,来衡量软件的性能是否达到要求运行时错误(Run-Time Error)以前没有有效的检测技术,一般不会专门做运行时错误的检查对于嵌入式系统软件来说,这些错误中,运行时错误是最难发现、又最具风险的错误。

欧洲航天局阿里亚纳501号火箭在升空后不到20秒就发生爆炸,其原因就是因为控制飞行姿态的一段代码蕴含有一个变量溢出的运行错误,发生了溢出的变量控制着火箭急速转向而过载。

那么到底什么是软件运行时错误呢?运行时错误都包括什么类型呢?1 什么是软件运行时错误?(Run-time Errors)运行时错误(Run-time Errors)就是软件在动态运行时出现的错误,是所有的软件错误中最具风险的。

相信熟悉Windows应用系统的人来说,一定经历过以下的情形:图1.1 Windows 2000操作系统上发生运行时错误的现象图1.2 Windows XP操作系统上发生运行时错误的现象图1.3 UNIX操作系统上发生运行时错误的现象这种情况下,不管我们做什么选择,应用程序都会退出。

可能对于一般的软件来说,出现这样的错误没关系,但对于航空航天、汽车以及医疗设备等安全级别要求非常高的系统来说,一旦出现这样的运行错误,损失就是不可估量的。

运行时错误由ANSI C定义,是指那些能导致预定义之外的不正确结果或者处理器停机的错误,它是所有的软件错误中最具风险的,其后果包括:处理器停机,数据崩溃、安全保密受到破坏等。

典型的运行时错误有以下几种:・企图读未初始的变量・对空指针和越界指针的引用・对超界数组的访问・非法类型转换(long to short, float to integer)・非法的算数运算(例,除零错误,负数开方)・整数和浮点数的上溢出/下溢出・多线程应用中未保护数据的访问冲突・不可达到的代码运行时错误属于潜在的威胁,广泛的存在各种软件中。

根据Berkeley大学与 IBM Watson的研究报道指出所有IBM大型软件的漏洞中,30%-40%是运行时错误引起的。

既然运行时错误如此广泛存在,那么我们应该怎样检测运行时错误呢?2 普通软件测试技术的限制传统的软件测试技术一般分成静态测试和动态测试,这两种测试方法在检测软件动态运行时错误方面有着很多的限制,如图2。

图2 普通测试技术的限制静态测试技术可以检查软件代码的编程规范,分析程序的静态结构,对软件的质量进行度量。

借助于静态测试技术,可以使代码更加规范,结构更加清晰,但由于静态测试技术不分析代码的动态行为,不分析各个变量之间的关系,因此普通的静态测试技术不能有效的检查出只有动态运行才会出现的错误,即运行时错误。

动态测试技术需要将被测的程序运行起来,最好能放到实际的软硬件环境中。

动态测试技术主要有以下的特点:z不完全:测试的步骤一般是:测试计划——测试用例——测试执行——发现并提交BUG。

这种方法只能发现一部分运行时错误,即测试用例所能覆盖到的错误,但是完全的测试是不可能的(软件测试的原则之一),即不可能穷尽所有的输入,所以依赖于测试用例的测试最终只能保证测试过的输入不会导致运行时错误,不敢保证其他大部分的输入也能正常工作。

z效率低:动态测试技术能发现一部分运行时错误,但它发现的只是现象,类似于图1这样的现象,而不是问题的根源。

测试人员提交BUG后,开发人员还需要重现BUG,然后使用传统的调试工具来定位问题所在。

对于一般的错误,定位并修复一个错误大约需要10个小时,而对于偶尔死机这样的错误,则需要更多的时间去调试。

3 PolySpace的语义分析技术PolySpace使用的是目前最新的语义分析技术,它依靠大量的数学定理提供的规则去分析软件的动态行为。

语义分析技术没有使用简单的穷举法,却有能力在更普通的模式下去表达程序的状态,还能提供规则巧妙的去处理它。

在以前的软硬件环境下,这个问题会非常复杂,很难去解决。

随着计算机处理能力的不断增强,在当前的硬件条件下,语义分析技术已经完全可以高效的实现。

当应用在运行时错误的检测时,语义分析技术会对所有危险的操作,执行一个详细的分析,在程序动态运行之前,最早在编码阶段,就能够发现其中的运行时错误。

举例说明,一个程序P,使用了两个变量:x和y。

检查语句X = X / ( X-Y )的运行时错误。

z第1步:为了保证穷尽,先列举该语句可能存在的所有运行时错误。

X和Y可能没有初始化X – Y 可能会溢出X和Y可能会相等,从而导致除数为0X / ( X – Y )可能会溢出下面以第3个为例,详细介绍一下语义分析如何检查除数为0z第2步:为了更好的理解语义分析,可以在二维的坐标系中表示X和Y所有可能的取值。

红线表示能够导致除数为0的X和Y的集合。

图3.1 建立二维的坐标系z第3步:根据这个图,我们如何去判断是否会出现除数为零的状态?最直观的方法就是穷举X和Y的每一个状态,检查它是否在红线上,这个活动称为“测试”,并且我们能够很快了解该原理的局限性:因为在实际的程序里肯定不只两个变量,所以将会有无数个状态。

如果要穷举所有的状态,花费的时间将会无限长穷举法不能查出一些运行时错误,包括读取未初始化的变量语义分析的方法是建立自己的规则来熟练处理所有的状态。

如何对程序进行抽象,可以检测程序的特性呢。

如下是一个简单的例子:间隔分析:根据坐标系中X,Y的坐标,得到X和Y的最小值和最大值,画出一个相应的矩形图。

这个矩形有以下特性:它包括X和Y所有可能的取值,用四个数据表示(X的最小值,X的最大值,Y的最小值,Y的最大值)。

什么特性是最让人关心的?显然矩形和红线的交集是我们最关心的,就是说,如果交集是空集的话,就说明除数不可能为0。

图3.2 矩形中包含了X和Y的所有可能的取值,通过X和Y的最大和最小值绘制。

这种类型的抽象,也叫做间隔分析。

编译器、链接器和一般的静态分析工具已经在使用这种技术。

z第4步:根据语义分析的概念,我们怎样才能高效的用来进行运行时错误的检测呢?第3步表现了一个从程序中得到的非常简单的抽象(一个矩形),该抽象采用的是间隔分析的技术,目前大多数的编译器、链接器和一般的静态分析工具都已经在使用这种技术。

这种方法的问题是抽象出来的矩形不是一个很好的形状,因为它包含了海量的不实际的X、Y的值,运行时错误的检测结果包含了大量的警告信息,不适合实际的分析。

语义分析技术能够依据自己的规则,建立非常精确的形状,包括网格或者多个多边形,基于变量(X,Y)之间的关系,程序的控制结构(if-then-else, for, while loops, switch),内部过程之间的关系(函数调用),多任务分析,进行运行时错误的检测。

语义分析的技术原理不仅仅是计算数据类型和常量的值,象编译器和一般的静态分析工具那样,语义分析包括很多方面。

它起源于这些包括在程序里面的每一个操作的相关的语义和操作数据的关系,并以此作为基础去详细审查源代码和细微的运行时错误,举例如下:传递给函数的参数不再是一个变量或者常量,而是一个用来约束函数内部局部变量的集合在多任务的程序中,全部共享变量的值随时都会改变,除非使用了保护机制 变量不仅仅是有一定取值范围的类型,还是用一套包括控制流关系去表示的方程式最后,由于使用了变量的方程式,语义分析能够解决运行时错误的检测图3.3 语义分析技术可以验证控制结构、内部过程和多任务的分析,从而可以测试程序的动态属性,高效的检测运行时错误。

4 例子以下的例子是由语义分析测试的结果,标成红色的代码表示错误。

以下的例子请仔细的思考,这里不再做详细的说明。

4.1 控制结构分析:for循环结束后指针访问越界借助于语义分析,以上指针访问越界(Out of Bounds pointer de-referencing)的错误被自动检测到,而其他的操作都是安全没有错误的。

如果不修复,该错误将导致内存冲突,需要大量的调试时间。

程序员对这种错误非常熟悉。

语义分析是唯一能够在编译时就能发现这些错误的解决方法。

4.2 控制结构分析:在嵌套的for循环中数组访问越界借助于语义分析,数组访问越界(Out of Bounds array access)被自动检测到,而其他的操作都是安全没有错误的。

这个例子表现了语义分析对控制结构分析的能力。

如果不修复,该错误将导致数据冲突,需要大量的调试时间。

4.3 内部过程分析:除数为0借助于语义分析,函数foo中的除数可能为0的错误被自动检测到,而其他的操作都是安全没有错误的。

这个例子表现了语义分析对内部过程分析的能力,能够明确的标示出错误的函数调用和正确的函数调用。

如果不修复,除数为0的错误可能导致处理器宕机,同时由于递归的使用,要调试解决该错误,需要大量的调试时间。

5为什么PolySpace可以取代传统的代码覆盖率的测试?传统的测试理论中,测试结果一般都对代码覆盖率作了要求,要求必须达到90%或者更高。

让我举一个简单的例子来说明代码覆盖率的局限。

static void Recursion (int* depth)97 /* if depth<0, recursion will lead to division by zero */98 { float advance;99100 *depth = *depth + 1;101 advance = 1.0/(float)(*depth - 6); /* potential division by zero */ 102……………..}在做代码覆盖率测试时,只需要一个测试用例*depth = 10;就可以使以上的代码覆盖率达到100%。

如果只是追求高覆盖率尽快达到要求的话,就很可能漏过*depth = 5 会导致除数为0这样的致命的错误。

当然实际的代码可能会更复杂,不会那么简单。

假如GlobalFlag是一个被多个任务使用的全局变量,*depth = 10这一个测试用例可能也会让代码覆盖达到100%,但这个100%能保证下面代码中的除数不为0吗?static void Recursion (int* depth)97 /* if depth<0, recursion will lead to division by zero */98 { float advance;99100 *depth = *depth + 1;101 advance = 1.0/(float)(*depth - GlobalFlag); /* potential division by zero */ 103……………..}我认为覆盖应该分为两种,一是传统意义上说的结构覆盖,即逻辑覆盖(语句覆盖、分支覆盖等)和以及基本路径覆盖,第二是数据输入覆盖。

相关文档
最新文档