llvm-dis.cpp revision 218885
1193323Sed//===-- llvm-dis.cpp - The low-level LLVM disassembler --------------------===// 2193323Sed// 3193323Sed// The LLVM Compiler Infrastructure 4193323Sed// 5193323Sed// This file is distributed under the University of Illinois Open Source 6193323Sed// License. See LICENSE.TXT for details. 7193323Sed// 8193323Sed//===----------------------------------------------------------------------===// 9193323Sed// 10193323Sed// This utility may be invoked in the following manner: 11193323Sed// llvm-dis [options] - Read LLVM bitcode from stdin, write asm to stdout 12193323Sed// llvm-dis [options] x.bc - Read LLVM bitcode from the x.bc file, write asm 13193323Sed// to the x.ll file. 14193323Sed// Options: 15193323Sed// --help - Output information about command line switches 16193323Sed// 17193323Sed//===----------------------------------------------------------------------===// 18193323Sed 19195340Sed#include "llvm/LLVMContext.h" 20193323Sed#include "llvm/Module.h" 21212793Sdim#include "llvm/Type.h" 22193323Sed#include "llvm/Bitcode/ReaderWriter.h" 23212793Sdim#include "llvm/Assembly/AssemblyAnnotationWriter.h" 24193323Sed#include "llvm/Support/CommandLine.h" 25212793Sdim#include "llvm/Support/FormattedStream.h" 26193323Sed#include "llvm/Support/ManagedStatic.h" 27193323Sed#include "llvm/Support/MemoryBuffer.h" 28193323Sed#include "llvm/Support/PrettyStackTrace.h" 29218885Sdim#include "llvm/Support/ToolOutputFile.h" 30218885Sdim#include "llvm/Support/Signals.h" 31218885Sdim#include "llvm/Support/system_error.h" 32193323Sedusing namespace llvm; 33193323Sed 34193323Sedstatic cl::opt<std::string> 35193323SedInputFilename(cl::Positional, cl::desc("<input bitcode>"), cl::init("-")); 36193323Sed 37193323Sedstatic cl::opt<std::string> 38193323SedOutputFilename("o", cl::desc("Override output filename"), 39193323Sed cl::value_desc("filename")); 40193323Sed 41193323Sedstatic cl::opt<bool> 42198090SrdivackyForce("f", cl::desc("Enable binary output on terminals")); 43193323Sed 44193323Sedstatic cl::opt<bool> 45193323SedDontPrint("disable-output", cl::desc("Don't output the .ll file"), cl::Hidden); 46193323Sed 47212793Sdimstatic cl::opt<bool> 48212793SdimShowAnnotations("show-annotations", 49212793Sdim cl::desc("Add informational comments to the .ll file")); 50212793Sdim 51212793Sdimnamespace { 52218885Sdim 53212793Sdimclass CommentWriter : public AssemblyAnnotationWriter { 54212793Sdimpublic: 55212793Sdim void emitFunctionAnnot(const Function *F, 56212793Sdim formatted_raw_ostream &OS) { 57212793Sdim OS << "; [#uses=" << F->getNumUses() << ']'; // Output # uses 58212793Sdim OS << '\n'; 59212793Sdim } 60212793Sdim void printInfoComment(const Value &V, formatted_raw_ostream &OS) { 61212793Sdim if (V.getType()->isVoidTy()) return; 62218885Sdim 63212793Sdim OS.PadToColumn(50); 64212793Sdim OS << "; [#uses=" << V.getNumUses() << ']'; // Output # uses 65212793Sdim } 66212793Sdim}; 67218885Sdim 68212793Sdim} // end anon namespace 69212793Sdim 70193323Sedint main(int argc, char **argv) { 71193323Sed // Print a stack trace if we signal out. 72193323Sed sys::PrintStackTraceOnErrorSignal(); 73193323Sed PrettyStackTraceProgram X(argc, argv); 74218885Sdim 75198090Srdivacky LLVMContext &Context = getGlobalContext(); 76193323Sed llvm_shutdown_obj Y; // Call llvm_shutdown() on exit. 77218885Sdim 78218885Sdim 79198090Srdivacky cl::ParseCommandLineOptions(argc, argv, "llvm .bc -> .ll disassembler\n"); 80193323Sed 81198090Srdivacky std::string ErrorMessage; 82198090Srdivacky std::auto_ptr<Module> M; 83218885Sdim 84218885Sdim { 85218885Sdim OwningPtr<MemoryBuffer> BufferPtr; 86218885Sdim if (error_code ec = MemoryBuffer::getFileOrSTDIN(InputFilename, BufferPtr)) 87218885Sdim ErrorMessage = ec.message(); 88218885Sdim else 89218885Sdim M.reset(ParseBitcodeFile(BufferPtr.get(), Context, &ErrorMessage)); 90198090Srdivacky } 91193323Sed 92198090Srdivacky if (M.get() == 0) { 93198090Srdivacky errs() << argv[0] << ": "; 94198090Srdivacky if (ErrorMessage.size()) 95198090Srdivacky errs() << ErrorMessage << "\n"; 96198090Srdivacky else 97198090Srdivacky errs() << "bitcode didn't read correctly.\n"; 98198090Srdivacky return 1; 99198090Srdivacky } 100218885Sdim 101198090Srdivacky // Just use stdout. We won't actually print anything on it. 102198090Srdivacky if (DontPrint) 103198090Srdivacky OutputFilename = "-"; 104218885Sdim 105198090Srdivacky if (OutputFilename.empty()) { // Unspecified output, infer it. 106198090Srdivacky if (InputFilename == "-") { 107198090Srdivacky OutputFilename = "-"; 108198090Srdivacky } else { 109198090Srdivacky const std::string &IFN = InputFilename; 110198090Srdivacky int Len = IFN.length(); 111198090Srdivacky // If the source ends in .bc, strip it off. 112198090Srdivacky if (IFN[Len-3] == '.' && IFN[Len-2] == 'b' && IFN[Len-1] == 'c') 113198090Srdivacky OutputFilename = std::string(IFN.begin(), IFN.end()-3)+".ll"; 114193323Sed else 115198090Srdivacky OutputFilename = IFN+".ll"; 116193323Sed } 117198090Srdivacky } 118193323Sed 119198090Srdivacky std::string ErrorInfo; 120218885Sdim OwningPtr<tool_output_file> 121212793Sdim Out(new tool_output_file(OutputFilename.c_str(), ErrorInfo, 122212793Sdim raw_fd_ostream::F_Binary)); 123198090Srdivacky if (!ErrorInfo.empty()) { 124198090Srdivacky errs() << ErrorInfo << '\n'; 125198090Srdivacky return 1; 126198090Srdivacky } 127193323Sed 128212793Sdim OwningPtr<AssemblyAnnotationWriter> Annotator; 129212793Sdim if (ShowAnnotations) 130212793Sdim Annotator.reset(new CommentWriter()); 131218885Sdim 132198090Srdivacky // All that llvm-dis does is write the assembly to a file. 133198090Srdivacky if (!DontPrint) 134212793Sdim M->print(Out->os(), Annotator.get()); 135193323Sed 136212793Sdim // Declare success. 137212793Sdim Out->keep(); 138212793Sdim 139198090Srdivacky return 0; 140193323Sed} 141193323Sed 142