1#!/bin/bash
2PROJECT_PATH=system/core/fs_mgr/libsnapshot
3FUZZ_TARGET=libsnapshot_fuzzer
4TARGET_ARCH=$(get_build_var TARGET_ARCH)
5FUZZ_BINARY=/data/fuzz/${TARGET_ARCH}/${FUZZ_TARGET}/${FUZZ_TARGET}
6DEVICE_INIT_CORPUS_DIR=/data/fuzz/${TARGET_ARCH}/${FUZZ_TARGET}/corpus
7DEVICE_GENERATED_CORPUS_DIR=/data/local/tmp/${FUZZ_TARGET}/corpus
8DEVICE_GCOV_DIR=/data/local/tmp/${FUZZ_TARGET}/gcov
9HOST_SCRATCH_DIR=/tmp/${FUZZ_TARGET}
10GCOV_TOOL=${HOST_SCRATCH_DIR}/llvm-gcov
11
12build_normal() (
13    pushd $(gettop)
14    NATIVE_COVERAGE="" NATIVE_LINE_COVERAGE="" NATIVE_COVERAGE_PATHS="" m ${FUZZ_TARGET}
15    ret=$?
16    popd
17    return ${ret}
18)
19
20build_cov() {
21    pushd $(gettop)
22    NATIVE_COVERAGE="true" NATIVE_LINE_COVERAGE="true" NATIVE_COVERAGE_PATHS="${PROJECT_PATH}" m ${FUZZ_TARGET}
23    ret=$?
24    popd
25    return ${ret}
26}
27
28prepare_device() {
29    adb root && adb remount &&
30    adb shell mkdir -p ${DEVICE_GENERATED_CORPUS_DIR} &&
31    adb shell rm -rf ${DEVICE_GCOV_DIR} &&
32    adb shell mkdir -p ${DEVICE_GCOV_DIR}
33}
34
35push_binary() {
36    adb push ${ANDROID_PRODUCT_OUT}/${FUZZ_BINARY} ${FUZZ_BINARY} &&
37    adb push ${ANDROID_PRODUCT_OUT}/${DEVICE_INIT_CORPUS_DIR} $(dirname ${FUZZ_BINARY})
38}
39
40prepare_host() {
41    which lcov || {
42        echo "please run:";
43        echo "   sudo apt-get install lcov ";
44        return 1;
45    }
46    rm -rf ${HOST_SCRATCH_DIR} &&
47    mkdir -p ${HOST_SCRATCH_DIR}
48}
49
50# run_snapshot_fuzz -runs=10000
51generate_corpus() {
52    [[ "$@" ]] || { echo "run with -runs=X"; return 1; }
53
54    prepare_device &&
55    build_normal &&
56    push_binary &&
57    adb shell ${FUZZ_BINARY} "$@" ${DEVICE_INIT_CORPUS_DIR} ${DEVICE_GENERATED_CORPUS_DIR}
58}
59
60run_snapshot_fuzz() {
61    prepare_device &&
62    build_cov &&
63    push_binary &&
64    adb shell GCOV_PREFIX=${DEVICE_GCOV_DIR} GCOV_PREFIX_STRIP=3 \
65        ${FUZZ_BINARY} \
66        -runs=0 \
67        ${DEVICE_INIT_CORPUS_DIR} ${DEVICE_GENERATED_CORPUS_DIR}
68}
69
70show_fuzz_result() {
71    prepare_host &&
72    unzip -o -j -d ${HOST_SCRATCH_DIR} ${ANDROID_PRODUCT_OUT}/coverage/data/fuzz/${TARGET_ARCH}/${FUZZ_TARGET}/${FUZZ_TARGET}.zip &&
73    adb shell find ${DEVICE_GCOV_DIR} -type f | xargs -I {} adb pull {} ${HOST_SCRATCH_DIR} &&
74    ls ${HOST_SCRATCH_DIR} &&
75    cat > ${GCOV_TOOL} <<< '
76#!/bin/bash
77exec llvm-cov gcov "$@"
78' &&
79    chmod +x ${GCOV_TOOL} &&
80    lcov --directory ${HOST_SCRATCH_DIR} --base-directory $(gettop) --gcov-tool ${GCOV_TOOL} --capture -o ${HOST_SCRATCH_DIR}/report.cov &&
81    genhtml ${HOST_SCRATCH_DIR}/report.cov -o ${HOST_SCRATCH_DIR}/html &&
82    echo file://$(realpath ${HOST_SCRATCH_DIR}/html/index.html)
83}
84
85# run_snapshot_fuzz -runs=10000
86run_snapshot_fuzz_all() {
87    generate_corpus "$@" &&
88    run_snapshot_fuzz &&
89    show_fuzz_result
90}
91