From 1a3061766444af9a12ff5d4b6f99a85a68cba090 Mon Sep 17 00:00:00 2001 From: Chris Lattner Date: Wed, 31 Oct 2001 04:28:11 +0000 Subject: [PATCH] Initial checkin of GCCAS llvm-svn: 1058 --- llvm/tools/gccas/Makefile | 6 ++++ llvm/tools/gccas/gccas.cpp | 74 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 80 insertions(+) create mode 100644 llvm/tools/gccas/Makefile create mode 100644 llvm/tools/gccas/gccas.cpp diff --git a/llvm/tools/gccas/Makefile b/llvm/tools/gccas/Makefile new file mode 100644 index 000000000000..5efda5c1c07f --- /dev/null +++ b/llvm/tools/gccas/Makefile @@ -0,0 +1,6 @@ +LEVEL = ../.. + +TOOLNAME = gccas +USEDLIBS = asmparser bcwriter analysis transforms opt vmcore asmwriter support + +include $(LEVEL)/Makefile.common diff --git a/llvm/tools/gccas/gccas.cpp b/llvm/tools/gccas/gccas.cpp new file mode 100644 index 000000000000..4d1f0b2d7948 --- /dev/null +++ b/llvm/tools/gccas/gccas.cpp @@ -0,0 +1,74 @@ +//===------------------------------------------------------------------------=== +// LLVM 'GCCAS' UTILITY +// +// This utility is designed to be used by the GCC frontend for creating +// bytecode files from it's intermediate llvm assembly. The requirements for +// this utility are thus slightly different than that of the standard as util. +// +//===------------------------------------------------------------------------=== + +#include "llvm/Module.h" +#include "llvm/Assembly/Parser.h" +#include "llvm/Transforms/CleanupGCCOutput.h" +#include "llvm/Optimizations/DCE.h" +#include "llvm/Bytecode/Writer.h" +#include "llvm/Support/CommandLine.h" +#include +#include +#include + +cl::String InputFilename ("", "Parse file, compile to bytecode", + cl::Required, ""); +cl::String OutputFilename("o", "Override output filename", cl::NoFlags, ""); + +int main(int argc, char **argv) { + cl::ParseCommandLineOptions(argc, argv, " llvm .ll -> .bc assembler\n"); + + ostream *Out = 0; + std::auto_ptr M; + try { + // Parse the file now... + M.reset(ParseAssemblyFile(InputFilename)); + } catch (const ParseException &E) { + cerr << E.getMessage() << endl; + return 1; + } + + if (M.get() == 0) { + cerr << "assembly didn't read correctly.\n"; + return 1; + } + + if (OutputFilename == "") { // Didn't specify an output filename? + string IFN = InputFilename; + int Len = IFN.length(); + if (IFN[Len-2] == '.' && IFN[Len-1] == 's') { // Source ends in .s? + OutputFilename = string(IFN.begin(), IFN.end()-2); + } else { + OutputFilename = IFN; // Append a .o to it + } + OutputFilename += ".o"; + } + + Out = new ofstream(OutputFilename.c_str(), ios::out); + if (!Out->good()) { + cerr << "Error opening " << OutputFilename << "!\n"; + return 1; + } + + // In addition to just parsing the input from GCC, we also want to spiff it up + // a little bit. Do this now. + // + vector Passes; + Passes.push_back(new CleanupGCCOutput()); + Passes.push_back(new opt::DeadCodeElimination()); + + // Run our queue of passes all at once now, efficiently. This form of + // runAllPasses frees the Pass objects after runAllPasses completes. + // + Pass::runAllPassesAndFree(M.get(), Passes); + + WriteBytecodeToFile(M.get(), *Out); + return 0; +} +