Generalize abstract interpreter interface to allow linking in an arbitrary number of shared objects

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@9129 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Chris Lattner 2003-10-14 21:52:52 +00:00
parent b8d15b2ad0
commit eeed983821
4 changed files with 86 additions and 50 deletions

View File

@ -27,18 +27,28 @@ public:
static GCC* create(const std::string &ProgramPath, std::string &Message);
/// ExecuteProgram - Execute the program specified by "ProgramFile" (which is
/// either a .s file, or a .c file, specified by FileType), with the specified
/// arguments. Standard input is specified with InputFile, and standard
/// Output is captured to the specified OutputFile location. The SharedLibs
/// option specifies optional native shared objects that can be loaded into
/// the program for execution.
///
int ExecuteProgram(const std::string &ProgramFile,
const std::vector<std::string> &Args,
FileType fileType,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
int MakeSharedObject(const std::string &InputFile,
FileType fileType,
/// MakeSharedObject - This compiles the specified file (which is either a .c
/// file or a .s file) into a shared object.
///
int MakeSharedObject(const std::string &InputFile, FileType fileType,
std::string &OutputFile);
private:
void ProcessFailure(const char **Args);
};
@ -68,7 +78,8 @@ struct AbstractInterpreter {
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "") = 0;
const std::vector<std::string> &SharedLibs =
std::vector<std::string>()) = 0;
};
//===---------------------------------------------------------------------===//
@ -85,7 +96,8 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
// Sometimes we just want to go half-way and only generate the .c file,
// not necessarily compile it with GCC and run the program.
@ -109,7 +121,8 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
// Sometimes we just want to go half-way and only generate the .s file,
// not necessarily compile it all the way and run the program.

View File

