用于程序调试中的变量跟踪的方法和系统的制作方法_2

文档序号:9921952阅读:来源:国知局
。在此例中,断言语句“assert”被插入程序代码中。由此,程序的执行将在此中断,使得调试器可以获取分配给待检查变量的存储地址中实际存储的值。断言语句的工作原理是本领域已知的,在此不再赘述。换言之,如果变量guy的值在语句225处小于0,则认为变量值发生异常。
[0030]如果调试器在语句225的监测点发现异常,在传统方案中,需要在所有可能改变guy值的位置以及能够影响guy值的赋值语句处设置监测点,以便找到异常的根源。例如,在函数police_chase 210中,在语句212、214和216处,均有可能改变或者影响变量suspect的值,从而影响函数sentence 220中变量guy的值。因此,需要设置多个监测点来跟踪变量suspect。
[0031]而且,可以看到,语句212调用另一函数find_suspect 230来给变量suspect赋值。在函数find_suspect 230中,整型变量candidate的值是该函数的返回值。因此,在函数find_suspect230中,需要在给变量candidate赋值的语句235以及任何其他可能改变变量candidate值的赋值语句处设置监测点。
[0032]在这种传统方案中,程序员必须以人工方式添加这些监测点。这是因为,目前已知的任何调试器或者调试脚本均无法跨函数确定变量guy、suspect和candidate之间的关联关系。因此,监测点无法被自动添加到正确的位置。而且,假设导致变量suspect的值发生异常的根源是语句216。此时,在该语句之前的各个位置处(例如语句212和214处)设置的监测点所导致的程序执行的中断都将增加程序员在调试过程中的负担,使得调试过程非常繁琐。
[0033]为了解决上述以及其他潜在问题,本发明的实施例提供了一种用于程序调试中的变量跟踪方法。参考图3,其示出了根据本发明的一个示例性实施例的用于程序调试中的变量跟踪的方法300的示例性流程图。在一个实施例中,方法300可以由调试器调用和执行。方法300从较高的抽象级别给出了本发明所提出的变量跟踪的机制的概况。
[0034]方法300开始于步骤S310,在此对包含待跟踪变量的程序代码片段进行正向处理,以便收集与变量的别名(Alias)和/或用于赋值语句的控制流有关的运行时信息。以此方式,可以避免在监测点的自动设置过程中可能出现的、由变量别名和/或控制流(例如,循环)而引起的错误或漏检。步骤S310的具体实现将在下文详细描述。
[0035]将会理解,步骤S310是可选的,并且因此在图中以虚线示出。例如,在待跟踪的变量不存在别名和/或程序片段中不包括循环之类的控制流时,步骤S310可被省略。
[0036]在步骤S320,在程序代码中进行逆向扫描,以便在所有改变待跟踪变量的值的位置处,自动地设置针对有关表达式的监测点。根据本发明的实施例,用于收集运行时信息的步骤S310是按照程序的执行顺序执行的。在某些情况下,也可以找代码顺序执行。与此相反,根据本发明的实施例,步骤S320按照程序的执行顺序或者代码顺序的逆序执行。
[0037]根据本发明的实施例,在一个函数的函数体内,逆向扫描按照从最后一行代码到第一行代码的顺序执行扫描。在不同的函数之间,按照函数调用顺序的逆序来执行扫描。例如,如已知的,当程序执行时,将会创建运行栈。程序执行过程中所涉及到的函数按照调用顺序被压入堆栈中。在一个实施例中,可以按照从函数运行栈的栈顶到栈底的顺序,依次在相关函数中执行扫描。
[0038]根据本发明的实施例,通过对代码的逆向扫描,可以基于代码中与待跟踪变量有关的赋值表达式,在合适的位置插入针对适当表达式的监测点。特别地,通过根据赋值表达式自适应地更新作为扫描目标的表达式和/或变量,能够及时而准确地发现导致变量值异常的根源。
[0039]下面将结合图4详细描述方法300中的步骤S320。换言之,参考图4描述的方法400是步骤S320的具体实现。如图所示,方法400开始于步骤S410,在此确定待跟踪的变量(称为“第一变量”)以及与该第一变量相关联的待监测的表达式(称为“第一表达式”)。
[0040]根据本发明的实施例,在方法400被初次执行时,第一表达式例如可以由用户指定。在一个实施例中,第一表达式可以是与调试过程中被发现的变量值异常有关的表达式。例如,如果程序员在程序调试过程中发现某个表达式导致变量的值出现异常,他/她可以向调试器提供能够唯一地标识第一变量和第一表达式的信息。作为示例,用户可以通过鼠标之类的指点设备在IDE中选中第一表达式和第一变量。备选地或附加地,用户也可以在调试器提供的指定输入域中,以人工方式录入第一变量和第一表达式。其他任何方式均是可行的。
[0041]参考图2所示的示例,用户可以向调试器指示:待跟踪的第一变量是suspect,与该变量相关联的待监测的第一表达式是“suspect >= O”。用户还可以输入第一表达式在函数police_chase中的位置,例如行号,以便唯一地定位第一表达式。由此,第一变量suspect是待跟踪的目标变量,第一表达式“suspect >= O”是待监测的目标表达式。
[0042]方法400进行到步骤S420,在此对所调试的程序执行逆向扫描。如上所述,在一个实施例中,逆向扫描按照程序的执行顺序的逆序对代码进行扫描。备选地,也可以按照代码顺序的逆序执行扫描。逆向扫描的目的是搜索对第一变量进行赋值的表达式,称为“赋值表达式”。
[0043]作为示例,在C/C++之类的高级程序语言中,赋值表达式可以包括运算公式。一般而言,在一个程序语句中,如果待跟踪的目标变量(即,第一变量)处于等号的左边,则可以认为等号右边的表达式是赋值表达式。例如,在赋值语句“A = B+C”中,表达式“B+C”是用于变量A的赋值表达式。特别地,赋值表达式可以是一个单独的变量。例如,在赋值语句“A = B”中,变量B可被视作用于变量A的赋值表达式。备选地或附加地,赋值表达式可以包括函数调用或者能够改变第一变量的值的任何其他表达式。这方面的实施例将在下文讨论。在程序运行过程中,赋值表达式可被转换为类似于“r3 = rl+r2”、“mV r3,r2”之类的汇编语言表示。这是本领域中已知的,在此不再赘述。
[0044]为讨论之目的,仍然参考图2所示的示例。在对函数police_chase的逆向扫描中,可以确定语句216是一个涉及第一变量suspect的赋值语句。在赋值语句216中,表达式“ suspect+2 ”是赋值表达式。
[0045]方法400继而进行到步骤S430,在此响应于找到赋值表达式,在包含赋值表达式的赋值语句之后,设置与第一表达式相关联的监测点。如已知的,设置监测点的目的是为了检查在该位置处,待监测的第一表达式是否成立。在图2所示的示例中,可以在语句216之后,插入与第一表达式“suspect >= O”相关联的监视点。以C/C++语言为例,可以在语句216之后插入断言语句“assert (suspect >= O) ”,从而完成监视点的设置。
[0046]将会理解,监测点的设置并非一定依赖于assert语句,而是可以随着不同的程序而改变。本发明的范围在此方面不受限制。另外,监测点的插入位置并非一定要紧邻赋值语句之后。例如,在一个实施例之间,所设置的监测点与赋值语句可以间隔一个或多个其他语句,只要这些语句不会改变第一变量的值即可。本发明的范围在此方面亦不受限制。
[0047]通过设置该监测点,调试器可以在语句216之后、语句218之前确定表达式“suspect >= O”是否成立。如果该表达式不成立,则函数sentence函数中的表达式“guy>=O”必然不会成立。因此,赋值语句216可以被确定为导致变量guy的值异常的根源。
[0048]继续参考图4,在某些情况下,例如当搜索到的赋值语句被确定为变量值异常的根源时,方法400可以就此结束。在另一些情况中,可能需要对程序代码继续执行逆向扫描,称为“后续逆向扫描”。此时,方法400可以进行到可选的步骤S440(在图中以虚线示出),在此基于第一表达式和赋值表达式来确定第二表达式。该第二表达式将在接下来进行的后续逆向扫描中作为监测目标。特别地,根据本发明的实施例,所获得的第二表达式在语义上与第一表达式是相关的。更具体地说,第二表达式在包含赋值表达式的赋值语句之前的语义,与第一表达式在该赋值语句之后的语义相同。
[0049]考虑图2所述的具体示例。如上所述,第一变量是“suspect”,第一表达式是“suspect >= O”,并且赋值表达式是“suspect+2”。可以看到,赋值表达式中包含的变量只有第一变量。换言之,赋值表达式不包含除第一变量之外的其他变量。在这种情况下,在一个实施例中,可以利用赋值表达式来替换第一表达式中
当前第2页1 2 3 4 5 
网友询问留言 已有0条留言
  • 还没有人留言评论。精彩留言会获得点赞!
1