Surveyor provides a user interface for exploring, inspecting, and reasoning about programs. It is structured as a core engine supporting multiple user interfaces. There are currently two frontends: crux-dbg and surveyor-brick. It supports programs represented as:
- Machine code (x86_64 and PowerPC 32 and PowerPC 64)
- LLVM bitcode
- JVM bytecode
The primary frontend is currently crux-dbg, which is intended as a drop-in replacement for the crux-llvm tool, but with extra debugging capabilities.
git clone git@github.com:GaloisInc/surveyor.git
cd surveyor
git submodule update --init
ln -s cabal.project.dist cabal.project
cabal v2-build pkg:crux-dbgcabal v2-run exe:crux-dbg -- examples/crc_break.bcSurveyor will load the binary and make its contents available for exploration. The interface is styled after emacs. Commands can be run by pressing M-x and entering a command. Some useful commands include
describe-commandlist-functions
Selecting a function will list its blocks (eventually, this will be a rendered control flow graph). Within a block, the arrow keys can be used to select instructions. Machine code blocks can be viewed in two alternative intermediate representations: macaw and crucible. The relevant commands (accessible via M-x) are show-macaw-block and show-crucible-block, respectively.
The crux-dbg tool is intended to be a drop-in replacement for crux-llvm (and eventually other crux frontends). Beyond the functionality provided by crux-llvm, it adds:
- Support for explicit source-level breakpoints through the
crucible_breakpointfunction, which drops the user into an interactive TUI for inspecting symbolic execution states. Additionally, the breakpoint function can “capture” values for inspection in the symbolic debugger. - Signal handling to allow users to interrupt execution at any time by sending
SIGUSR2to thecrux-dbgprocess (e.g., to interrupt a non-terminating loop for diagnosis). - Eager checking of assertions for validity, dropping into the debugger as soon as any
crucible_assertdoes not hold. - Rendering of complex symbolic terms into graphviz graphs for easier visualization.
From the suspended symbolic execution state, the user can inspect the Crucible code being symbolically executed and inspect individual symbolic values at each program point. The symbolic debugger provides commands to step execution.
The surveyor-brick tool is intended to be a standalone interface for interactively loading programs and exploring them by initiating symbolic execution queries and interactively adding breakpoints and watchpoints. These features are not yet complete.
The frontends support a number of common commands:
describe-commandprovides explanations of the capabilities and arguments for each commandlist-functionslists all of the functions in the programload-fileloads a new programenable-recordingrecords a trace of symbolic events that can be replayed in the symbolic debuggerstep-trace-backwardswalks backwards in time through a recorded trace (supporting replay debugging)step-trace-forwardswalks forwards in time through a recorded trace (without resuming program execution)step-executionsteps symbolic execution forward by one stepcontinue-executionresumes symbolic exeuctionstep-out-executionsteps out of the current function frame (to the caller)
Commands can be accessed by invoking them through the minibuffer. To activate the minibuffer, use M-x. Commands auto-complete based on fragments typed in. Commands that require additional arguments (e.g., file names) will prompt for them.
- Qt UI
- Web UI
- Interactive breakpoints
- Symbolic watchpoints
- Scheme extensions for dynamic value inspection
- Integration with external tools (e.g., ghidra)