@ -23,15 +23,16 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
};
int LLI::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
if (!SharedLib.empty()) {
const std::vector<std::string> &SharedLibs) {
if (!SharedLibs.empty()) {
std::cerr << "LLI currently does not support loading shared libraries.\n"
<< "Exiting.\n";
exit(1);
@ -99,7 +100,8 @@ int LLC::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
const std::vector<std::string> &SharedLibs) {
std::string OutputAsmFile;
if (OutputAsm(Bytecode, OutputAsmFile)) {
std::cerr << "Could not generate asm code with `llc', exiting.\n";
@ -108,7 +110,7 @@ int LLC::ExecuteProgram(const std::string &Bytecode,
// Assuming LLC worked, compile the result with GCC and run it.
int Result = gcc->ExecuteProgram(OutputAsmFile, Args, GCC::AsmFile,
InputFile, OutputFile, SharedLib);
InputFile, OutputFile, SharedLibs);
removeFile(OutputAsmFile);
return Result;
}
@ -145,22 +147,24 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
};
int JIT::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
const std::vector<std::string> &SharedLibs) {
// Construct a vector of parameters, incorporating those from the command-line
std::vector<const char*> JITArgs;
JITArgs.push_back(LLIPath.c_str());
JITArgs.push_back("-quiet");
JITArgs.push_back("-force-interpreter=false");
if (!SharedLib.empty()) {
for (unsigned i = 0, e = SharedLibs.size(); i != e; ++i) {
JITArgs.push_back("-load");
JITArgs.push_back(SharedLib.c_str());
JITArgs.push_back(SharedLibs[i].c_str());
}
JITArgs.push_back(Bytecode.c_str());
// Add optional parameters to the running program from Argv
@ -220,7 +224,7 @@ int CBE::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
const std::vector<std::string> &SharedLibs) {
std::string OutputCFile;
if (OutputC(Bytecode, OutputCFile)) {
std::cerr << "Could not generate C code with `llvm-dis', exiting.\n";
@ -228,7 +232,7 @@ int CBE::ExecuteProgram(const std::string &Bytecode,
}
int Result = gcc->ExecuteProgram(OutputCFile, Args, GCC::CFile,
InputFile, OutputFile, SharedLib);
InputFile, OutputFile, SharedLibs);
removeFile(OutputCFile);
return Result;
@ -257,21 +261,21 @@ CBE *AbstractInterpreter::createCBE(const std::string &ProgramPath,
//===---------------------------------------------------------------------===//
// GCC abstraction
//
// This is not a *real* AbstractInterpreter as it does not accept bytecode
// files, but only input acceptable to GCC, i.e. C, C++, and assembly files
//
int GCC::ExecuteProgram(const std::string &ProgramFile,
const std::vector<std::string> &Args,
FileType fileType,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
std::string OutputBinary = getUniqueFilename(ProgramFile+".gcc.exe");
const std::vector<std::string> &SharedLibs) {
std::vector<const char*> GCCArgs;
GCCArgs.push_back(GCCPath.c_str());
if (!SharedLib.empty()) // Specify the shared library to link in...
GCCArgs.push_back(SharedLib.c_str());
// Specify the shared libraries to link in...
for (unsigned i = 0, e = SharedLibs.size(); i != e; ++i)
GCCArgs.push_back(SharedLibs[i].c_str());
// Specify -x explicitly in case the extension is wonky
GCCArgs.push_back("-x");
if (fileType == CFile) {
GCCArgs.push_back("c");
@ -281,6 +285,7 @@ int GCC::ExecuteProgram(const std::string &ProgramFile,
}
GCCArgs.push_back(ProgramFile.c_str()); // Specify the input filename...
GCCArgs.push_back("-o");
std::string OutputBinary = getUniqueFilename(ProgramFile+".gcc.exe");
GCCArgs.push_back(OutputBinary.c_str()); // Output to the right file...
GCCArgs.push_back("-lm"); // Hard-code the math library...
GCCArgs.push_back("-O2"); // Optimize the program a bit...

View File

@ -23,15 +23,16 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
};
int LLI::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
if (!SharedLib.empty()) {
const std::vector<std::string> &SharedLibs) {
if (!SharedLibs.empty()) {
std::cerr << "LLI currently does not support loading shared libraries.\n"
<< "Exiting.\n";
exit(1);
@ -99,7 +100,8 @@ int LLC::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
const std::vector<std::string> &SharedLibs) {
std::string OutputAsmFile;
if (OutputAsm(Bytecode, OutputAsmFile)) {
std::cerr << "Could not generate asm code with `llc', exiting.\n";
@ -108,7 +110,7 @@ int LLC::ExecuteProgram(const std::string &Bytecode,
// Assuming LLC worked, compile the result with GCC and run it.
int Result = gcc->ExecuteProgram(OutputAsmFile, Args, GCC::AsmFile,
InputFile, OutputFile, SharedLib);
InputFile, OutputFile, SharedLibs);
removeFile(OutputAsmFile);
return Result;
}
@ -145,22 +147,24 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
};
int JIT::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
const std::vector<std::string> &SharedLibs) {
// Construct a vector of parameters, incorporating those from the command-line
std::vector<const char*> JITArgs;
JITArgs.push_back(LLIPath.c_str());
JITArgs.push_back("-quiet");
JITArgs.push_back("-force-interpreter=false");
if (!SharedLib.empty()) {
for (unsigned i = 0, e = SharedLibs.size(); i != e; ++i) {
JITArgs.push_back("-load");
JITArgs.push_back(SharedLib.c_str());
JITArgs.push_back(SharedLibs[i].c_str());
}
JITArgs.push_back(Bytecode.c_str());
// Add optional parameters to the running program from Argv
@ -220,7 +224,7 @@ int CBE::ExecuteProgram(const std::string &Bytecode,
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
const std::vector<std::string> &SharedLibs) {
std::string OutputCFile;
if (OutputC(Bytecode, OutputCFile)) {
std::cerr << "Could not generate C code with `llvm-dis', exiting.\n";
@ -228,7 +232,7 @@ int CBE::ExecuteProgram(const std::string &Bytecode,
}
int Result = gcc->ExecuteProgram(OutputCFile, Args, GCC::CFile,
InputFile, OutputFile, SharedLib);
InputFile, OutputFile, SharedLibs);
removeFile(OutputCFile);
return Result;
@ -257,21 +261,21 @@ CBE *AbstractInterpreter::createCBE(const std::string &ProgramPath,
//===---------------------------------------------------------------------===//
// GCC abstraction
//
// This is not a *real* AbstractInterpreter as it does not accept bytecode
// files, but only input acceptable to GCC, i.e. C, C++, and assembly files
//
int GCC::ExecuteProgram(const std::string &ProgramFile,
const std::vector<std::string> &Args,
FileType fileType,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib) {
std::string OutputBinary = getUniqueFilename(ProgramFile+".gcc.exe");
const std::vector<std::string> &SharedLibs) {
std::vector<const char*> GCCArgs;
GCCArgs.push_back(GCCPath.c_str());
if (!SharedLib.empty()) // Specify the shared library to link in...
GCCArgs.push_back(SharedLib.c_str());
// Specify the shared libraries to link in...
for (unsigned i = 0, e = SharedLibs.size(); i != e; ++i)
GCCArgs.push_back(SharedLibs[i].c_str());
// Specify -x explicitly in case the extension is wonky
GCCArgs.push_back("-x");
if (fileType == CFile) {
GCCArgs.push_back("c");
@ -281,6 +285,7 @@ int GCC::ExecuteProgram(const std::string &ProgramFile,
}
GCCArgs.push_back(ProgramFile.c_str()); // Specify the input filename...
GCCArgs.push_back("-o");
std::string OutputBinary = getUniqueFilename(ProgramFile+".gcc.exe");
GCCArgs.push_back(OutputBinary.c_str()); // Output to the right file...
GCCArgs.push_back("-lm"); // Hard-code the math library...
GCCArgs.push_back("-O2"); // Optimize the program a bit...

View File

@ -27,18 +27,28 @@ public:
static GCC* create(const std::string &ProgramPath, std::string &Message);
/// ExecuteProgram - Execute the program specified by "ProgramFile" (which is
/// either a .s file, or a .c file, specified by FileType), with the specified
/// arguments. Standard input is specified with InputFile, and standard
/// Output is captured to the specified OutputFile location. The SharedLibs
/// option specifies optional native shared objects that can be loaded into
/// the program for execution.
///
int ExecuteProgram(const std::string &ProgramFile,
const std::vector<std::string> &Args,
FileType fileType,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
int MakeSharedObject(const std::string &InputFile,
FileType fileType,
/// MakeSharedObject - This compiles the specified file (which is either a .c
/// file or a .s file) into a shared object.
///
int MakeSharedObject(const std::string &InputFile, FileType fileType,
std::string &OutputFile);
private:
void ProcessFailure(const char **Args);
};
@ -68,7 +78,8 @@ struct AbstractInterpreter {
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "") = 0;
const std::vector<std::string> &SharedLibs =
std::vector<std::string>()) = 0;
};
//===---------------------------------------------------------------------===//
@ -85,7 +96,8 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
// Sometimes we just want to go half-way and only generate the .c file,
// not necessarily compile it with GCC and run the program.
@ -109,7 +121,8 @@ public:
const std::vector<std::string> &Args,
const std::string &InputFile,
const std::string &OutputFile,
const std::string &SharedLib = "");
const std::vector<std::string> &SharedLibs =
std::vector<std::string>());
// Sometimes we just want to go half-way and only generate the .s file,
// not necessarily compile it all the way and run the program.