Skip to content

Hacking on Manticore

Yan edited this page Aug 8, 2017 · 21 revisions

Event System

Manticore implements a synchronous publish/subscribe system for executing code when certain analysis events happen.

If you are implementing an event handler there are certain things you need to know about locking: https://github.com/trailofbits/manticore/pull/433#issuecomment-320056828

Existing events that get produced

The following classes produce the following events:

  • manticore.core.cpu.Cpu
    • will_write_register, arguments: register, value
    • did_write_register, arguments: register, value
    • will_read_register, arguments: register
    • did_read_register, arguments: register, value
    • will_write_memory, arguments: where, expression, size
    • did_write_memory, arguments: where, expression, size
    • will_read_memory, arguments: where, size
    • did_read_memory, arguments: where, value, size
    • will_decode_instruction, arguments: pc
    • will_execute_instruction, arguments: instruction
    • will_emulate_instruction, arguments: instruction
    • did_emulate_instruction, arguments: instruction
    • did_execute_instruction, arguments: instruction
  • manticore.core.Executor
    • did_add_state, arguments: state_id, state
    • will_generate_testcase, arguments: state, prefix, message
    • will_fork_state, arguments: state, expression, solutions, policy
    • forking_state, arguments: state, expression, new_value, policy
    • will_load_state, arguments: current_state, current_state_id
    • will_terminate_state, arguments: current_state, current_state_id, message or exception
    • will_finish_run
    • All events produced by currently-executing manticore.core.State
  • manticore.core.State
    • state_generate_inputs, arguments: name, message
    • All events produced by manticore.platforms.Platform
  • manticore.platforms.Platform
    • All events produced by manticore.core.cpus.Cpu

Adding a Syscall

as of a0717aa661c0b04d5f73879b265da4da05756630

To implement a Linux syscall:

  • Look up the name of your syscall in manticore/platforms/linux_syscalls.py to get the correct name of your syscall for the corresponding syscall number.
  • In manticore/platforms/linux.py, add a method to the SLinux (Symbolic Linux) class for your syscall. Name your method precisely the name above. The arguments to this method should be
    • 1: self (standard Python self variable)
    • 2: cpu (manticore.core.abstractcpu.Cpu object representing current cpu state)
    • 3+: arguments to the syscall
  • Implement the logic of the syscall in this method, using the Cpu APIs as needed
  • The method should return the value returned by the syscall

Adding an Instruction

as of c78ea5c9109191654d26c7bfd2bedd662dafcdc5

To implement a cpu instruction:

  • Open the file according to the architecture for this instruction
    • x86 is in manticore/core/cpu/x86.py
    • armv7 is in manticore/core/cpu/arm.py
  • Add a method to the Cpu class in either of those files that subclasses Cpu
    • Decorate it with the @instruction decorator
    • The arguments to the method should be
      • 1: self
      • 2+ one argument for every operand in instruction.operands as decoded by Capstone. The types of these arguments are manticore.core.abstractcpu.Operand which is a light wrapper over a Capstone operand object (e.g. ArmOp)) and notably support convenience .read and .write methods.
  • Implement the instruction's effects

Source Tree

manticore/
├── binary # code related to binary formats. ignore this
│   ├── grr
│   │   ├── __init__.py
│   │   └── snapshot.py
│   ├── __init__.py
│   └── pe
│       ├── __init__.py
│       └── minidump.py
├── core
│   ├── cpu # code implementing symbolic emulators
│   │   ├── abstractcpu.py
│   │   ├── arm.py
│   │   ├── bitwise.py
│   │   ├── cpufactory.py
│   │   ├── __init__.py
│   │   ├── register.py
│   │   └── x86.py
│   ├── executor.py # main symbolic execution file
│   ├── __init__.py
│   ├── mappings.py
│   ├── memory.py
│   ├── parser
│   │   ├── __init__.py
│   │   └── parser.py
│   ├── smtlib # code related to handling symbolic data
│   │   ├── constraints.py #
│   │   ├── expression.py # defines symbolic data types
│   │   ├── __init__.py
│   │   ├── operators.py # library of operators for transparently handling concrete or symbolic data
│   │   ├── solver.py # code for interacting with the SMT solver
│   │   └── visitors.py # code for transforming expression trees, including serializing to SMTLIB
│   └── state.py # defines type for program state
├── __init__.py
├── __main__.py
├── manticore.py # high level API object
├── platforms # operating system models implemented here
│   ├── cgcrandom.py
│   ├── decree.py
│   ├── __init__.py
│   ├── libc.py
│   ├── linux.py
│   ├── windows.py
│   └── windows_syscalls.py
└── utils
    ├── emulate.py # code integrating unicorn for emulation of unimplemented instructions
    ├── event.py
    ├── helpers.py
    ├── __init__.py
    ├── iterpickle.py
    └── nointerrupt.py

Building the html docs

  • Do a Manticore dev install (see README), or just install Sphinx
  • cd docs
  • make html