зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1879171 - Add AFL++ fuzzing build r=decoder,taskgraph-reviewers,bhearsum
Differential Revision: https://phabricator.services.mozilla.com/D208401
This commit is contained in:
Родитель
599c8b98ba
Коммит
bcc2c75572
|
@ -62,6 +62,8 @@ if CONFIG["LIBFUZZER"]:
|
|||
LOCAL_INCLUDES += [
|
||||
"/tools/fuzzing/libfuzzer",
|
||||
]
|
||||
elif CONFIG["FUZZING_INTERFACES"]:
|
||||
USE_LIBS += ["fuzzer-interface"]
|
||||
|
||||
if CONFIG["MOZ_GECKODRIVER"]:
|
||||
DEFINES["MOZ_GECKODRIVER"] = True
|
||||
|
|
|
@ -0,0 +1,9 @@
|
|||
. "$topsrcdir/browser/config/mozconfigs/linux64/nightly-fuzzing-asan"
|
||||
|
||||
export CC="$MOZ_FETCHES_DIR/afl-instrumentation/bin/afl-clang-fast"
|
||||
export CXX="$MOZ_FETCHES_DIR/afl-instrumentation/bin/afl-clang-fast++"
|
||||
|
||||
export HOST_CC="$MOZ_FETCHES_DIR/clang/bin/clang"
|
||||
export HOST_CXX="$MOZ_FETCHES_DIR/clang/bin/clang++"
|
||||
|
||||
. "$topsrcdir/build/mozconfig.common.override"
|
|
@ -33,9 +33,10 @@ if CONFIG["FUZZING"]:
|
|||
include("/tools/fuzzing/libfuzzer-config.mozbuild")
|
||||
|
||||
if CONFIG["FUZZING_INTERFACES"]:
|
||||
USE_LIBS += [
|
||||
"static:fuzzer",
|
||||
]
|
||||
if CONFIG["LIBFUZZER"]:
|
||||
USE_LIBS += ["static:fuzzer"]
|
||||
else:
|
||||
USE_LIBS += ["static:fuzzer-interface"]
|
||||
|
||||
USE_LIBS += [
|
||||
"static:js",
|
||||
|
|
|
@ -11,8 +11,10 @@
|
|||
|
||||
#include <stdio.h> // fflush, fprintf, fputs
|
||||
|
||||
#include "FuzzerDefs.h"
|
||||
#include "FuzzingInterface.h"
|
||||
#ifdef LIBFUZZER
|
||||
# include "FuzzerDefs.h"
|
||||
#endif
|
||||
|
||||
#include "jsapi.h" // JS_ClearPendingException, JS_IsExceptionPending
|
||||
|
||||
#include "js/CompilationAndEvaluation.h" // JS::Evaluate
|
||||
|
|
|
@ -26,9 +26,10 @@ UNIFIED_SOURCES += [
|
|||
|
||||
if CONFIG["FUZZING_INTERFACES"]:
|
||||
UNIFIED_SOURCES += ["jsrtfuzzing/jsrtfuzzing.cpp"]
|
||||
USE_LIBS += [
|
||||
"static:fuzzer",
|
||||
]
|
||||
if CONFIG["LIBFUZZER"]:
|
||||
USE_LIBS += ["static:fuzzer"]
|
||||
else:
|
||||
USE_LIBS += ["static:fuzzer-interface"]
|
||||
|
||||
if CONFIG["FUZZING_JS_FUZZILLI"]:
|
||||
OS_LIBS += ["rt"]
|
||||
|
|
|
@ -10,8 +10,11 @@ SOURCES += [
|
|||
"xpcshell.cpp",
|
||||
]
|
||||
|
||||
if CONFIG["LIBFUZZER"]:
|
||||
USE_LIBS += ["fuzzer"]
|
||||
if CONFIG["FUZZING_INTERFACES"]:
|
||||
if CONFIG["LIBFUZZER"]:
|
||||
USE_LIBS += ["fuzzer"]
|
||||
else:
|
||||
USE_LIBS += ["fuzzer-interface"]
|
||||
|
||||
if CONFIG["MOZ_WIDGET_TOOLKIT"] == "cocoa":
|
||||
SOURCES += [
|
||||
|
|
|
@ -1084,6 +1084,56 @@ linux64-asan-fuzzing/noopt:
|
|||
optimization:
|
||||
skip-unless-expanded: null
|
||||
|
||||
linux64-asan-fuzzing-afl/opt:
|
||||
description: "Linux64 Fuzzing Opt ASAN AFL"
|
||||
index:
|
||||
product: firefox
|
||||
job-name: linux64-fuzzing-asan-afl-opt
|
||||
attributes:
|
||||
# The gtest libxul contains libFuzzer targets
|
||||
skip-verify-test-packaging: true
|
||||
treeherder:
|
||||
platform: linux64/asan
|
||||
symbol: Boaf
|
||||
worker:
|
||||
env:
|
||||
PERFHERDER_EXTRA_OPTIONS: asan-fuzzing-afl
|
||||
MOZ_AUTOMATION_PACKAGE_TESTS: "1"
|
||||
AFL_CC: /builds/worker/fetches/clang/bin/clang
|
||||
AFL_CXX: /builds/worker/fetches/clang/bin/clang++
|
||||
AFL_LLVM_INSTRUMENT: llvmnative
|
||||
AFL_LLVM_NO_RPATH: "1"
|
||||
max-run-time: 7200
|
||||
run:
|
||||
using: mozharness
|
||||
actions: [get-secrets, build]
|
||||
config:
|
||||
- builds/releng_base_firefox.py
|
||||
- builds/releng_base_linux_64_builds.py
|
||||
script: "mozharness/scripts/fx_desktop_build.py"
|
||||
secrets: true
|
||||
custom-build-variant-cfg: fuzzing-asan-tc
|
||||
mozconfig-variant: nightly-fuzzing-asan-afl
|
||||
tooltool-downloads: public
|
||||
use-sccache: true
|
||||
fetches:
|
||||
toolchain:
|
||||
- linux64-afl-instrumentation
|
||||
- linux64-clang
|
||||
- linux64-rust-dev
|
||||
- linux64-rust-size
|
||||
- linux64-cbindgen
|
||||
- linux64-dump_syms
|
||||
- linux64-llvm-symbolizer
|
||||
- linux64-sccache
|
||||
- linux64-nasm
|
||||
- linux64-node
|
||||
- linux64-pkgconf
|
||||
- sysroot-x86_64-linux-gnu
|
||||
- sysroot-wasm32-wasi
|
||||
optimization:
|
||||
skip-unless-expanded: null
|
||||
|
||||
linux64-asan-fuzzing-nyx/opt:
|
||||
description: "Linux64 Fuzzing Opt ASAN NYX"
|
||||
index:
|
||||
|
|
|
@ -28,3 +28,21 @@ LazyLogModule gFuzzingLog("nsFuzzing");
|
|||
#endif
|
||||
|
||||
} // namespace mozilla
|
||||
|
||||
#ifdef AFLFUZZ
|
||||
__AFL_FUZZ_INIT();
|
||||
|
||||
int afl_interface_raw(FuzzingTestFuncRaw testFunc) {
|
||||
# ifdef __AFL_HAVE_MANUAL_CONTROL
|
||||
__AFL_INIT();
|
||||
# endif
|
||||
uint8_t* buf = __AFL_FUZZ_TESTCASE_BUF;
|
||||
|
||||
while (__AFL_LOOP(1000)) {
|
||||
size_t len = __AFL_FUZZ_TESTCASE_LEN;
|
||||
testFunc(buf, len);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif // AFLFUZZ
|
||||
|
|
|
@ -37,55 +37,17 @@ extern LazyLogModule gFuzzingLog;
|
|||
MOZ_LOG(mozilla::gFuzzingLog, mozilla::LogLevel::Verbose, args)
|
||||
#endif // JS_STANDALONE
|
||||
|
||||
} // namespace mozilla
|
||||
|
||||
typedef int (*FuzzingTestFuncRaw)(const uint8_t*, size_t);
|
||||
|
||||
#ifdef AFLFUZZ
|
||||
|
||||
static int afl_interface_raw(const char* testFile,
|
||||
FuzzingTestFuncRaw testFunc) {
|
||||
char* buf = NULL;
|
||||
|
||||
while (__AFL_LOOP(1000)) {
|
||||
std::ifstream is;
|
||||
is.open(testFile, std::ios::binary);
|
||||
is.seekg(0, std::ios::end);
|
||||
int len = is.tellg();
|
||||
is.seekg(0, std::ios::beg);
|
||||
MOZ_RELEASE_ASSERT(len >= 0);
|
||||
if (!len) {
|
||||
is.close();
|
||||
continue;
|
||||
}
|
||||
buf = (char*)realloc(buf, len);
|
||||
MOZ_RELEASE_ASSERT(buf);
|
||||
is.read(buf, len);
|
||||
is.close();
|
||||
testFunc((uint8_t*)buf, (size_t)len);
|
||||
}
|
||||
|
||||
free(buf);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
# define MOZ_AFL_INTERFACE_COMMON() \
|
||||
char* testFilePtr = getenv("MOZ_FUZZ_TESTFILE"); \
|
||||
if (!testFilePtr) { \
|
||||
fprintf(stderr, \
|
||||
"Must specify testfile in MOZ_FUZZ_TESTFILE environment " \
|
||||
"variable.\n"); \
|
||||
return 1; \
|
||||
} \
|
||||
/* Make a copy of testFilePtr so the testing function can safely call \
|
||||
* getenv \
|
||||
*/ \
|
||||
std::string testFile(testFilePtr);
|
||||
int afl_interface_raw(FuzzingTestFuncRaw testFunc);
|
||||
|
||||
# define MOZ_AFL_INTERFACE_RAW(initFunc, testFunc, moduleName) \
|
||||
static int afl_fuzz_##moduleName(const uint8_t* data, size_t size) { \
|
||||
MOZ_RELEASE_ASSERT(data == NULL && size == 0); \
|
||||
MOZ_AFL_INTERFACE_COMMON(); \
|
||||
return ::mozilla::afl_interface_raw(testFile.c_str(), testFunc); \
|
||||
return afl_interface_raw(testFunc); \
|
||||
} \
|
||||
static void __attribute__((constructor)) AFLRegister##moduleName() { \
|
||||
::mozilla::FuzzerRegistry::getInstance().registerModule( \
|
||||
|
@ -110,6 +72,4 @@ static int afl_interface_raw(const char* testFile,
|
|||
MOZ_LIBFUZZER_INTERFACE_RAW(initFunc, testFunc, moduleName); \
|
||||
MOZ_AFL_INTERFACE_RAW(initFunc, testFunc, moduleName);
|
||||
|
||||
} // namespace mozilla
|
||||
|
||||
#endif // FuzzingInterface_h__
|
||||
|
|
|
@ -1,54 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
/*
|
||||
* Interface implementation for the unified fuzzing interface
|
||||
*/
|
||||
|
||||
#include "nsIFile.h"
|
||||
#include "nsIPrefService.h"
|
||||
#include "nsIProperties.h"
|
||||
|
||||
#include "FuzzingInterfaceStream.h"
|
||||
|
||||
#include "mozilla/Assertions.h"
|
||||
|
||||
#ifndef JS_STANDALONE
|
||||
# include "nsNetUtil.h"
|
||||
#endif
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
#ifdef AFLFUZZ
|
||||
|
||||
void afl_interface_stream(const char* testFile,
|
||||
FuzzingTestFuncStream testFunc) {
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIProperties> dirService =
|
||||
do_GetService(NS_DIRECTORY_SERVICE_CONTRACTID);
|
||||
MOZ_RELEASE_ASSERT(dirService != nullptr);
|
||||
nsCOMPtr<nsIFile> file;
|
||||
rv = dirService->Get(NS_OS_CURRENT_WORKING_DIR, NS_GET_IID(nsIFile),
|
||||
getter_AddRefs(file));
|
||||
MOZ_RELEASE_ASSERT(NS_SUCCEEDED(rv));
|
||||
file->AppendNative(nsDependentCString(testFile));
|
||||
while (__AFL_LOOP(1000)) {
|
||||
nsCOMPtr<nsIInputStream> inputStream;
|
||||
rv = NS_NewLocalFileInputStream(getter_AddRefs(inputStream), file);
|
||||
MOZ_RELEASE_ASSERT(NS_SUCCEEDED(rv));
|
||||
if (!NS_InputStreamIsBuffered(inputStream)) {
|
||||
nsCOMPtr<nsIInputStream> bufStream;
|
||||
rv = NS_NewBufferedInputStream(getter_AddRefs(bufStream),
|
||||
inputStream.forget(), 1024);
|
||||
MOZ_RELEASE_ASSERT(NS_SUCCEEDED(rv));
|
||||
inputStream = bufStream;
|
||||
}
|
||||
testFunc(inputStream.forget());
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
} // namespace mozilla
|
|
@ -28,32 +28,25 @@
|
|||
|
||||
#include "FuzzingInterface.h"
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
typedef int (*FuzzingTestFuncStream)(nsCOMPtr<nsIInputStream>);
|
||||
|
||||
#ifdef AFLFUZZ
|
||||
void afl_interface_stream(const char* testFile, FuzzingTestFuncStream testFunc);
|
||||
|
||||
# define MOZ_AFL_INTERFACE_COMMON(initFunc) \
|
||||
if (initFunc) initFunc(NULL, NULL); \
|
||||
char* testFilePtr = getenv("MOZ_FUZZ_TESTFILE"); \
|
||||
if (!testFilePtr) { \
|
||||
fprintf(stderr, \
|
||||
"Must specify testfile in MOZ_FUZZ_TESTFILE environment " \
|
||||
"variable.\n"); \
|
||||
return; \
|
||||
} \
|
||||
/* Make a copy of testFilePtr so the testing function can safely call \
|
||||
* getenv \
|
||||
*/ \
|
||||
std::string testFile(testFilePtr);
|
||||
|
||||
# define MOZ_AFL_INTERFACE_STREAM(initFunc, testFunc, moduleName) \
|
||||
TEST(AFL, moduleName) \
|
||||
{ \
|
||||
MOZ_AFL_INTERFACE_COMMON(initFunc); \
|
||||
::mozilla::afl_interface_stream(testFile.c_str(), testFunc); \
|
||||
# define MOZ_AFL_INTERFACE_STREAM(initFunc, testFunc, moduleName) \
|
||||
static int afl_fuzz_inner_##moduleName(const uint8_t* data, size_t size) { \
|
||||
if (size > INT32_MAX) return 0; \
|
||||
nsCOMPtr<nsIInputStream> stream; \
|
||||
nsresult rv = NS_NewByteInputStream(getter_AddRefs(stream), \
|
||||
Span((const char*)data, size), \
|
||||
NS_ASSIGNMENT_DEPEND); \
|
||||
MOZ_RELEASE_ASSERT(NS_SUCCEEDED(rv)); \
|
||||
return testFunc(stream.forget()); \
|
||||
} \
|
||||
static int afl_fuzz_##moduleName(const uint8_t* data, size_t size) { \
|
||||
return afl_interface_raw(afl_fuzz_inner_##moduleName); \
|
||||
} \
|
||||
static void __attribute__((constructor)) AFLRegister##moduleName() { \
|
||||
::mozilla::FuzzerRegistry::getInstance().registerModule( \
|
||||
#moduleName, initFunc, afl_fuzz_##moduleName); \
|
||||
}
|
||||
#else
|
||||
# define MOZ_AFL_INTERFACE_STREAM(initFunc, testFunc, moduleName) /* Nothing \
|
||||
|
@ -85,6 +78,4 @@ void afl_interface_stream(const char* testFile, FuzzingTestFuncStream testFunc);
|
|||
MOZ_LIBFUZZER_INTERFACE_STREAM(initFunc, testFunc, moduleName); \
|
||||
MOZ_AFL_INTERFACE_STREAM(initFunc, testFunc, moduleName);
|
||||
|
||||
} // namespace mozilla
|
||||
|
||||
#endif // FuzzingInterfaceStream_h__
|
||||
|
|
|
@ -21,10 +21,6 @@ else:
|
|||
"FuzzingInterfaceStream.h",
|
||||
]
|
||||
|
||||
SOURCES += [
|
||||
"FuzzingInterfaceStream.cpp",
|
||||
]
|
||||
|
||||
DIRS += [
|
||||
"harness",
|
||||
]
|
||||
|
|
Загрузка…
Ссылка в новой задаче