LCOV - code coverage report
Current view: top level - lib/FuzzMutate - FuzzerCLI.cpp (source / functions) Hit Total Coverage
Test: llvm-toolchain.info Lines: 38 95 40.0 %
Date: 2018-02-25 19:55:18 Functions: 6 7 85.7 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : //===-- FuzzerCLI.cpp -----------------------------------------------------===//
       2             : //
       3             : //                     The LLVM Compiler Infrastructure
       4             : //
       5             : // This file is distributed under the University of Illinois Open Source
       6             : // License. See LICENSE.TXT for details.
       7             : //
       8             : //===----------------------------------------------------------------------===//
       9             : 
      10             : #include "llvm/FuzzMutate/FuzzerCLI.h"
      11             : #include "llvm/ADT/Triple.h"
      12             : #include "llvm/Bitcode/BitcodeReader.h"
      13             : #include "llvm/Bitcode/BitcodeWriter.h"
      14             : #include "llvm/IR/LLVMContext.h"
      15             : #include "llvm/Support/CommandLine.h"
      16             : #include "llvm/Support/Compiler.h"
      17             : #include "llvm/Support/Error.h"
      18             : #include "llvm/Support/MemoryBuffer.h"
      19             : #include "llvm/Support/SourceMgr.h"
      20             : #include "llvm/Support/raw_ostream.h"
      21             : #include "llvm/IR/Verifier.h"
      22             : 
      23             : using namespace llvm;
      24             : 
      25          11 : void llvm::parseFuzzerCLOpts(int ArgC, char *ArgV[]) {
      26             :   std::vector<const char *> CLArgs;
      27          22 :   CLArgs.push_back(ArgV[0]);
      28             : 
      29             :   int I = 1;
      30          22 :   while (I < ArgC)
      31          20 :     if (StringRef(ArgV[I++]).equals("-ignore_remaining_args=1"))
      32             :       break;
      33          63 :   while (I < ArgC)
      34          52 :     CLArgs.push_back(ArgV[I++]);
      35             : 
      36          22 :   cl::ParseCommandLineOptions(CLArgs.size(), CLArgs.data());
      37          11 : }
      38             : 
      39           5 : void llvm::handleExecNameEncodedBEOpts(StringRef ExecName) {
      40           5 :   std::vector<std::string> Args{ExecName};
      41             : 
      42           5 :   auto NameAndArgs = ExecName.split("--");
      43           5 :   if (NameAndArgs.second.empty())
      44           5 :     return;
      45             : 
      46             :   SmallVector<StringRef, 4> Opts;
      47           0 :   NameAndArgs.second.split(Opts, '-');
      48           0 :   for (StringRef Opt : Opts) {
      49             :     if (Opt.equals("gisel")) {
      50           0 :       Args.push_back("-global-isel");
      51             :       // For now we default GlobalISel to -O0
      52           0 :       Args.push_back("-O0");
      53             :     } else if (Opt.startswith("O")) {
      54           0 :       Args.push_back("-" + Opt.str());
      55           0 :     } else if (Triple(Opt).getArch()) {
      56           0 :       Args.push_back("-mtriple=" + Opt.str());
      57             :     } else {
      58           0 :       errs() << ExecName << ": Unknown option: " << Opt << ".\n";
      59           0 :       exit(1);
      60             :     }
      61             :   }
      62           0 :   errs() << NameAndArgs.first << ": Injected args:";
      63           0 :   for (int I = 1, E = Args.size(); I < E; ++I)
      64           0 :     errs() << " " << Args[I];
      65           0 :   errs() << "\n";
      66             : 
      67             :   std::vector<const char *> CLArgs;
      68           0 :   CLArgs.reserve(Args.size());
      69           0 :   for (std::string &S : Args)
      70           0 :     CLArgs.push_back(S.c_str());
      71             : 
      72           0 :   cl::ParseCommandLineOptions(CLArgs.size(), CLArgs.data());
      73             : }
      74             : 
      75           6 : void llvm::handleExecNameEncodedOptimizerOpts(StringRef ExecName) {
      76             :   // TODO: Refactor parts common with the 'handleExecNameEncodedBEOpts'
      77           6 :   std::vector<std::string> Args{ExecName};
      78             : 
      79           6 :   auto NameAndArgs = ExecName.split("--");
      80           6 :   if (NameAndArgs.second.empty())
      81           6 :     return;
      82             : 
      83             :   SmallVector<StringRef, 4> Opts;
      84           0 :   NameAndArgs.second.split(Opts, '-');
      85           0 :   for (StringRef Opt : Opts) {
      86             :     if (Opt == "instcombine") {
      87           0 :       Args.push_back("-passes=instcombine");
      88             :     } else if (Opt == "earlycse") {
      89           0 :       Args.push_back("-passes=early-cse");
      90             :     } else if (Opt == "simplifycfg") {
      91           0 :       Args.push_back("-passes=simplify-cfg");
      92             :     } else if (Opt == "gvn") {
      93           0 :       Args.push_back("-passes=gvn");
      94             :     } else if (Opt == "sccp") {
      95           0 :       Args.push_back("-passes=sccp");
      96             :     
      97             :     } else if (Opt == "loop_predication") {
      98           0 :       Args.push_back("-passes=loop-predication");
      99             :     } else if (Opt == "guard_widening") {
     100           0 :       Args.push_back("-passes=guard-widening");
     101             :     } else if (Opt == "loop_rotate") {
     102           0 :       Args.push_back("-passes=loop(rotate)");
     103             :     } else if (Opt == "loop_unswitch") {
     104           0 :       Args.push_back("-passes=loop(unswitch)");
     105             :     } else if (Opt == "loop_unroll") {
     106           0 :       Args.push_back("-passes=unroll");
     107             :     } else if (Opt == "loop_vectorize") {
     108           0 :       Args.push_back("-passes=loop-vectorize");
     109             :     } else if (Opt == "licm") {
     110           0 :       Args.push_back("-passes=licm");
     111             :     } else if (Opt == "indvars") {
     112           0 :       Args.push_back("-passes=indvars");
     113             :     } else if (Opt == "strength_reduce") {
     114           0 :       Args.push_back("-passes=strength-reduce");
     115             :       
     116           0 :     } else if (Triple(Opt).getArch()) {
     117           0 :       Args.push_back("-mtriple=" + Opt.str());
     118             :     } else {
     119           0 :       errs() << ExecName << ": Unknown option: " << Opt << ".\n";
     120           0 :       exit(1);
     121             :     }
     122             :   }
     123             : 
     124           0 :   errs() << NameAndArgs.first << ": Injected args:";
     125           0 :   for (int I = 1, E = Args.size(); I < E; ++I)
     126           0 :     errs() << " " << Args[I];
     127           0 :   errs() << "\n";
     128             : 
     129             :   std::vector<const char *> CLArgs;
     130           0 :   CLArgs.reserve(Args.size());
     131           0 :   for (std::string &S : Args)
     132           0 :     CLArgs.push_back(S.c_str());
     133             : 
     134           0 :   cl::ParseCommandLineOptions(CLArgs.size(), CLArgs.data());
     135             : }
     136             : 
     137          11 : int llvm::runFuzzerOnInputs(int ArgC, char *ArgV[], FuzzerTestFun TestOne,
     138             :                             FuzzerInitFun Init) {
     139          11 :   errs() << "*** This tool was not linked to libFuzzer.\n"
     140          11 :          << "*** No fuzzing will be performed.\n";
     141          11 :   if (int RC = Init(&ArgC, &ArgV)) {
     142           0 :     errs() << "Initialization failed\n";
     143           0 :     return RC;
     144             :   }
     145             : 
     146          21 :   for (int I = 1; I < ArgC; ++I) {
     147          14 :     StringRef Arg(ArgV[I]);
     148           0 :     if (Arg.startswith("-")) {
     149             :       if (Arg.equals("-ignore_remaining_args=1"))
     150             :         break;
     151           0 :       continue;
     152             :     }
     153             : 
     154             :     auto BufOrErr = MemoryBuffer::getFile(Arg, /*FileSize-*/ -1,
     155           7 :                                           /*RequiresNullTerminator=*/false);
     156           7 :     if (std::error_code EC = BufOrErr.getError()) {
     157           0 :       errs() << "Error reading file: " << Arg << ": " << EC.message() << "\n";
     158             :       return 1;
     159             :     }
     160             :     std::unique_ptr<MemoryBuffer> Buf = std::move(BufOrErr.get());
     161          14 :     errs() << "Running: " << Arg << " (" << Buf->getBufferSize() << " bytes)\n";
     162          14 :     TestOne(reinterpret_cast<const uint8_t *>(Buf->getBufferStart()),
     163             :             Buf->getBufferSize());
     164             :   }
     165             :   return 0;
     166             : }
     167             : 
     168           5 : std::unique_ptr<Module> llvm::parseModule(
     169             :     const uint8_t *Data, size_t Size, LLVMContext &Context) {
     170             : 
     171           5 :   if (Size <= 1)
     172             :     // We get bogus data given an empty corpus - just create a new module.
     173           0 :     return llvm::make_unique<Module>("M", Context);
     174             : 
     175             :   auto Buffer = MemoryBuffer::getMemBuffer(
     176             :       StringRef(reinterpret_cast<const char *>(Data), Size), "Fuzzer input",
     177           5 :       /*RequiresNullTerminator=*/false);
     178             : 
     179           5 :   SMDiagnostic Err;
     180          10 :   auto M = parseBitcodeFile(Buffer->getMemBufferRef(), Context);
     181           5 :   if (Error E = M.takeError()) {
     182           5 :     errs() << toString(std::move(E)) << "\n";
     183             :     return nullptr;
     184             :   }
     185             :   return std::move(M.get());
     186             : }
     187             : 
     188           0 : size_t llvm::writeModule(const Module &M, uint8_t *Dest, size_t MaxSize) {
     189             :   std::string Buf;
     190             :   {
     191           0 :     raw_string_ostream OS(Buf);
     192           0 :     WriteBitcodeToFile(M, OS);
     193             :   }
     194           0 :   if (Buf.size() > MaxSize)
     195             :       return 0;
     196           0 :   memcpy(Dest, Buf.data(), Buf.size());
     197           0 :   return Buf.size();
     198             : }
     199             : 
     200           5 : std::unique_ptr<Module> llvm::parseAndVerify(const uint8_t *Data, size_t Size,
     201             :                                              LLVMContext &Context) {
     202          10 :   auto M = parseModule(Data, Size, Context);
     203           9 :   if (!M || verifyModule(*M, &errs()))
     204             :     return nullptr;
     205             :   
     206             :   return M;
     207             : }

Generated by: LCOV version 1.13