您好,欢迎访问三七文档
第3章程序安全本章要点具有安全隐患的编程错误恶意代码防止恶意代码和脆弱性的程序开发控制控制程序运行时的缺陷程序构成了一个计算机系统的很多部分,因此多种形式保护程序是计算机安全的核心。我们将所有代码片称之为“程序”(program)。这里需要提出两个重要问题:怎样消除程序中的缺陷?在程序有缺陷的情况下,如何保护计算机资源?本章讨论的是一般的程序话题,包括程序编写。程序安全中一个重要问题是信任。信任问题是指:假设提供一个已完成的程序,如何来确定它的安全性或者说如何以最安全的方式使用它?答案是采用独立的第三方的评估。3.1安全程序评估程序安全与软件质量的评估相似,一种评估软件安全性或质量的方法是让人们列出能反映该软件整体安全的那些特性。然而,不同的人有不同的答案。人们对软件质量的总体设想也会影响对安全性的评估。一般而言,开发者把错误的数量和种类作为衡量产品质量的依据。当一个人在从事软件活动的过程中有所疏失时,我们称之为过失(error)。过失可能会在计算机程序中导致一个错误(fault),或者一个不确定的步骤、命令、过程或数据定义。一个单独的过失可以产生很多错误,一个错误可以隐藏在任何产品的开发和维护中。一次失效(failure)就是对系统要求行为的一次违反。一次失效意味着系统没有按照需求执行。错误是对系统的内部观点而言的,是开发者所见到的;而失效则是对系统的外部观点而言的,是用户看到的问题。3.1.1修改错误修改错误是评估安全质量的一种方法。计算机安全工作建立在“查找错误并打补丁”(penetrateandpatch)的模式上。分析专家在该模式下寻找错误,并给错误打上补丁。3.1.1修改错误(续)缺陷:1)修补指定问题的压力使得人们仅仅关注错误本身,而不是与之相关的上下文环境。2)在离错误较远的区域,其副作用不明显。3)修补一个问题时常导致其他地方的失败,或者说补丁仅仅解决一个地方的问题,而没有解决相关地方的问题。4)打补丁可能会影响系统的功能和性能,所以补丁经常不能恰当地修补系统错误。3.1.2意外行为“程序安全缺陷”(programsecurityflaw)是由于程序的脆弱点而引起的不恰当的程序行为。“脆弱点”和“缺陷”这组词与“错误”和“失效”这组词之间并没有直接的对应关系。一个缺陷可以是一个错误或是失效,而脆弱点经常用来描述某一类缺陷,诸如缓冲区溢出。尽管不一致,但应该记住:我们必须从两个方面来看待脆弱点和缺陷,即起因和影响。程序安全性缺陷可以来源于任何种类的软件错误。有必要将程序缺陷划分为两种逻辑类别:由开发者的疏忽所引起的错误和恶(有)意设计的缺陷。3.1.2意外行为(续)分类帮助我们理解一些方法,用以防止将缺陷有意或无意地引入到以后的代码编写中。一个因疏忽而引起的错误给用户及其组织带来的损失可能与恶意漏洞带来的损失相当。计算机攻击(cyberattack)即有意的安全事件,是如今最大的安全威胁。从根本上说安全是困难的,安全时常与有效性和性能相冲突,而且错误的安全解决方案会阻碍安全编程的真实进展。我们还没有技术来消除或解决所有的程序安全缺陷。原因有两个:3.1.2意外行为(续)1)程序控制是在单独的程序和程序员的级别上实施的。功能测试是解决程序“应该做什么”的问题,而安全测试还要确定“不应该做什么”的问题。要保证程序精确地按照设计者和用户的意图来执行而没有其他的行为,这几乎是不可能的。在一个复杂的大型系统中,不管设计者或程序员的意图何在,许多相关模块都以各种各样难以控制的方式交织着。巨大的规模和复杂性使得我们不可能去预防和检查所有缺陷。想要植入恶意代码的程序员可以利用系统的不完整性成功地将漏洞隐藏其中。3.1.2意外行为(续)2)程序设计和软件工程技术的发展迅速远远超过了计算机安全技术的发展速度。所以我们经常发现自己还在努力保护去年的技术,而软件开发者却正迅速地采用当前最新的技术了。#尽管如此,我们可以通过理解什么导致错误以及怎样阻止它,来开发技术和工具,保护大多数计算机的应用程序。3.1.3缺陷类型Landwehr等提出了一种关于程序缺陷的分类法,首先分为有意和无意的缺陷。进一步将有意缺陷细分为恶意和非恶意的类型。无意的缺陷分为6类:失效过失(不完善或不一致):许可权核查。域过失:对于数据的受控访问。序列化和混淆:程序流顺序。不充分的识别和鉴别:授权的基础。边界条件违规:首次或末次案例失效。其他可以利用的逻辑过失。3.2非恶意的程序漏洞3.2.1缓冲区溢出问题说明定义1缓冲区(或数组、字符串)是一个用来存储数据的空间。缓冲区位于内存中。由于内存是有限的,所以缓冲区的容量也是有限的。因此,在许多程序设计语言中,程序员必须声明缓冲区的最大容量,以使编译器能留出所需的空间。3.2.1缓冲区溢出(续)C程序中:charsample[10];sample[10]=‘B’;sample[i]=‘B’;//执行过程确定i的值3.2.1缓冲区溢出(续)若有:for(i=0;i10;i++)sample[i]=‘A’;sample[10]=‘B’;图3.1缓冲区会溢出的位置3.2.1缓冲区溢出(续)安全含义一个非恶意的过失造成的缺陷仍然会带来危害,因为一个恶意攻击者会利用这些缺陷。攻击者可以把数据插入到紧跟缓冲区的空间中以造成损害,可以诱使系统执行那些已经计划好的指令代码。这里,给出两类经常使用的缓冲区溢出攻击。一类是,攻击者可能替换系统空间中的代码,并有可能提高自身的权限。另一类是,攻击者可能会利用堆栈指针或返回值的寄存器。3.2.1缓冲区溢出(续)另一种缓冲区溢出在参数值被传递到程序中时发生,特别是当参数值被传递到Web服务器上时。例如,当参数转递到URL中,语法是:=(808)555-1212&parm2=2009Jan17(808)555-1212可能是电话,2009Jan17可能是日期。攻击者可能想了解一个非常长的电话号码,服务器做何反应,如,500位或1000位。这时程序会崩溃吗?会按照可以接受的方式崩溃吗?3.2.1缓冲区溢出(续)带数组的高级语言出现时,缓冲区溢出就随之出现了。起初给程序员和用户带来的困扰很小,最多不过出现系统崩溃。而攻击者利用它首先使系统崩溃,然后制造出可控制的故障,这就导致了严重的安全问题。3.2.2不完全验证问题说明还是,=(808)555-1212&parm2=2009Jan17,参数parm2表示日期,若输入1800Jan01、1800Feb30、2048Min32、1Aardvark2Many会发生怎样的情况?一种可能是,系统将由于尝试处理不正确的数据类型,而发生灾难性故障。另一种可能是接收到这些错误参数的程序将继续运行而得出错误的结果。3.2.2不完全验证(续)一种解决方法是预测出所有潜在可能发生的问题。通过提交验证技术,程序员可能避免用户无意制造的错误。然而,由于用户可以操作和修改URL,所以这种改进仍然脆弱。在这种情况下,提交的数据并没有经过完善验证,那些敏感的数据处于公开和不受控制的状态。3.2.2不完全验证(续)安全含义不完全的参数验证很容易被利用。例如,Things公司专门经营客户产品。如果客户想要购买20个编号555A的物品。每个物品的售价10元,则网站可以计算总价格是200元,客户端的浏览器会自动按格式填充数据:=101&part=555A&qy=20&price=10&ship=boat&shipcost=5&total=205攻击者可以做如下修改=101&part=555A&qy=20&price=1&ship=boat&shipcost=5&total=253.2.3“检测时刻到使用时刻”错误问题说明现代处理器和操作系统经常改变指令和程序的执行顺序。访问控制是确定具有访问权限的人或进程才能进行相应的访问,主要由访问策略实现。访问策略的执行代理对访问请求进行仲裁。检查时刻到使用时刻(time-of-checktotime-of-use,TOCTTOU)的漏洞与仲裁在执行中受到诱骗有关。该漏洞也称为序列化(serialization)漏洞或同步(synchronization)漏洞。3.2.3“检测时刻到使用时刻”错误(续)计算系统的攻击例子图3.2文件访问的数据结构图3.3被修改的数据#在访问被检查和检查结果被使用之间的时段,发生一些变化,并导致了检查结果的错误。3.2.3“检测时刻到使用时刻”错误(续)安全含义检查一个动作而执行另一个动作,是一个无效访问控制的原因。解决的办法有:1)确保关键参数在失控时不暴露。访问控制软件一直掌握请求数据直到请求动作完成。2)确保序列的完整性。也就是在验证期间禁止中断,或验证程序复制数据到程序空间,并基于该数据完成验证。3.2.4非恶意程序漏洞的结合使用以上三种漏洞还可以结合起来使用,以三叉式攻击出现。攻击者先借助缓冲区溢出来破坏机器上运行的任意代码,同时利用检查时刻至使用时刻的漏洞来添加一个新的系统用户。接下来,攻击者以新的用户身份登录系统并应用不完整的参数检查漏洞获得一定权限或做其他事情。因此,对任何一个小漏洞我们都必须了解并保护它不受攻击。3.3病毒和其他恶意代码就程序本身而言很少对安全性构成威胁。程序对数据进行操作,只有当数据和状态发生改变并满足其触发条件时,才采取行动。程序所做的大部分工作对用户来说是不可见的,所以一般用户不太可能发现它们在进行危险的活动。由于用户不能对计算机的程序和数据进行观察,攻击者可以编写自己的程序作为工具来访问和修改其他程序的数据。3.3.1关注恶意代码的原因恶意代码可以以意料之外的方式运行,我们把恶意代码看作是系统中的潜伏者,它可能是正在运行的程序的全部或一部分。恶意代码是如何进入系统的?当安装一个大型软件包,会运行诸如INSTALL或SETUP之类的命令;当浏览站点并盲目地从中下载应用程序,如Javaapplet或ActiveX等。在这些情况下,大量的程序与数据被传送,大量新的文件被创立,已经存在的文件被修改,而作为用户其实对这些实际的过程并不知情。3.3.1关注恶意代码的原因(续)恶意代码极具破坏性其他程序能做到的事情,恶意代码也能做到。恶意代码可能什么也不做,直到产生一些触发事件来驱动它运行。恶意代码每一次都可以做不同的事情。通常说,恶意代码行为的可预测性和两岁小孩行为的可预测性相似:大体我们知道他想做什么,甚至知道某些特定环境下的行为,但是他也经常能做出超乎想象的事情。恶意代码在非法获取的用户授权下运行,与用户有相同的权限,但无需用户授权,甚至无需用户知道。3.3.1关注恶意代码的原因(续)恶意代码的长期存在恶意代码不是现在才出现的一种新现象,早在1970年Ware和Anderson就准确地描述了病毒的威胁、程序的脆弱点和程序安全缺陷,特别是那些恶意部分。恶意代码将仍然继续存在下去。研究它们的外在表现和工作原理对我们阻止它们进行破坏活动,或者至少减弱它们的影响十分重要。3.3.1关注恶意代码的原因(续)产品漏洞和漏洞利用代码出现的时间间隔正在缩短。一般利用过程符合如下序列:1)攻击者发现一个先前的未知漏洞2)生产商知道这个漏洞3)有人开发出代码(称概念证明)证明在特定设置下的漏洞4)生产商开发并发布一个针对该漏洞的补丁或者对策5)用户采取相应保护措施6)有人扩展概念证明或者原始漏洞定义得到一个实际攻击一旦用户在实际攻击前接受并采取了相应保护措施,就可以避免灾难发生。一种攻击在保护措施可获得之前发生就是0天利用(Zerodayexploit)。3.3.2恶意代码的种类恶意代码(maliciouscode)和欺诈程序(r
本文标题:程序安全
链接地址:https://www.777doc.com/doc-3972839 .html