英语原文共 5 页,剩余内容已隐藏,支付完成后下载完整资料
通过符号执行测试Android应用程序
Nariman Mirzaei, Sam Malek, Corina S. Păsăreanu, Naeem Esfahani, Riyadh Mahmood
摘要:针对Android应用程序的自动化测试技术的需求日益增长。一个关键的挑战是系统生成测试用例。系统地为Java程序生成测试用例的一种方法是符号执行。但是,使用象征性执行工具(如符号探路者(SPF))为Android应用程序生成测试用例受到Android应用程序在Dalvik虚拟机(DVM)而不是JVM上运行的挑战。此外,由于Android应用程序依赖于应用程序开发框架,因此它们是事件驱动的,并且容易受到路径分歧。本文概述了缓解这些问题的双管齐下的方法。首先,我们在Java Pathfinder(JPF)中开发了一个Android库模型,以便以解决与JVM不兼容和路径分歧的问题的方式执行Android应用程序。其次,我们利用程序分析技术将事件与其处理程序关联起来,以自动生成模拟所有有效事件的Android特定驱动程序。
类别和主题描述符:D.2.5 [测试和调试]:符号执行或测试工具。
一般术语:可靠性,安全性。
关键词:Java探路者,符号探路者,Android,测试。
1.简介
2008年,Google和Open Handset Alliance推出了Android平台移动设备。 Android是用于移动通信设备的综合软件框架,包括智能手机和PDA。自从诞生以来,Android发展迅猛,部分原因在于其充满活力的应用程序市场,该应用程序市场目前提供了超过50万的应用程序,每天增加和更新数千个应用程序。毫不奇怪,开发人员,消费者和市场运营商对适用于Android应用的自动测试技术的需求日益增加。有前途的自动化测试技术是符号执行[12],这是一种程序分析技术,它使用符号值而不是实际值作为程序输入。它收集程序每条路径上这些值的约束,并在求解器的帮助下为所有可达路径生成输入。虽然Android应用程序是用Java开发的,但它们为面向Java的符号执行工具,即符号路径查找器(SPF)[22],提出了三个挑战。第一个挑战是Android应用程序依赖于在设备或仿真器外部不可用的专有库集。 Android代码在Dalvik虚拟机(DVM)[6]上运行,而不是传统的Java虚拟机(JVM)。因此,Android应用程序被编译成Dalvik字节码而不是Java字节码。他们使用SPF来象征性地执行Android应用程序
需要转换成相应的Java字节码表示。第二个挑战是Android程序对框架库的依赖使得它们很容易出现路径分歧问题,而且比传统的Java程序更为重要。一般而言,当符号值超出正在被符号执行的程序的上下文以及边界框架或任何外部库的上下文时,可能会发生路径分歧问题。然而,在Android中,路径分歧是常态,而不是例外。一个典型的Android应用程序由多个活动和服务组成,扮演着软件组件的角色,它们使用Android的消息传递系统Intents进行广泛沟通。 Intent用于将值传递给另一个Activity / Service,并使值在应用程序边界处离开,并在新Activity / Service中检索之前通过Android库传递。最后,Android是一个事件驱动系统,提取程序输入值在很大程度上取决于用户的操作,这意味着符号执行引擎必须等待用户与系统交互并点击按钮或启动其他程序继续执行某个路径的事件类型。此外,系统本身或第三方应用程序可以启动事件并使应用程序以某种方式运行。由于智能手机的上下文敏感特性,这类事件在智能手机应用中比传统软件系统更为频繁。目前处理基于传统事件的系统的技术或者使用捕获重放或者模型驱动方法。在捕获 - 重放方法[1,16,17]中,用户使用GUI记录她的交互序列,并在测试时重播。模型驱动技术[15,24]要求用户提供软件系统使用的模型。捕获 - 重放和模型驱动方法都取决于手动操作,因此不是很方便,并且很容易忽略不知道应用程序参与的方式。事实上,在安全测试的背景下,应用程序可能会故意将其隐藏的方式纳入其中。也有人努力自动提取有向图模型。事实上,在安全测试的背景下,应用程序可能会故意将其隐藏的方式纳入其中。 也有人试图通过抓取GUI来自动提取有向图模型[1,16,17],并使用这些图生成测试序列,但也可能无法确定系统可以使用的其他方式。 在本文中,我们概述了应对这些挑战的多方面方法。 我们描述了提供模拟Android库的存根的SPF扩展。 这些模型使我们能够在JVM上编译Android应用程序,并在Java PathFinder(JPF)上运行它们以解决第一个挑战,即DVM和JVM不兼容。 另外,我们在某些存根中提供逻辑来模拟Android库类的行为,以解决路径分歧问题。 最后,我们利用Android规范的知识和应用程序的专用调用图模型,将事件与其处理程序关联起来[13]。使用此模型,我们可以自动生成驱动程序,以提取用户输入值并生成用于锻炼应用程序的有效事件序列。司机通过指导旨在模拟实际用户行为的事件序列生成来解决最后的挑战。由此产生的SPF扩展版本使我们能够象征性地执行Android应用程序,以生成实现高代码覆盖率的测试用例。本文组织如下。第2部分提供了Symbolic PathFinder和Android的背景。第3部分介绍了一个用于说明研究的Android应用程序。第4部分概述了我们的方法。第5部分详细介绍了我们如何对Android库进行建模,而第6部分详细介绍了我们为Android应用程序生成驱动程序的方法。本白皮书总结了第7章中的相关研究,并在第8章中讨论了我们的未来工作。
2.背景
在本节中,我们首先提供SPF的简要背景,然后是更详细的Android框架概述。
2.1符号路径查找器JPF [11]是Java程序的通用模型检查器,它使用自己的虚拟机而不是传统的JVM。符号探路者(JPF-Symbc)构建在JPF之上,作为一个扩展,使用修改的JPF JVM实现对Java字节码的非标准解释[5]。 SPF分析Java字节码,并且可以通过启发式求解来处理混合整数和实际约束,以及复杂的数学约束。 SPF可用于测试输入生成和发现安全特性的反例[23]。我们正在扩展SPF以模拟Android应用,并利用它来为它们生成输入和测试用例。
2.2 Android Android是一个用于移动通信设备(包括智能手机和PDA)的全面软件框架。 Android框架包括基于ARM处理器,系统库,中间件和一套预安装应用程序的完整Linux操作系统。 Google Android平台基于DVM,用于执行和包含用Java编写的程序。 Android还附带了一个应用程序开发框架,该框架为应用程序开发提供了一个环境,并包含用于构建GUI应用程序,数据访问和其他组件类型的服务。该框架旨在简化组件的重用和集成。每个Android应用都有一个强制清单文件。这是每个应用程序所需的XML文件,并提供了管理Android平台中应用程序生命周期的重要信息。包含在清单文件中的各种信息的例子是应用程序的活动,服务,广播接收器和内容提供者以及其他架构和配置属性的描述。 “活动”是一个呈现给用户的屏幕,其中包含一组布局(例如,在屏幕上水平或垂直组织项目的LinearLayout)。这些布局包含GUI控件,称为视图窗口小部件(例如,用于查看文本的TextView和用于文本输入的EditText)。布局和控件通常在配置XML文件中进行描述,每个布局和控件都有唯一的标识符。服务是一个在后台运行并执行长时间运行任务的组件,例如播放音乐。与活动不同,服务不会向用户显示交互屏幕。内容提供者管理存储在文件系统或数据库上的结构化数据
如联系信息。广播接收器响应系统范围的广播消息,例如屏幕已关闭或电池电量不足。活动,服务和广播接收器通过意图消息激活。意图消息是与支持该操作的数据一起执行的操作的事件。意图消息传递允许组件之间的后期运行时绑定,其中调用在代码中不明确,而是通过事件消息传递进行连接。活动和服务需要遵循预先规定的生命周期[3]。例如,图1显示了Activity的生命周期中的事件:onCreate(),onStart(),onResume(),onPause(),onStop(),onRestart()和onDestroy()。这些生命周期事件在我们的研究中扮演着重要的角色,后面会解释。除了这些组件外,典型应用程序还利用了许多资源。这些资源包括动画文件,图形文件,布局文件,菜单文件,字符串常量,用户界面控件的样式。其中大部分是使用XML文件描述的。如前所述,一个例子是布局。布局XML文件定义了活动使用的用户界面控件。每个资源都有一个唯一标识符,用于在应用程序代码中区分并获取对它们的引用。
3.举例
说明为了说明这种方法,我们将使用Driving Directions应用程序,这是软件系统的一个子集,叫做紧急部署系统(EDS)[14]。 EDS旨在允许搜索和救援人员实时共享并获得对情况的评估(例如,地图上的交互式覆盖),彼此协调(例如发送报告,聊天和分享视频流),并从事总部(例如,请求资源)。驾驶方向应用程序可用于计算两个地理点之间的越野驾驶方向,同时考虑成本目标,如距离,时间和安全。它还为用户提供距离源,目的地或路线最近的调度。图2描述了这个Android应用程序的GUI。输入框用于纬度/经度对,按钮用于计算方向的其他方式。纬度/经度坐标可以输入或从地图中选择。由此产生的逐向方向显示在单独的文本框中,并可选地显示在地图上。
4.方法概述
我们的工具的主要目标是使用SPF为Android应用程序自动生成测试输入。为此,我们首先需要生成可以在JVM上执行的应用程序的Java字节码。因此,我们必须使用Java编译器来编译应用程序的源代码,而不是使用Android的软件开发工具包(SDK)。这是通过首先用我们的模型替换每个应用所需的Android库的平台特定部分来实现的。这些模型实质上是存根,它们以保持每个组件的组合和回调行为的方式创建。这使我们可以在JPF上执行Android应用程序而无需修改应用程序的实现。另外,我们必须考虑到一个典型的应用程序由多个组件(即活动和服务)组成的事实,这些组件使用Android的意图消息进行通信。当使用Intent将符号值传递给另一个活动或服务时,会出现Pathdivergence问题。为了解决这个问题,我们已经实现了适当的逻辑来模拟Android平台如何调解组件的基于事件的交互,并将该逻辑合并到Activity,Service和Intent存根中。我们将这些增强的存根称为模拟类,因为它们模拟相应的Android构造如何表现。这样我们就可以解决由Android组件之间相互通信的基本机制引起的路径不一致问题。我们的方法的第二步是使用其调用图模型为应用程序生成驱动程序。与传统的Java程序不同,Android应用程序不包含成为调用图的根节点的主类,该程序始终启动。 Android应用程序是事件驱动的,这意味着执行的线程不断地改变应用程序逻辑,系统和用户之间的上下文。因此,Android应用程序不是代表应用程序完整控制流的连接调用图,而是由一组断开的子调用图组成,它们共同表示应用程序的逻辑。这些子调用图对应于用户或Android平台可以启动,访问应用程序的所有方式。图3展示了Android应用程序的假设调用图模型,其中A,B和C分别是具有根节点a,b和c的子调用图,而黑色圆圈表示应用程序的开始。在生成子调用图之后,我们解析源代码,资源和配置信息(包括清单文件),以查找事件处理程序。这使我们能够自动连接子调用图以构建系统的调用图模型。图3显示了Driving Directions应用程序的调用图模型的一个子集。连接两个子图的虚线箭头表示由用户或系统启动事件。调用图模型表示应用程序内所有可能的方法调用序列(执行轨迹),图中用黑色箭头表示。最后,我们使用call graph模型来派生一个Context Free
语法(CFG),用于生成驱动程序。驱动程序是模拟用户与应用程序交互的一系列事件。由于每个子图的根节点表示正在处理的事件,因此根节点的每个有效组合代表用户与应用交互的场景。例如,基于图3中的调用图模型,{a,c}和{a,c,b}是两个可能的事件序列。我们使用EMMA [7]监视执行测试的代码覆盖率,这是一个用于监视和报告Java代码覆盖率的开源工具包。我们从单个事件驱动程序开始,并继续迭代地生成具有更多事件序列的驱动程序。当我们达到预先指定的代码覆盖阈值时,测试停止。我们在接下来的两节中更详细地描述该方法。
5.建模ANDROID程序库
解决Java程序依赖于外部库时发生的路径分歧问题的传统技术是为这些库提供存根。我们探讨了三种可能的技术来开发支持Android应用程序的存根,如下所述。对我们来说,第一个也许是最直接的方法就是利用Android库类的实现。 Android平台提供了一组应用程序用来访问手机资源的库类。这些库类包含本地方法和Java本地接口(JNI)调用,这些调用是依赖于平台的,并且不能在实际的电话之外执行。为了支持开发活动,Google为android.jar提供了Android的软件开发工具包,它允许开发人员在开发环境中解决依赖关系和编译应用程
剩余内容已隐藏,支付完成后下载完整资料
资料编号:[23026],资料为PDF文档或Word文档,PDF文档可免费转换为Word
以上是毕业论文外文翻译,课题毕业论文、任务书、文献综述、开题报告、程序设计、图纸设计等资料可联系客服协助查找。