Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fuzzer: some fixes and improvements #1608

Merged
merged 7 commits into from
Oct 6, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 6 additions & 3 deletions .github/workflows/fuzzing.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,9 @@ on:
- wasm_instrument
- decimal
- parse_decimal
- role_assignment
- royalty_state
- system

duration_hours:
description: 'Fuzzing duration [h]'
Expand Down Expand Up @@ -195,12 +198,12 @@ jobs:
# Archive panic summary files (useful when grouping crashes by panic type)
find local_* -type f -name "*.panic" | tee -a list
echo "archive results"
tar -hczf fuzz_transaction.tgz -T list
tar -hczf fuzz_results.tgz -T list

- name: Upload artifacts
if: success() || failure() || cancelled()
uses: actions/upload-artifact@v3
with:
name: fuzz_${{ github.event.inputs.fuzz_target }}.tgz
name: fuzz_results.tgz
path: |
fuzz-tests/fuzz_${{ github.event.inputs.fuzz_target }}.tgz
fuzz-tests/fuzz_results.tgz
34 changes: 21 additions & 13 deletions fuzz-tests/fuzz.sh
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,10 @@ DFLT_TIMEOUT=1000
function usage() {
echo "$0 [FUZZER/COMMAND] [SUBCOMMAND] [FUZZ-TARGET] [COMMAND-ARGS]"
echo "Available targets:"
echo " transaction"
echo " wasm_instrument"
echo " decimal"
echo " parse_decimal"
echo " role_assignment"
echo " system"
echo " royalty_state"
targets=$(./list-fuzz-targets.sh)
for t in $targets ; do
echo " $t"
done
echo "Available fuzzers"
echo " libfuzzer - 'cargo fuzz' wrapper"
echo " afl - 'cargo afl' wrapper"
Expand Down Expand Up @@ -77,6 +74,17 @@ function error() {
exit 1
}

function check_target_available() {
local target=$1
targets=$(./list-fuzz-targets.sh)
for t in $targets ; do
if [ "$t" = "$target" ] ; then
return 0
fi
done
return 1
}

function fuzzer_libfuzzer() {
local cmd=$DFLT_SUBCOMMAND
if [ $# -ge 1 ] ; then
Expand Down Expand Up @@ -201,10 +209,11 @@ function generate_input() {
return
fi

if [ $target = "transaction" -o $target = "wasm_instrument" -o $target = "decimal" -o $target = "parse_decimal" -o $target = "role_assignment" -o $target = "system" -o $target = "royalty_state" ] ; then
if [ ! -f target-afl/release/${target} ] ; then
if check_target_available $target ; then
# in 'raw' mode we don't need afl binary
if [ ! -f target-afl/release/${target} -a $mode != "raw" ] ; then
echo "target binary 'target-afl/release/${target}' not built. Call below command to build it"
echo "$THIS_SCRIPT afl build"
echo "$THIS_SCRIPT afl build $target"
exit 1
fi

Expand All @@ -218,9 +227,8 @@ function generate_input() {
fi


if [ $target = "transaction" -o $target = "decimal" -o $target = "parse_decimal" -o $target = "role_assignment" -o $target = "system" -o $target = "royalty_state" ] ; then
if [ $target != "wasm_instrument" ] ; then
# Collect input data

cargo nextest run test_${target}_generate_fuzz_input_data --release

if [ $mode = "raw" ] ; then
Expand All @@ -232,7 +240,7 @@ function generate_input() {
#mv ../radix-engine-tests/manifest_*.raw ${curr_path}/${raw_dir}
mv ${target}_*.raw ${curr_path}/${raw_dir}

elif [ $target = "wasm_instrument" ] ; then
else
# TODO generate more wasm inputs. and maybe smaller
if [ $mode = "raw" ] ; then
find .. -name "*.wasm" | while read f ; do cp $f $final_dir ; done
Expand Down
4 changes: 4 additions & 0 deletions fuzz-tests/list-fuzz-targets.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
#!/bin/bash

# List all fuzz targets
cargo metadata --format-version=1 | jq -r '.packages[] | select(.source == null) .targets[] | select(.kind[] | contains("bin")).name'
25 changes: 13 additions & 12 deletions fuzz-tests/process_fuzz_results.sh
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,14 @@
set -e
set -u

#TARGET=transaction
TARGET=wasm_instrument
CRASH_INVENTORY_FILE=crash_inventory.txt
CRASH_SUMMARY=crash_summary.txt
ARTIFACT_NAME=fuzz_${TARGET}.tgz
ARTIFACT_NAME=fuzz_results.tgz
INSPECT_TIMEOUT=20000
url_or_dir=$1
inspect_timeout=${2:-$INSPECT_TIMEOUT}
gh_run_id=
local_dir=

target=

function usage() {
echo "$0 <run-id>"
Expand Down Expand Up @@ -53,6 +50,9 @@ function validate_gh_run() {
exit 1
fi

# this variable is expected outside this function
target=$(echo $title | grep 'target=' | sed -E 's/^.*target=([A-Za-z0-9_-]+) .*/\1/g')

echo "Found run:"
echo " title : $title"
echo " branch: $branch"
Expand Down Expand Up @@ -107,7 +107,7 @@ function inspect_crashes() {
fi
pushd $repo_dir > /dev/null
echo "Building simple fuzzer"
./fuzz.sh simple build $TARGET
./fuzz.sh simple build $target
popd > /dev/null
echo "Checking crash/hangs files"
for f in $files ; do
Expand All @@ -119,8 +119,8 @@ function inspect_crashes() {
fi

# calling target directly to get rid of unnecessary debugs
#./fuzz.sh simple run $TARGET ../../$f >/dev/null || true
cmd="${repo_dir}/target/release/${TARGET} $f"
#./fuzz.sh simple run $target ../../$f >/dev/null || true
cmd="${repo_dir}/target/release/${target} $f"
echo
echo "file : $f"
echo "command : $cmd"
Expand All @@ -136,7 +136,7 @@ function inspect_crashes() {

cat <<EOF >> $CRASH_INVENTORY_FILE
Crash/hang info
command : radixdlt-scrypto/fuzz-tests/target/release/${TARGET} <file>
command : radixdlt-scrypto/fuzz-tests/target/release/${target} <file>
EOF
for f in *.panic ; do
echo
Expand Down Expand Up @@ -179,8 +179,6 @@ fi
# check if argument is an existing AFL output directory
if [ -d $url_or_dir ] ; then
if ls -A ${url_or_dir}/*/fuzzer_stats > /dev/null ; then
local_dir=$url_or_dir
afl_dir=$local_dir
work_dir=local_$(date -u +%Y%m%d%H%M%S)
else
echo "This is not AFL output directory"
Expand All @@ -189,15 +187,18 @@ if [ -d $url_or_dir ] ; then
else
gh_run_id=${url_or_dir##*/}
work_dir=run_${gh_run_id}
afl_dir="afl/${TARGET}"
fi


if [ "$gh_run_id" != "" ] ; then
validate_gh_run
# we know target after validate_gh_run
afl_dir="afl/${target}"
get_gh_artifacs
show_gh_summary $work_dir
else
target=${url_or_dir##*/}
afl_dir=$url_or_dir
mkdir -p $work_dir
afl_path=$(cd $(dirname $afl_dir) ; pwd)
ln -s $afl_path $work_dir
Expand Down
2 changes: 1 addition & 1 deletion fuzz-tests/src/bin/system.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ use serde::{Deserialize, Serialize};

use radix_engine::prelude::ManifestArgs;
use radix_engine::types::ScryptoSbor;
use radix_engine_common::constants::XRD;
use radix_engine_common::prelude::{
scrypto_encode, GlobalAddress, NodeId, Own, ScryptoCustomTypeKind,
};
Expand Down Expand Up @@ -347,6 +346,7 @@ impl VmInvoke for FuzzSystem {
#[test]
fn test_system_generate_fuzz_input_data() {
use bincode::serialize;
use radix_engine_common::constants::XRD;
use std::fs;

{
Expand Down