mirror of
https://github.com/AFLplusplus/AFLplusplus.git
synced 2025-06-14 19:08:08 +00:00
fix libfuzzer custom mutator and add introspection function
This commit is contained in:
@ -83,6 +83,8 @@ void WriteToFile(const std::string &Data, const std::string &Path) {
|
|||||||
|
|
||||||
void WriteToFile(const uint8_t *Data, size_t Size, const std::string &Path) {
|
void WriteToFile(const uint8_t *Data, size_t Size, const std::string &Path) {
|
||||||
|
|
||||||
|
return;
|
||||||
|
|
||||||
// Use raw C interface because this function may be called from a sig handler.
|
// Use raw C interface because this function may be called from a sig handler.
|
||||||
FILE *Out = fopen(Path.c_str(), "wb");
|
FILE *Out = fopen(Path.c_str(), "wb");
|
||||||
if (!Out) return;
|
if (!Out) return;
|
||||||
@ -93,6 +95,8 @@ void WriteToFile(const uint8_t *Data, size_t Size, const std::string &Path) {
|
|||||||
|
|
||||||
void AppendToFile(const std::string &Data, const std::string &Path) {
|
void AppendToFile(const std::string &Data, const std::string &Path) {
|
||||||
|
|
||||||
|
return;
|
||||||
|
|
||||||
AppendToFile(reinterpret_cast<const uint8_t *>(Data.data()), Data.size(),
|
AppendToFile(reinterpret_cast<const uint8_t *>(Data.data()), Data.size(),
|
||||||
Path);
|
Path);
|
||||||
|
|
||||||
@ -100,6 +104,8 @@ void AppendToFile(const std::string &Data, const std::string &Path) {
|
|||||||
|
|
||||||
void AppendToFile(const uint8_t *Data, size_t Size, const std::string &Path) {
|
void AppendToFile(const uint8_t *Data, size_t Size, const std::string &Path) {
|
||||||
|
|
||||||
|
return;
|
||||||
|
|
||||||
FILE *Out = fopen(Path.c_str(), "a");
|
FILE *Out = fopen(Path.c_str(), "a");
|
||||||
if (!Out) return;
|
if (!Out) return;
|
||||||
fwrite(Data, sizeof(Data[0]), Size, Out);
|
fwrite(Data, sizeof(Data[0]), Size, Out);
|
||||||
@ -182,6 +188,7 @@ void Printf(const char *Fmt, ...) {
|
|||||||
|
|
||||||
void VPrintf(bool Verbose, const char *Fmt, ...) {
|
void VPrintf(bool Verbose, const char *Fmt, ...) {
|
||||||
|
|
||||||
|
return;
|
||||||
if (!Verbose) return;
|
if (!Verbose) return;
|
||||||
va_list ap;
|
va_list ap;
|
||||||
va_start(ap, Fmt);
|
va_start(ap, Fmt);
|
||||||
|
@ -206,6 +206,8 @@ void Fuzzer::StaticDeathCallback() {
|
|||||||
|
|
||||||
void Fuzzer::DumpCurrentUnit(const char *Prefix) {
|
void Fuzzer::DumpCurrentUnit(const char *Prefix) {
|
||||||
|
|
||||||
|
return;
|
||||||
|
|
||||||
if (!CurrentUnitData) return; // Happens when running individual inputs.
|
if (!CurrentUnitData) return; // Happens when running individual inputs.
|
||||||
ScopedDisableMsanInterceptorChecks S;
|
ScopedDisableMsanInterceptorChecks S;
|
||||||
MD.PrintMutationSequence();
|
MD.PrintMutationSequence();
|
||||||
@ -733,6 +735,7 @@ std::string Fuzzer::WriteToOutputCorpus(const Unit &U) {
|
|||||||
|
|
||||||
void Fuzzer::WriteUnitToFileWithPrefix(const Unit &U, const char *Prefix) {
|
void Fuzzer::WriteUnitToFileWithPrefix(const Unit &U, const char *Prefix) {
|
||||||
|
|
||||||
|
return;
|
||||||
if (!Options.SaveArtifacts) return;
|
if (!Options.SaveArtifacts) return;
|
||||||
std::string Path = Options.ArtifactPrefix + Prefix + Hash(U);
|
std::string Path = Options.ArtifactPrefix + Prefix + Hash(U);
|
||||||
if (!Options.ExactArtifactPath.empty())
|
if (!Options.ExactArtifactPath.empty())
|
||||||
@ -1073,13 +1076,21 @@ void Fuzzer::MinimizeCrashLoop(const Unit &U) {
|
|||||||
|
|
||||||
} // namespace fuzzer
|
} // namespace fuzzer
|
||||||
|
|
||||||
|
#ifdef INTROSPECTION
|
||||||
|
extern const char *introspection_ptr;
|
||||||
|
#endif
|
||||||
|
|
||||||
extern "C" {
|
extern "C" {
|
||||||
|
|
||||||
ATTRIBUTE_INTERFACE size_t LLVMFuzzerMutate(uint8_t *Data, size_t Size,
|
ATTRIBUTE_INTERFACE size_t LLVMFuzzerMutate(uint8_t *Data, size_t Size,
|
||||||
size_t MaxSize) {
|
size_t MaxSize) {
|
||||||
|
|
||||||
assert(fuzzer::F);
|
assert(fuzzer::F);
|
||||||
return fuzzer::F->GetMD().DefaultMutate(Data, Size, MaxSize);
|
size_t r = fuzzer::F->GetMD().DefaultMutate(Data, Size, MaxSize);
|
||||||
|
#ifdef INTROSPECTION
|
||||||
|
introspection_ptr = fuzzer::F->GetMD().WriteMutationSequence();
|
||||||
|
#endif
|
||||||
|
return r;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -14,6 +14,8 @@
|
|||||||
#include "FuzzerMutate.h"
|
#include "FuzzerMutate.h"
|
||||||
#include "FuzzerOptions.h"
|
#include "FuzzerOptions.h"
|
||||||
#include "FuzzerTracePC.h"
|
#include "FuzzerTracePC.h"
|
||||||
|
#include <random>
|
||||||
|
#include <chrono>
|
||||||
|
|
||||||
namespace fuzzer {
|
namespace fuzzer {
|
||||||
|
|
||||||
@ -100,15 +102,17 @@ size_t MutationDispatcher::Mutate_CustomCrossOver(uint8_t *Data, size_t Size,
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
size_t MutationDispatcher::Mutate_ShuffleBytes(uint8_t *Data, size_t Size,
|
size_t MutationDispatcher::Mutate_ShuffleBytes(uint8_t *Data, size_t Size,
|
||||||
size_t MaxSize) {
|
size_t MaxSize) {
|
||||||
|
|
||||||
if (Size > MaxSize || Size == 0) return 0;
|
if (Size > MaxSize || Size == 0) return 0;
|
||||||
size_t ShuffleAmount =
|
size_t ShuffleAmount =
|
||||||
Rand(std::min(Size, (size_t)8)) + 1; // [1,8] and <= Size.
|
Rand(std::min(Size, (size_t)8)) + 1; // [1,8] and <= Size.
|
||||||
size_t ShuffleStart = Rand(Size - ShuffleAmount);
|
size_t ShuffleStart = Rand(Size - ShuffleAmount);
|
||||||
assert(ShuffleStart + ShuffleAmount <= Size);
|
assert(ShuffleStart + ShuffleAmount <= Size);
|
||||||
std::shuffle(Data + ShuffleStart, Data + ShuffleStart + ShuffleAmount, Rand);
|
unsigned num = std::chrono::system_clock::now().time_since_epoch().count();
|
||||||
|
std::shuffle(Data + ShuffleStart, Data + ShuffleStart + ShuffleAmount, std::default_random_engine(num));
|
||||||
|
//std::shuffle(Data + ShuffleStart, Data + ShuffleStart + ShuffleAmount, Rand);
|
||||||
return Size;
|
return Size;
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -609,8 +613,24 @@ void MutationDispatcher::PrintRecommendedDictionary() {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const char *MutationDispatcher::WriteMutationSequence() {
|
||||||
|
|
||||||
|
static std::string buf;
|
||||||
|
buf = "";
|
||||||
|
|
||||||
|
for (size_t i = 0; i < CurrentMutatorSequence.size(); i++) {
|
||||||
|
|
||||||
|
buf = buf + " " + CurrentMutatorSequence[i].Name;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
return buf.c_str();
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
void MutationDispatcher::PrintMutationSequence(bool Verbose) {
|
void MutationDispatcher::PrintMutationSequence(bool Verbose) {
|
||||||
|
|
||||||
|
return;
|
||||||
Printf("MS: %zd ", CurrentMutatorSequence.size());
|
Printf("MS: %zd ", CurrentMutatorSequence.size());
|
||||||
size_t EntriesToPrint =
|
size_t EntriesToPrint =
|
||||||
Verbose ? CurrentMutatorSequence.size()
|
Verbose ? CurrentMutatorSequence.size()
|
||||||
|
@ -26,6 +26,7 @@ public:
|
|||||||
void StartMutationSequence();
|
void StartMutationSequence();
|
||||||
/// Print the current sequence of mutations. Only prints the full sequence
|
/// Print the current sequence of mutations. Only prints the full sequence
|
||||||
/// when Verbose is true.
|
/// when Verbose is true.
|
||||||
|
const char *WriteMutationSequence();
|
||||||
void PrintMutationSequence(bool Verbose = true);
|
void PrintMutationSequence(bool Verbose = true);
|
||||||
/// Return the current sequence of mutations.
|
/// Return the current sequence of mutations.
|
||||||
std::string MutationSequence();
|
std::string MutationSequence();
|
||||||
|
@ -3,6 +3,11 @@ CFLAGS = -g -O3 -funroll-loops -fPIC -fpermissive -std=c++11
|
|||||||
#CFLAGS = -g -O0 -fPIC -fpermissive -std=c++11
|
#CFLAGS = -g -O0 -fPIC -fpermissive -std=c++11
|
||||||
CXX ?= clang++
|
CXX ?= clang++
|
||||||
|
|
||||||
|
ifdef INTROSPECTION
|
||||||
|
$(info Compiling with introspection documentation)
|
||||||
|
CFLAGS += -DINTROSPECTION=1
|
||||||
|
endif
|
||||||
|
|
||||||
all: libfuzzer-mutator.so
|
all: libfuzzer-mutator.so
|
||||||
|
|
||||||
FuzzerCrossOver.o: FuzzerCrossOver.cpp
|
FuzzerCrossOver.o: FuzzerCrossOver.cpp
|
||||||
|
@ -6,6 +6,10 @@
|
|||||||
//#include "debug.h"
|
//#include "debug.h"
|
||||||
#include "afl-fuzz.h"
|
#include "afl-fuzz.h"
|
||||||
|
|
||||||
|
#ifdef INTROSPECTION
|
||||||
|
const char *introspection_ptr;
|
||||||
|
#endif
|
||||||
|
|
||||||
afl_state_t *afl_struct;
|
afl_state_t *afl_struct;
|
||||||
|
|
||||||
extern "C" size_t LLVMFuzzerMutate(uint8_t *Data, size_t Size, size_t MaxSize);
|
extern "C" size_t LLVMFuzzerMutate(uint8_t *Data, size_t Size, size_t MaxSize);
|
||||||
@ -133,6 +137,14 @@ extern "C" size_t afl_custom_fuzz(my_mutator_t *data, uint8_t *buf,
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef INTROSPECTION
|
||||||
|
extern "C" const char* afl_custom_introspection(my_mutator_t *data) {
|
||||||
|
|
||||||
|
return introspection_ptr;
|
||||||
|
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Deinitialize everything
|
* Deinitialize everything
|
||||||
*
|
*
|
||||||
|
Reference in New Issue
Block a user