xref: /openbsd-src/gnu/llvm/llvm/tools/bugpoint/ToolRunner.h (revision 097a140d792de8b2bbe59ad827d39eabf9b4280a)
109467b48Spatrick //===-- tools/bugpoint/ToolRunner.h -----------------------------*- C++ -*-===//
209467b48Spatrick //
309467b48Spatrick // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
409467b48Spatrick // See https://llvm.org/LICENSE.txt for license information.
509467b48Spatrick // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
609467b48Spatrick //
709467b48Spatrick //===----------------------------------------------------------------------===//
809467b48Spatrick //
909467b48Spatrick // This file exposes an abstraction around a platform C compiler, used to
1009467b48Spatrick // compile C and assembly code.  It also exposes an "AbstractIntepreter"
1109467b48Spatrick // interface, which is used to execute code using one of the LLVM execution
1209467b48Spatrick // engines.
1309467b48Spatrick //
1409467b48Spatrick //===----------------------------------------------------------------------===//
1509467b48Spatrick 
1609467b48Spatrick #ifndef LLVM_TOOLS_BUGPOINT_TOOLRUNNER_H
1709467b48Spatrick #define LLVM_TOOLS_BUGPOINT_TOOLRUNNER_H
1809467b48Spatrick 
1909467b48Spatrick #include "llvm/ADT/Triple.h"
2009467b48Spatrick #include "llvm/Support/CommandLine.h"
2109467b48Spatrick #include "llvm/Support/Error.h"
2209467b48Spatrick #include "llvm/Support/Path.h"
2309467b48Spatrick #include "llvm/Support/SystemUtils.h"
2409467b48Spatrick #include <exception>
2509467b48Spatrick #include <vector>
2609467b48Spatrick 
2709467b48Spatrick namespace llvm {
2809467b48Spatrick 
2909467b48Spatrick extern cl::opt<bool> SaveTemps;
3009467b48Spatrick extern Triple TargetTriple;
3109467b48Spatrick 
3209467b48Spatrick class LLC;
3309467b48Spatrick 
3409467b48Spatrick //===---------------------------------------------------------------------===//
3509467b48Spatrick // CC abstraction
3609467b48Spatrick //
3709467b48Spatrick class CC {
3809467b48Spatrick   std::string CCPath;              // The path to the cc executable.
3909467b48Spatrick   std::string RemoteClientPath;    // The path to the rsh / ssh executable.
4009467b48Spatrick   std::vector<std::string> ccArgs; // CC-specific arguments.
CC(StringRef ccPath,StringRef RemotePath,const std::vector<std::string> * CCArgs)4109467b48Spatrick   CC(StringRef ccPath, StringRef RemotePath,
4209467b48Spatrick      const std::vector<std::string> *CCArgs)
43*097a140dSpatrick       : CCPath(std::string(ccPath)), RemoteClientPath(std::string(RemotePath)) {
4409467b48Spatrick     if (CCArgs)
4509467b48Spatrick       ccArgs = *CCArgs;
4609467b48Spatrick   }
4709467b48Spatrick 
4809467b48Spatrick public:
4909467b48Spatrick   enum FileType { AsmFile, ObjectFile, CFile };
5009467b48Spatrick 
5109467b48Spatrick   static CC *create(const char *Argv0, std::string &Message,
5209467b48Spatrick                     const std::string &CCBinary,
5309467b48Spatrick                     const std::vector<std::string> *Args);
5409467b48Spatrick 
5509467b48Spatrick   /// ExecuteProgram - Execute the program specified by "ProgramFile" (which is
5609467b48Spatrick   /// either a .s file, or a .c file, specified by FileType), with the specified
5709467b48Spatrick   /// arguments.  Standard input is specified with InputFile, and standard
5809467b48Spatrick   /// Output is captured to the specified OutputFile location.  The SharedLibs
5909467b48Spatrick   /// option specifies optional native shared objects that can be loaded into
6009467b48Spatrick   /// the program for execution.
6109467b48Spatrick   ///
6209467b48Spatrick   Expected<int> ExecuteProgram(
6309467b48Spatrick       const std::string &ProgramFile, const std::vector<std::string> &Args,
6409467b48Spatrick       FileType fileType, const std::string &InputFile,
6509467b48Spatrick       const std::string &OutputFile,
6609467b48Spatrick       const std::vector<std::string> &CCArgs = std::vector<std::string>(),
6709467b48Spatrick       unsigned Timeout = 0, unsigned MemoryLimit = 0);
6809467b48Spatrick 
6909467b48Spatrick   /// MakeSharedObject - This compiles the specified file (which is either a .c
7009467b48Spatrick   /// file or a .s file) into a shared object.
7109467b48Spatrick   ///
7209467b48Spatrick   Error MakeSharedObject(const std::string &InputFile, FileType fileType,
7309467b48Spatrick                          std::string &OutputFile,
7409467b48Spatrick                          const std::vector<std::string> &ArgsForCC);
7509467b48Spatrick };
7609467b48Spatrick 
7709467b48Spatrick //===---------------------------------------------------------------------===//
7809467b48Spatrick /// AbstractInterpreter Class - Subclasses of this class are used to execute
7909467b48Spatrick /// LLVM bitcode in a variety of ways.  This abstract interface hides this
8009467b48Spatrick /// complexity behind a simple interface.
8109467b48Spatrick ///
8209467b48Spatrick class AbstractInterpreter {
8309467b48Spatrick   virtual void anchor();
8409467b48Spatrick 
8509467b48Spatrick public:
8609467b48Spatrick   static LLC *createLLC(const char *Argv0, std::string &Message,
8709467b48Spatrick                         const std::string &CCBinary,
8809467b48Spatrick                         const std::vector<std::string> *Args = nullptr,
8909467b48Spatrick                         const std::vector<std::string> *CCArgs = nullptr,
9009467b48Spatrick                         bool UseIntegratedAssembler = false);
9109467b48Spatrick 
9209467b48Spatrick   static AbstractInterpreter *
9309467b48Spatrick   createLLI(const char *Argv0, std::string &Message,
9409467b48Spatrick             const std::vector<std::string> *Args = nullptr);
9509467b48Spatrick 
9609467b48Spatrick   static AbstractInterpreter *
9709467b48Spatrick   createJIT(const char *Argv0, std::string &Message,
9809467b48Spatrick             const std::vector<std::string> *Args = nullptr);
9909467b48Spatrick 
10009467b48Spatrick   static AbstractInterpreter *
10109467b48Spatrick   createCustomCompiler(const char *Argv0, std::string &Message,
10209467b48Spatrick                        const std::string &CompileCommandLine);
10309467b48Spatrick 
10409467b48Spatrick   static AbstractInterpreter *
10509467b48Spatrick   createCustomExecutor(const char *Argv0, std::string &Message,
10609467b48Spatrick                        const std::string &ExecCommandLine);
10709467b48Spatrick 
~AbstractInterpreter()10809467b48Spatrick   virtual ~AbstractInterpreter() {}
10909467b48Spatrick 
11009467b48Spatrick   /// compileProgram - Compile the specified program from bitcode to executable
11109467b48Spatrick   /// code.  This does not produce any output, it is only used when debugging
11209467b48Spatrick   /// the code generator.  It returns false if the code generator fails.
11309467b48Spatrick   virtual Error compileProgram(const std::string &Bitcode, unsigned Timeout = 0,
11409467b48Spatrick                                unsigned MemoryLimit = 0) {
11509467b48Spatrick     return Error::success();
11609467b48Spatrick   }
11709467b48Spatrick 
11809467b48Spatrick   /// Compile the specified program from bitcode to code understood by the CC
11909467b48Spatrick   /// driver (either C or asm).  Returns an error if the code generator fails,,
12009467b48Spatrick   /// otherwise, the type of code emitted.
12109467b48Spatrick   virtual Expected<CC::FileType> OutputCode(const std::string &Bitcode,
12209467b48Spatrick                                             std::string &OutFile,
12309467b48Spatrick                                             unsigned Timeout = 0,
12409467b48Spatrick                                             unsigned MemoryLimit = 0) {
12509467b48Spatrick     return make_error<StringError>(
12609467b48Spatrick         "OutputCode not supported by this AbstractInterpreter!",
12709467b48Spatrick         inconvertibleErrorCode());
12809467b48Spatrick   }
12909467b48Spatrick 
13009467b48Spatrick   /// ExecuteProgram - Run the specified bitcode file, emitting output to the
13109467b48Spatrick   /// specified filename.  This sets RetVal to the exit code of the program or
13209467b48Spatrick   /// returns an Error if a problem was encountered that prevented execution of
13309467b48Spatrick   /// the program.
13409467b48Spatrick   ///
13509467b48Spatrick   virtual Expected<int> ExecuteProgram(
13609467b48Spatrick       const std::string &Bitcode, const std::vector<std::string> &Args,
13709467b48Spatrick       const std::string &InputFile, const std::string &OutputFile,
13809467b48Spatrick       const std::vector<std::string> &CCArgs = std::vector<std::string>(),
13909467b48Spatrick       const std::vector<std::string> &SharedLibs = std::vector<std::string>(),
14009467b48Spatrick       unsigned Timeout = 0, unsigned MemoryLimit = 0) = 0;
14109467b48Spatrick };
14209467b48Spatrick 
14309467b48Spatrick //===---------------------------------------------------------------------===//
14409467b48Spatrick // LLC Implementation of AbstractIntepreter interface
14509467b48Spatrick //
14609467b48Spatrick class LLC : public AbstractInterpreter {
14709467b48Spatrick   std::string LLCPath;               // The path to the LLC executable.
14809467b48Spatrick   std::vector<std::string> ToolArgs; // Extra args to pass to LLC.
14909467b48Spatrick   CC *cc;
15009467b48Spatrick   bool UseIntegratedAssembler;
15109467b48Spatrick 
15209467b48Spatrick public:
LLC(const std::string & llcPath,CC * cc,const std::vector<std::string> * Args,bool useIntegratedAssembler)15309467b48Spatrick   LLC(const std::string &llcPath, CC *cc, const std::vector<std::string> *Args,
15409467b48Spatrick       bool useIntegratedAssembler)
15509467b48Spatrick       : LLCPath(llcPath), cc(cc),
15609467b48Spatrick         UseIntegratedAssembler(useIntegratedAssembler) {
15709467b48Spatrick     ToolArgs.clear();
15809467b48Spatrick     if (Args)
15909467b48Spatrick       ToolArgs = *Args;
16009467b48Spatrick   }
~LLC()16109467b48Spatrick   ~LLC() override { delete cc; }
16209467b48Spatrick 
16309467b48Spatrick   /// compileProgram - Compile the specified program from bitcode to executable
16409467b48Spatrick   /// code.  This does not produce any output, it is only used when debugging
16509467b48Spatrick   /// the code generator.  Returns false if the code generator fails.
16609467b48Spatrick   Error compileProgram(const std::string &Bitcode, unsigned Timeout = 0,
16709467b48Spatrick                        unsigned MemoryLimit = 0) override;
16809467b48Spatrick 
16909467b48Spatrick   Expected<int> ExecuteProgram(
17009467b48Spatrick       const std::string &Bitcode, const std::vector<std::string> &Args,
17109467b48Spatrick       const std::string &InputFile, const std::string &OutputFile,
17209467b48Spatrick       const std::vector<std::string> &CCArgs = std::vector<std::string>(),
17309467b48Spatrick       const std::vector<std::string> &SharedLibs = std::vector<std::string>(),
17409467b48Spatrick       unsigned Timeout = 0, unsigned MemoryLimit = 0) override;
17509467b48Spatrick 
17609467b48Spatrick   Expected<CC::FileType> OutputCode(const std::string &Bitcode,
17709467b48Spatrick                                     std::string &OutFile, unsigned Timeout = 0,
17809467b48Spatrick                                     unsigned MemoryLimit = 0) override;
17909467b48Spatrick };
18009467b48Spatrick 
18109467b48Spatrick /// Find the first executable file \ExeName, either in the user's PATH or,
18209467b48Spatrick /// failing that, in the same directory as argv[0]. This allows us to find
18309467b48Spatrick /// another LLVM tool if it is built in the same directory. If no executable is
18409467b48Spatrick /// found, an error is returned.
18509467b48Spatrick ErrorOr<std::string> FindProgramByName(const std::string &ExeName,
18609467b48Spatrick                                        const char *Argv0, void *MainAddr);
18709467b48Spatrick 
18809467b48Spatrick } // End llvm namespace
18909467b48Spatrick 
19009467b48Spatrick #endif
191