From e641b527e8eaea96438a8a6971d242a12cf1803d Mon Sep 17 00:00:00 2001 From: Anton Korobeynikov Date: Wed, 5 Aug 2009 09:29:56 +0000 Subject: [PATCH] Emit module-level inline asm for CBE. Patch by Sandeep Patel git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@78180 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/CBackend/CBackend.cpp | 48 ++++++++++++++++++++++++++++++++ 1 file changed, 48 insertions(+) diff --git a/lib/Target/CBackend/CBackend.cpp b/lib/Target/CBackend/CBackend.cpp index f7923200a97..155bb17f87d 100644 --- a/lib/Target/CBackend/CBackend.cpp +++ b/lib/Target/CBackend/CBackend.cpp @@ -29,6 +29,7 @@ #include "llvm/Analysis/ConstantsScanner.h" #include "llvm/Analysis/FindUsedTypes.h" #include "llvm/Analysis/LoopInfo.h" +#include "llvm/Analysis/ValueTracking.h" #include "llvm/CodeGen/Passes.h" #include "llvm/CodeGen/IntrinsicLowering.h" #include "llvm/Transforms/Scalar.h" @@ -1811,6 +1812,30 @@ static SpecialGlobalClass getGlobalVariableClass(const GlobalVariable *GV) { return NotSpecial; } +// PrintEscapedString - Print each character of the specified string, escaping +// it if it is not printable or if it is an escape char. +static void PrintEscapedString(const char *Str, unsigned Length, + raw_ostream &Out) { + for (unsigned i = 0; i != Length; ++i) { + unsigned char C = Str[i]; + if (isprint(C) && C != '\\' && C != '"') + Out << C; + else if (C == '\\') + Out << "\\\\"; + else if (C == '\"') + Out << "\\\""; + else if (C == '\t') + Out << "\\t"; + else + Out << "\\x" << hexdigit(C >> 4) << hexdigit(C & 0x0F); + } +} + +// PrintEscapedString - Print each character of the specified string, escaping +// it if it is not printable or if it is an escape char. +static void PrintEscapedString(const std::string &Str, raw_ostream &Out) { + PrintEscapedString(Str.c_str(), Str.size(), Out); +} bool CWriter::doInitialization(Module &M) { FunctionPass::doInitialization(M); @@ -1865,6 +1890,29 @@ bool CWriter::doInitialization(Module &M) { // First output all the declarations for the program, because C requires // Functions & globals to be declared before they are used. // + if (!M.getModuleInlineAsm().empty()) { + Out << "/* Module asm statements */\n" + << "asm("; + + // Split the string into lines, to make it easier to read the .ll file. + std::string Asm = M.getModuleInlineAsm(); + size_t CurPos = 0; + size_t NewLine = Asm.find_first_of('\n', CurPos); + while (NewLine != std::string::npos) { + // We found a newline, print the portion of the asm string from the + // last newline up to this newline. + Out << "\""; + PrintEscapedString(std::string(Asm.begin()+CurPos, Asm.begin()+NewLine), + Out); + Out << "\\n\"\n"; + CurPos = NewLine+1; + NewLine = Asm.find_first_of('\n', CurPos); + } + Out << "\""; + PrintEscapedString(std::string(Asm.begin()+CurPos, Asm.end()), Out); + Out << "\");\n" + << "/* End Module asm statements */\n"; + } // Loop over the symbol table, emitting all named constants... printModuleTypes(M.getTypeSymbolTable());