summaryrefslogtreecommitdiff
path: root/gnu/llvm/clang/tools/clang-fuzzer
diff options
context:
space:
mode:
authorRobert Nagy <robert@cvs.openbsd.org>2023-11-11 18:17:06 +0000
committerRobert Nagy <robert@cvs.openbsd.org>2023-11-11 18:17:06 +0000
commita388acc7d111eece16e7c46f357872ec47588443 (patch)
treea636add3cb3f4afb8c45bb8302545f79f9e37d37 /gnu/llvm/clang/tools/clang-fuzzer
parent77976eff798a4c323c3194ff91190574c44d047d (diff)
import of clang from LLVM-16.0.6
Diffstat (limited to 'gnu/llvm/clang/tools/clang-fuzzer')
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/CMakeLists.txt3
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/dictionary/CMakeLists.txt4
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/dictionary/dictionary.c57
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/fuzzer-initialize/fuzzer_initialize.cpp2
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/handle-cxx/CMakeLists.txt2
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/CMakeLists.txt3
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/handle_llvm.cpp106
-rw-r--r--gnu/llvm/clang/tools/clang-fuzzer/proto-to-cxx/CMakeLists.txt2
8 files changed, 125 insertions, 54 deletions
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/CMakeLists.txt b/gnu/llvm/clang/tools/clang-fuzzer/CMakeLists.txt
index 4b2243c5ceb..e68ed8bbcb0 100644
--- a/gnu/llvm/clang/tools/clang-fuzzer/CMakeLists.txt
+++ b/gnu/llvm/clang/tools/clang-fuzzer/CMakeLists.txt
@@ -1,4 +1,4 @@
-set(LLVM_LINK_COMPONENTS ${LLVM_TARGETS_TO_BUILD} FuzzMutate)
+set(LLVM_LINK_COMPONENTS ${LLVM_TARGETS_TO_BUILD} FuzzerCLI)
set(CXX_FLAGS_NOFUZZ ${CMAKE_CXX_FLAGS})
set(DUMMY_MAIN DummyClangFuzzer.cpp)
if(LLVM_LIB_FUZZING_ENGINE)
@@ -109,6 +109,7 @@ endif()
add_clang_subdirectory(handle-cxx)
add_clang_subdirectory(handle-llvm)
+add_clang_subdirectory(dictionary)
add_clang_executable(clang-fuzzer
EXCLUDE_FROM_ALL
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/dictionary/CMakeLists.txt b/gnu/llvm/clang/tools/clang-fuzzer/dictionary/CMakeLists.txt
new file mode 100644
index 00000000000..ee4aa587ea5
--- /dev/null
+++ b/gnu/llvm/clang/tools/clang-fuzzer/dictionary/CMakeLists.txt
@@ -0,0 +1,4 @@
+add_clang_executable(clang-fuzzer-dictionary
+ dictionary.c
+ )
+
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/dictionary/dictionary.c b/gnu/llvm/clang/tools/clang-fuzzer/dictionary/dictionary.c
new file mode 100644
index 00000000000..90490477f70
--- /dev/null
+++ b/gnu/llvm/clang/tools/clang-fuzzer/dictionary/dictionary.c
@@ -0,0 +1,57 @@
+//===-- dictionary.c - Generate fuzzing dictionary for clang --------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+//
+// This binary emits a fuzzing dictionary describing strings that are
+// significant to the clang parser: keywords and other tokens.
+//
+// The dictionary can be used by a fuzzer to reach interesting parser states
+// much more quickly.
+//
+// The output is a single-file dictionary supported by libFuzzer and AFL:
+// https://llvm.org/docs/LibFuzzer.html#dictionaries
+//
+//===----------------------------------------------------------------------===//
+
+#include <stdio.h>
+
+static void emit(const char *Name, const char *Spelling) {
+ static char Hex[] = "0123456789abcdef";
+
+ printf("%s=\"", Name);
+ unsigned char C;
+ while ((C = *Spelling++)) {
+ if (C < 32 || C == '"' || C == '\\')
+ printf("\\x%c%c", Hex[C>>4], Hex[C%16]);
+ else
+ printf("%c", C);
+ }
+ printf("\"\n");
+}
+
+int main(int argc, char **argv) {
+#define PUNCTUATOR(Name, Spelling) emit(#Name, Spelling);
+#define KEYWORD(Name, Criteria) emit(#Name, #Name);
+#define PPKEYWORD(Name) emit(#Name, #Name);
+#define CXX_KEYWORD_OPERATOR(Name, Equivalent) emit(#Name, #Name);
+#define OBJC_AT_KEYWORD(Name) emit(#Name, #Name);
+#define ALIAS(Spelling, Equivalent, Criteria) emit(Spelling, Spelling);
+#include "clang/Basic/TokenKinds.def"
+ // Some other sub-token chunks significant to the lexer.
+ emit("ucn16", "\\u0000");
+ emit("ucn32", "\\U00000000");
+ emit("rawstart", "R\"(");
+ emit("rawend", ")\"");
+ emit("quote", "\"");
+ emit("squote", "'");
+ emit("u8quote", "u8\"");
+ emit("u16quote", "u\"");
+ emit("u32quote", "U\"");
+ emit("esc_nl", "\\\n");
+ emit("hex", "0x");
+}
+
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/fuzzer-initialize/fuzzer_initialize.cpp b/gnu/llvm/clang/tools/clang-fuzzer/fuzzer-initialize/fuzzer_initialize.cpp
index 20cf98896e2..94f3b937d83 100644
--- a/gnu/llvm/clang/tools/clang-fuzzer/fuzzer-initialize/fuzzer_initialize.cpp
+++ b/gnu/llvm/clang/tools/clang-fuzzer/fuzzer-initialize/fuzzer_initialize.cpp
@@ -48,8 +48,6 @@ extern "C" int LLVMFuzzerInitialize(int *argc, char ***argv) {
initializeAnalysis(Registry);
initializeTransformUtils(Registry);
initializeInstCombine(Registry);
- initializeAggressiveInstCombine(Registry);
- initializeInstrumentation(Registry);
initializeTarget(Registry);
CLArgs.push_back("-O2");
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/handle-cxx/CMakeLists.txt b/gnu/llvm/clang/tools/clang-fuzzer/handle-cxx/CMakeLists.txt
index 6d62421d9a6..184d467b9c3 100644
--- a/gnu/llvm/clang/tools/clang-fuzzer/handle-cxx/CMakeLists.txt
+++ b/gnu/llvm/clang/tools/clang-fuzzer/handle-cxx/CMakeLists.txt
@@ -11,3 +11,5 @@ add_clang_library(clangHandleCXX
clangSerialization
clangTooling
)
+
+target_include_directories(clangHandleCXX PRIVATE .)
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/CMakeLists.txt b/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/CMakeLists.txt
index 9ceb1d33182..9962f9850f5 100644
--- a/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/CMakeLists.txt
+++ b/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/CMakeLists.txt
@@ -4,14 +4,17 @@ set(LLVM_LINK_COMPONENTS
Core
ExecutionEngine
IPO
+ IRPrinter
IRReader
MC
MCJIT
Object
+ Passes
RuntimeDyld
SelectionDAG
Support
Target
+ TargetParser
TransformUtils
native
)
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/handle_llvm.cpp b/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/handle_llvm.cpp
index 4adb6eb39d0..06df39dcdc4 100644
--- a/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/handle_llvm.cpp
+++ b/gnu/llvm/clang/tools/clang-fuzzer/handle-llvm/handle_llvm.cpp
@@ -30,47 +30,39 @@
#include "llvm/ExecutionEngine/SectionMemoryManager.h"
#include "llvm/IR/IRPrintingPasses.h"
#include "llvm/IR/LLVMContext.h"
-#include "llvm/IR/LegacyPassManager.h"
-#include "llvm/IR/LegacyPassNameParser.h"
#include "llvm/IR/Module.h"
#include "llvm/IR/Verifier.h"
+#include "llvm/IRPrinter/IRPrintingPasses.h"
#include "llvm/IRReader/IRReader.h"
-#include "llvm/Pass.h"
-#include "llvm/PassRegistry.h"
+#include "llvm/MC/TargetRegistry.h"
+#include "llvm/Passes/OptimizationLevel.h"
+#include "llvm/Passes/PassBuilder.h"
#include "llvm/Support/MemoryBuffer.h"
#include "llvm/Support/SourceMgr.h"
-#include "llvm/Support/TargetRegistry.h"
#include "llvm/Support/TargetSelect.h"
#include "llvm/Target/TargetMachine.h"
-#include "llvm/Transforms/IPO.h"
-#include "llvm/Transforms/IPO/PassManagerBuilder.h"
-#include "llvm/Transforms/Vectorize.h"
using namespace llvm;
-static codegen::RegisterCodeGenFlags CGF;
-
// Define a type for the functions that are compiled and executed
typedef void (*LLVMFunc)(int*, int*, int*, int);
// Helper function to parse command line args and find the optimization level
-static void getOptLevel(const std::vector<const char *> &ExtraArgs,
- CodeGenOpt::Level &OLvl) {
+static CodeGenOpt::Level
+getOptLevel(const std::vector<const char *> &ExtraArgs) {
// Find the optimization level from the command line args
- OLvl = CodeGenOpt::Default;
+ CodeGenOpt::Level OLvl = CodeGenOpt::Default;
for (auto &A : ExtraArgs) {
if (A[0] == '-' && A[1] == 'O') {
- switch(A[2]) {
- case '0': OLvl = CodeGenOpt::None; break;
- case '1': OLvl = CodeGenOpt::Less; break;
- case '2': OLvl = CodeGenOpt::Default; break;
- case '3': OLvl = CodeGenOpt::Aggressive; break;
- default:
- errs() << "error: opt level must be between 0 and 3.\n";
- std::exit(1);
+ if (auto Level = CodeGenOpt::parseLevel(A[2])) {
+ OLvl = *Level;
+ } else {
+ errs() << "error: opt level must be between 0 and 3.\n";
+ std::exit(1);
}
}
}
+ return OLvl;
}
static void ErrorAndExit(std::string message) {
@@ -80,16 +72,45 @@ static void ErrorAndExit(std::string message) {
// Helper function to add optimization passes to the TargetMachine at the
// specified optimization level, OptLevel
-static void AddOptimizationPasses(legacy::PassManagerBase &MPM,
- CodeGenOpt::Level OptLevel,
- unsigned SizeLevel) {
- // Create and initialize a PassManagerBuilder
- PassManagerBuilder Builder;
- Builder.OptLevel = OptLevel;
- Builder.SizeLevel = SizeLevel;
- Builder.Inliner = createFunctionInliningPass(OptLevel, SizeLevel, false);
- Builder.LoopVectorize = true;
- Builder.populateModulePassManager(MPM);
+static void RunOptimizationPasses(raw_ostream &OS, Module &M,
+ CodeGenOpt::Level OptLevel) {
+ llvm::OptimizationLevel OL;
+ switch (OptLevel) {
+ case CodeGenOpt::None:
+ OL = OptimizationLevel::O0;
+ break;
+ case CodeGenOpt::Less:
+ OL = OptimizationLevel::O1;
+ break;
+ case CodeGenOpt::Default:
+ OL = OptimizationLevel::O2;
+ break;
+ case CodeGenOpt::Aggressive:
+ OL = OptimizationLevel::O3;
+ break;
+ }
+
+ LoopAnalysisManager LAM;
+ FunctionAnalysisManager FAM;
+ CGSCCAnalysisManager CGAM;
+ ModuleAnalysisManager MAM;
+
+ PassBuilder PB;
+
+ PB.registerModuleAnalyses(MAM);
+ PB.registerCGSCCAnalyses(CGAM);
+ PB.registerFunctionAnalyses(FAM);
+ PB.registerLoopAnalyses(LAM);
+ PB.crossRegisterProxies(LAM, FAM, CGAM, MAM);
+
+ ModulePassManager MPM;
+ if (OL == OptimizationLevel::O0)
+ MPM = PB.buildO0DefaultPipeline(OL);
+ else
+ MPM = PB.buildPerModuleDefaultPipeline(OL);
+ MPM.addPass(PrintModulePass(OS));
+
+ MPM.run(M, MAM);
}
// Mimics the opt tool to run an optimization pass over the provided IR
@@ -120,26 +141,12 @@ static std::string OptLLVM(const std::string &IR, CodeGenOpt::Level OLvl) {
codegen::setFunctionAttributes(codegen::getCPUStr(),
codegen::getFeaturesStr(), *M);
- legacy::PassManager Passes;
-
- Passes.add(new TargetLibraryInfoWrapperPass(ModuleTriple));
- Passes.add(createTargetTransformInfoWrapperPass(TM->getTargetIRAnalysis()));
-
- LLVMTargetMachine &LTM = static_cast<LLVMTargetMachine &>(*TM);
- Passes.add(LTM.createPassConfig(Passes));
-
- Passes.add(createVerifierPass());
-
- AddOptimizationPasses(Passes, OLvl, 0);
-
// Add a pass that writes the optimized IR to an output stream
std::string outString;
raw_string_ostream OS(outString);
- Passes.add(createPrintModulePass(OS, "", false));
-
- Passes.run(*M);
+ RunOptimizationPasses(OS, *M, OLvl);
- return OS.str();
+ return outString;
}
// Takes a function and runs it on a set of inputs
@@ -216,8 +223,7 @@ void clang_fuzzer::HandleLLVM(const std::string &IR,
memcpy(UnoptArrays, InputArrays, kTotalSize);
// Parse ExtraArgs to set the optimization level
- CodeGenOpt::Level OLvl;
- getOptLevel(ExtraArgs, OLvl);
+ CodeGenOpt::Level OLvl = getOptLevel(ExtraArgs);
// First we optimize the IR by running a loop vectorizer pass
std::string OptIR = OptLLVM(IR, OLvl);
@@ -227,6 +233,4 @@ void clang_fuzzer::HandleLLVM(const std::string &IR,
if (memcmp(OptArrays, UnoptArrays, kTotalSize))
ErrorAndExit("!!!BUG!!!");
-
- return;
}
diff --git a/gnu/llvm/clang/tools/clang-fuzzer/proto-to-cxx/CMakeLists.txt b/gnu/llvm/clang/tools/clang-fuzzer/proto-to-cxx/CMakeLists.txt
index 339959b81af..baefc8a3014 100644
--- a/gnu/llvm/clang/tools/clang-fuzzer/proto-to-cxx/CMakeLists.txt
+++ b/gnu/llvm/clang/tools/clang-fuzzer/proto-to-cxx/CMakeLists.txt
@@ -14,6 +14,8 @@ add_clang_library(clangLoopProtoToCXX loop_proto_to_cxx.cpp
DEPENDS clangCXXLoopProto
LINK_LIBS clangCXXLoopProto ${PROTOBUF_LIBRARIES}
)
+target_include_directories(clangProtoToCXX PRIVATE .)
+target_include_directories(clangLoopProtoToCXX PRIVATE .)
add_clang_executable(clang-proto-to-cxx proto_to_cxx_main.cpp)
add_clang_executable(clang-loop-proto-to-cxx loop_proto_to_cxx_main.cpp)