|Version 4 (modified by 9 years ago) ( diff ),|
Keywords: Debugging, Testing, Back-in-time, Program Comprehension, Dynamic Analysis
In contrast to symbolic debuggers, back-in-time debuggers help to understand complete infection chains and to follow failure causes back to their defects. As the reasons for observable failures happened in the past, these debuggers record all run-time information before the failure occurs and then present it afterwards. Developers start with the observable failure, step backward, and search for infections at each point in the program’s execution history. By asking questions about a program’s run-time such as: “Where did the value of a variable change?”, they can develop a deeper understanding of infection chains step by step until it is clear how failures come to be.
For the purpose of localizing failure causes, our back-in-time debugger called PathFinder offers developers access to the entire execution history of a failing test case. Starting with a test case as a reproducible entry point, we record its behavior, present the run-time data in form of an explorable call tree, and so allow developers to follow the infection chain back to its root cause. In doing so, we provide arbitrary navigation through method call trees and their state spaces in both forward and backward direction. We restrict dynamic analysis to partial traces and, primarily, to the granularity level of methods. Apart from common back-in-time features, such as a query engine for getting a deeper understanding of what happened, our approach possesses two distinguishing characteristics. First, our step-wise run-time analysis (see more information below) allows for immediate access to run-time information of reproducible and deterministic test cases. Second, the integration of anomalies classifies suspicious trace data and so facilitates navigation in large traces (see also test-driven fault navigation).