Skip to content

bitdefender/distributed.tracer

Repository files navigation

Distributed Tracer

Distributed version of RIVER. Cardinal can trace multiple testcases at a time and log the resulting traces.

How to use it

    ./run.sh [binary-id] [runs] [cores] [benchmark-runs] [(no)rebuild] [(no)genetic]

             binary-id = unique identification string of the benchmark binary
             runs = number of testcases that are generated by base fuzzers
             cores = number of tracer processes that run in parallel
             benchmark-runs = number of repetitions for current benchmark
             (no)rebuild = if "rebuild", node-river build is updated
             (no)genetic = if "genetic", river.genetic component is enabled to enhance testcase quality

Components

Cardinal is a distributed environment that searches for security flaws in multiple binaries at a time. Cardinal testing targets can be either executables or source code. Cardinal tests represent binary stream generated by state-of-art fuzzers. The tests represent input data for testing targets. Once tests are sent to targets as input stream, the execution trace is collected by Cardinal and stored inside a global coverage state corresponding to the target executable.

tracer.node

tracer.node is the Cardinal component that starts the target execution. It sends the test as input to target program and collects the execution trace. The execution is traced using RIVER, a dynamic binary translation system. The trace format is shown below.

Trace representation

mongo.rabbit.bridge

mongo.rabbit.bridge component is based on Mongo Oplog. It tracks the Mongo changes in the tests collections and creates a Rabbit message corresponding to the test. The message is inserted in the corresponding Rabbit queue(new test or traced test).

process.manager

process.manager represents the processes orchestrator. It is the utility that manages Cardinal subcomponents. process.manager starts/stops subcomponents, limits the number of running processes and allow user configuration of Cardinal. 'process.manager/processes.json' shows the configuration for each component process as command line. 'process.manager/resources.json' is the configuration file that allows limitation of component running instances. For example, if configuration file contains: 'tracer.node : 10', then a maximum of 10 process instances of 'tracer.node' are allowed to run simultaneously.

river.genetic

river.genetic is a component that allows ranking input by the basic blocks exercised in the target program. In this manner, only inputs that discover new code or inputs that discover new paths are kept and used for mutations. This component can be disabled from command-line. Cardinal is more efficient when 'river.genetic' is enabled.

state.aggregator

The individual traces produced by 'tracer.node' represent the path in binary described by ordered basic blocks followed by target program when individual input is sent at runtime. One program execution shows one path. By gathering these paths together per each executable, Cardinal is able to show a global coverage state showing what basic blocks where exercised, how many times and what are the ancestors (incoming edge). The state aggregator is able to gather the traces from database and grouping these in local and global collections. The global collections per executable represent the current coverage obtained by Cardinal in testing the executables.

state.manager

The components is a helper for state.aggregator and can be used by command line to clean coverage data by executable id.

web.api and web.interface

Cardinal has a user-friendly interface that allows showing the status of each executable tested with Cardinal. It shows how many tests were traced, how many of them failed (possible vulnerabilities), what resources are used for testing each executable and the global coverage state.

Cardinal architecture

Cardinal architecture