X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=tools%2Fbugpoint%2FBugDriver.h;h=3169d293da027de12b44737a56306857065a2440;hb=a617b53aa86aaf3a3d6d248c53da8f91f3491f44;hp=3de7b055f94c7d29e5651de766d36c53fd0dc23f;hpb=4e3be89cb5cde6e2df294c64db3bc28133b67594;p=oota-llvm.git diff --git a/tools/bugpoint/BugDriver.h b/tools/bugpoint/BugDriver.h index 3de7b055f94..3169d293da0 100644 --- a/tools/bugpoint/BugDriver.h +++ b/tools/bugpoint/BugDriver.h @@ -2,8 +2,8 @@ // // The LLVM Compiler Infrastructure // -// This file was developed by the LLVM research group and is distributed under -// the University of Illinois Open Source License. See LICENSE.TXT for details. +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. // //===----------------------------------------------------------------------===// // @@ -16,11 +16,14 @@ #ifndef BUGDRIVER_H #define BUGDRIVER_H -#include +#include "llvm/IR/ValueMap.h" +#include "llvm/Transforms/Utils/ValueMapper.h" #include +#include namespace llvm { +class Value; class PassInfo; class Module; class GlobalVariable; @@ -28,6 +31,7 @@ class Function; class BasicBlock; class AbstractInterpreter; class Instruction; +class LLVMContext; class DebugCrashes; @@ -40,37 +44,42 @@ extern bool DisableSimplifyCFG; extern bool BugpointIsInterrupted; class BugDriver { - const std::string ToolName; // Name of bugpoint + LLVMContext& Context; + const char *ToolName; // argv[0] of bugpoint std::string ReferenceOutputFile; // Name of `good' output file Module *Program; // The raw program, linked together - std::vector PassesToRun; + std::vector PassesToRun; AbstractInterpreter *Interpreter; // How to run the program - AbstractInterpreter *cbe; + AbstractInterpreter *SafeInterpreter; // To generate reference output, etc. GCC *gcc; - bool run_as_child; bool run_find_bugs; unsigned Timeout; + unsigned MemoryLimit; + bool UseValgrind; // FIXME: sort out public/private distinctions... friend class ReducePassList; friend class ReduceMisCodegenFunctions; public: - BugDriver(const char *toolname, bool as_child, bool find_bugs, - unsigned timeout); + BugDriver(const char *toolname, bool find_bugs, + unsigned timeout, unsigned memlimit, bool use_valgrind, + LLVMContext& ctxt); + ~BugDriver(); + + const char *getToolName() const { return ToolName; } - const std::string &getToolName() const { return ToolName; } + LLVMContext& getContext() const { return Context; } // Set up methods... these methods are used to copy information about the // command line arguments into instance variables of BugDriver. // bool addSources(const std::vector &FileNames); - template - void addPasses(It I, It E) { PassesToRun.insert(PassesToRun.end(), I, E); } - void setPassesToRun(const std::vector &PTR) { + void addPass(std::string p) { PassesToRun.push_back(p); } + void setPassesToRun(const std::vector &PTR) { PassesToRun = PTR; } - const std::vector &getPassesToRun() const { + const std::vector &getPassesToRun() const { return PassesToRun; } @@ -78,7 +87,7 @@ public: /// variables are set up from command line arguments. The \p as_child argument /// indicates whether the driver is to run in parent mode or child mode. /// - bool run(); + bool run(std::string &ErrMsg); /// debugOptimizerCrash - This method is called when some optimizer pass /// crashes on input. It attempts to prune down the testcase to something @@ -89,12 +98,12 @@ public: /// debugCodeGeneratorCrash - This method is called when the code generator /// crashes on an input. It attempts to reduce the input as much as possible /// while still causing the code generator to crash. - bool debugCodeGeneratorCrash(); + bool debugCodeGeneratorCrash(std::string &Error); /// debugMiscompilation - This method is used when the passes selected are not /// crashing, but the generated output is semantically different from the /// input. - bool debugMiscompilation(); + void debugMiscompilation(std::string *Error); /// debugPassMiscompilation - This method is called when the specified pass /// miscompiles Program as input. It tries to reduce the testcase to @@ -106,14 +115,15 @@ public: const std::string &ReferenceOutput); /// compileSharedObject - This method creates a SharedObject from a given - /// BytecodeFile for debugging a code generator. + /// BitcodeFile for debugging a code generator. /// - std::string compileSharedObject(const std::string &BytecodeFile); + std::string compileSharedObject(const std::string &BitcodeFile, + std::string &Error); /// debugCodeGenerator - This method narrows down a module to a function or /// set of functions, using the CBE as a ``safe'' code generator for other /// functions that are not under consideration. - bool debugCodeGenerator(); + bool debugCodeGenerator(std::string *Error); /// isExecutingJIT - Returns true if bugpoint is currently testing the JIT /// @@ -121,12 +131,8 @@ public: /// runPasses - Run all of the passes in the "PassesToRun" list, discard the /// output, and return true if any of the passes crashed. - bool runPasses(Module *M = 0) { - if (M == 0) M = Program; - std::swap(M, Program); - bool Result = runPasses(PassesToRun); - std::swap(M, Program); - return Result; + bool runPasses(Module *M) const { + return runPasses(M, PassesToRun); } Module *getProgram() const { return Program; } @@ -139,9 +145,9 @@ public: return OldProgram; } - AbstractInterpreter *switchToCBE() { + AbstractInterpreter *switchToSafeInterpreter() { AbstractInterpreter *Old = Interpreter; - Interpreter = (AbstractInterpreter*)cbe; + Interpreter = (AbstractInterpreter*)SafeInterpreter; return Old; } @@ -154,28 +160,30 @@ public: /// the specified one as the current program. void setNewProgram(Module *M); - /// compileProgram - Try to compile the specified module, throwing an - /// exception if an error occurs, or returning normally if not. This is used - /// for code generation crash testing. + /// compileProgram - Try to compile the specified module, returning false and + /// setting Error if an error occurs. This is used for code generation + /// crash testing. /// - void compileProgram(Module *M); + void compileProgram(Module *M, std::string *Error) const; /// executeProgram - This method runs "Program", capturing the output of the - /// program to a file, returning the filename of the file. A recommended - /// filename may be optionally specified. If there is a problem with the code - /// generator (e.g., llc crashes), this will throw an exception. + /// program to a file. A recommended filename may be optionally specified. /// - std::string executeProgram(std::string RequestedOutputFilename = "", - std::string Bytecode = "", - const std::string &SharedObjects = "", - AbstractInterpreter *AI = 0, - bool *ProgramExitedNonzero = 0); - - /// executeProgramWithCBE - Used to create reference output with the C + std::string executeProgram(const Module *Program, + std::string OutputFilename, + std::string Bitcode, + const std::string &SharedObjects, + AbstractInterpreter *AI, + std::string *Error) const; + + /// executeProgramSafely - Used to create reference output with the "safe" /// backend, if reference output is not provided. If there is a problem with - /// the code generator (e.g., llc crashes), this will throw an exception. + /// the code generator (e.g., llc crashes), this will return false and set + /// Error. /// - std::string executeProgramWithCBE(std::string OutputFile = ""); + std::string executeProgramSafely(const Module *Program, + std::string OutputFile, + std::string *Error) const; /// createReferenceFile - calls compileProgram and then records the output /// into ReferenceOutputFile. Returns true if reference file created, false @@ -183,29 +191,31 @@ public: /// this function. /// bool createReferenceFile(Module *M, const std::string &Filename - = "bugpoint.reference.out"); + = "bugpoint.reference.out-%%%%%%%"); /// diffProgram - This method executes the specified module and diffs the /// output against the file specified by ReferenceOutputFile. If the output - /// is different, true is returned. If there is a problem with the code - /// generator (e.g., llc crashes), this will throw an exception. + /// is different, 1 is returned. If there is a problem with the code + /// generator (e.g., llc crashes), this will return -1 and set Error. /// - bool diffProgram(const std::string &BytecodeFile = "", + bool diffProgram(const Module *Program, + const std::string &BitcodeFile = "", const std::string &SharedObj = "", - bool RemoveBytecode = false); - - /// EmitProgressBytecode - This function is used to output the current Program - /// to a file named "bugpoint-ID.bc". + bool RemoveBitcode = false, + std::string *Error = nullptr) const; + + /// EmitProgressBitcode - This function is used to output M to a file named + /// "bugpoint-ID.bc". /// - void EmitProgressBytecode(const std::string &ID, bool NoFlyer = false); + void EmitProgressBitcode(const Module *M, const std::string &ID, + bool NoFlyer = false) const; /// deleteInstructionFromProgram - This method clones the current Program and /// deletes the specified instruction from the cloned module. It then runs a /// series of cleanup passes (ADCE and SimplifyCFG) to eliminate any code /// which depends on the value. The modified module is then returned. /// - Module *deleteInstructionFromProgram(const Instruction *I, unsigned Simp) - const; + Module *deleteInstructionFromProgram(const Instruction *I, unsigned Simp); /// performFinalCleanups - This method clones the current Program and performs /// a series of cleanups intended to get rid of extra cruft on the module. If @@ -232,20 +242,24 @@ public: /// failure. If AutoDebugCrashes is set to true, then bugpoint will /// automatically attempt to track down a crashing pass if one exists, and /// this method will never return null. - Module *runPassesOn(Module *M, const std::vector &Passes, - bool AutoDebugCrashes = false); + Module *runPassesOn(Module *M, const std::vector &Passes, + bool AutoDebugCrashes = false, unsigned NumExtraArgs = 0, + const char * const *ExtraArgs = nullptr); - /// runPasses - Run the specified passes on Program, outputting a bytecode + /// runPasses - Run the specified passes on Program, outputting a bitcode /// file and writting the filename into OutputFile if successful. If the /// optimizations fail for some reason (optimizer crashes), return true, - /// otherwise return false. If DeleteOutput is set to true, the bytecode is + /// otherwise return false. If DeleteOutput is set to true, the bitcode is /// deleted on success, and the filename string is undefined. This prints to - /// cout a single line message indicating whether compilation was successful - /// or failed, unless Quiet is set. + /// outs() a single line message indicating whether compilation was successful + /// or failed, unless Quiet is set. ExtraArgs specifies additional arguments + /// to pass to the child bugpoint instance. /// - bool runPasses(const std::vector &PassesToRun, + bool runPasses(Module *Program, + const std::vector &PassesToRun, std::string &OutputFilename, bool DeleteOutput = false, - bool Quiet = false) const; + bool Quiet = false, unsigned NumExtraArgs = 0, + const char * const *ExtraArgs = nullptr) const; /// runManyPasses - Take the specified pass list and create different /// combinations of passes to compile the program with. Compile the program with @@ -254,43 +268,45 @@ public: /// If the passes did not compile correctly, output the command required to /// recreate the failure. This returns true if a compiler error is found. /// - bool runManyPasses(const std::vector &AllPasses); + bool runManyPasses(const std::vector &AllPasses, + std::string &ErrMsg); /// writeProgramToFile - This writes the current "Program" to the named - /// bytecode file. If an error occurs, true is returned. + /// bitcode file. If an error occurs, true is returned. /// - bool writeProgramToFile(const std::string &Filename, Module *M = 0) const; + bool writeProgramToFile(const std::string &Filename, const Module *M) const; + bool writeProgramToFile(const std::string &Filename, int FD, + const Module *M) const; private: /// runPasses - Just like the method above, but this just returns true or /// false indicating whether or not the optimizer crashed on the specified /// input (true = crashed). /// - bool runPasses(const std::vector &PassesToRun, + bool runPasses(Module *M, + const std::vector &PassesToRun, bool DeleteOutput = true) const { std::string Filename; - return runPasses(PassesToRun, Filename, DeleteOutput); + return runPasses(M, PassesToRun, Filename, DeleteOutput); } - /// runAsChild - The actual "runPasses" guts that runs in a child process. - int runPassesAsChild(const std::vector &PassesToRun); - /// initializeExecutionEnvironment - This method is used to set up the /// environment for executing LLVM programs. /// bool initializeExecutionEnvironment(); }; -/// ParseInputFile - Given a bytecode or assembly input filename, parse and +/// ParseInputFile - Given a bitcode or assembly input filename, parse and /// return it, or return null if not possible. /// -Module *ParseInputFile(const std::string &InputFilename); +Module *ParseInputFile(const std::string &InputFilename, + LLVMContext& ctxt); /// getPassesString - Turn a list of passes into a string which indicates the /// command line options that must be passed to add the passes. /// -std::string getPassesString(const std::vector &Passes); +std::string getPassesString(const std::vector &Passes); /// PrintFunctionList - prints out list of problematic functions /// @@ -308,7 +324,8 @@ void DeleteFunctionBody(Function *F); /// SplitFunctionsOutOfModule - Given a module and a list of functions in the /// module, split the functions OUT of the specified module, and place them in /// the new module. -Module *SplitFunctionsOutOfModule(Module *M, const std::vector &F); +Module *SplitFunctionsOutOfModule(Module *M, const std::vector &F, + ValueToValueMapTy &VMap); } // End llvm namespace