Compiler.h revision da5e0c369ad20bf70556c7e7cf86807cf171730d
1/* 2 * Copyright 2010, The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17#ifndef BCC_COMPILER_H 18#define BCC_COMPILER_H 19 20#include <bcc/bcc.h> 21 22#include "CodeEmitter.h" 23#include "CodeMemoryManager.h" 24 25#include "librsloader.h" 26 27#include "llvm/ADT/OwningPtr.h" 28#include "llvm/ADT/StringRef.h" 29#include "llvm/ADT/SmallVector.h" 30#include "llvm/Target/TargetMachine.h" 31 32#include <stddef.h> 33 34#include <list> 35#include <string> 36#include <vector> 37#include <utility> 38 39 40namespace llvm { 41 class LLVMContext; 42 class Module; 43 class MemoryBuffer; 44 class NamedMDNode; 45 class TargetData; 46} 47 48 49namespace bcc { 50 class ScriptCompiled; 51 52 class Compiler { 53 private: 54 ////////////////////////////////////////////////////////////////////////// 55 // The variable section below (e.g., Triple, CodeGenOptLevel) 56 // is initialized in GlobalInitialization() 57 // 58 static bool GlobalInitialized; 59 60 // If given, this will be the name of the target triple to compile for. 61 // If not given, the initial values defined in this file will be used. 62 static std::string Triple; 63 64 static llvm::CodeGenOpt::Level CodeGenOptLevel; 65 66 // End of section of GlobalInitializing variables 67 ///////////////////////////////////////////////////////////////////////// 68 // If given, the name of the target CPU to generate code for. 69 static std::string CPU; 70 71 // The list of target specific features to enable or disable -- this should 72 // be a list of strings starting with '+' (enable) or '-' (disable). 73 static std::vector<std::string> Features; 74 75 static void LLVMErrorHandler(void *UserData, const std::string &Message); 76 77 static const llvm::StringRef PragmaMetadataName; 78 static const llvm::StringRef ExportVarMetadataName; 79 static const llvm::StringRef ExportFuncMetadataName; 80 static const llvm::StringRef ObjectSlotMetadataName; 81 82 friend class CodeEmitter; 83 friend class CodeMemoryManager; 84 85 86 private: 87 const char *mCachePath; 88 89 ScriptCompiled *mpResult; 90 91 std::string mError; 92 93#if USE_OLD_JIT 94 // The memory manager for code emitter 95 llvm::OwningPtr<CodeMemoryManager> mCodeMemMgr; 96 97 // The CodeEmitter 98 llvm::OwningPtr<CodeEmitter> mCodeEmitter; 99#endif 100 101#if USE_MCJIT 102 // Compilation buffer for MCJIT 103 llvm::SmallVector<char, 1024> mEmittedELFExecutable; 104 105 // Loaded and relocated executable 106 RSExecRef mRSExecutable; 107#endif 108 109 BCCSymbolLookupFn mpSymbolLookupFn; 110 void *mpSymbolLookupContext; 111 112 llvm::LLVMContext *mContext; 113 llvm::Module *mModule; 114 115 bool mHasLinked; 116 117 public: 118 Compiler(ScriptCompiled *result); 119 120 static void GlobalInitialization(); 121 122 void setCachePath(const char *cachePath) { 123 mCachePath = cachePath; 124 return; 125 } 126 127 void registerSymbolCallback(BCCSymbolLookupFn pFn, void *pContext) { 128 mpSymbolLookupFn = pFn; 129 mpSymbolLookupContext = pContext; 130 } 131 132#if USE_OLD_JIT 133 CodeMemoryManager *createCodeMemoryManager(); 134 135 CodeEmitter *createCodeEmitter(); 136#endif 137 138#if USE_MCJIT 139 bool getObjPath(std::string &objPath); 140 141 void *getSymbolAddress(char const *name); 142#endif 143 144 llvm::Module *parseBitcodeFile(llvm::MemoryBuffer *MEM); 145 146 int readModule(llvm::Module *module) { 147 mModule = module; 148 return hasError(); 149 } 150 151 int linkModule(llvm::Module *module); 152 153 int compile(); 154 155 char const *getErrorMessage() { 156 return mError.c_str(); 157 } 158 159 const llvm::Module *getModule() const { 160 return mModule; 161 } 162 163 ~Compiler(); 164 165 private: 166 167 int runCodeGen(llvm::TargetData *TD, llvm::TargetMachine *TM, 168 llvm::NamedMDNode const *ExportVarMetadata, 169 llvm::NamedMDNode const *ExportFuncMetadata); 170 171 int runMCCodeGen(llvm::TargetData *TD, llvm::TargetMachine *TM, 172 llvm::NamedMDNode const *ExportVarMetadata, 173 llvm::NamedMDNode const *ExportFuncMetadata); 174 175#if USE_MCJIT 176 static void *resolveSymbolAdapter(void *context, char const *name); 177#endif 178 179 int runLTO(llvm::TargetData *TD, 180 llvm::NamedMDNode const *ExportVarMetadata, 181 llvm::NamedMDNode const *ExportFuncMetadata); 182 183 int writeELFExecToFile(); 184 185 bool hasError() const { 186 return !mError.empty(); 187 } 188 189 void setError(const char *Error) { 190 mError.assign(Error); // Copying 191 } 192 193 void setError(const std::string &Error) { 194 mError = Error; 195 } 196 197 }; // End of class Compiler 198 199} // namespace bcc 200 201#endif // BCC_COMPILER_H 202