1 //===- IRTransformLayer.h - Run all IR through a functor --------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // Run all IR passed in through a user supplied functor. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #ifndef LLVM_EXECUTIONENGINE_ORC_IRTRANSFORMLAYER_H 15 #define LLVM_EXECUTIONENGINE_ORC_IRTRANSFORMLAYER_H 16 17 #include "llvm/ExecutionEngine/JITSymbol.h" 18 #include "llvm/ExecutionEngine/Orc/Layer.h" 19 #include <memory> 20 #include <string> 21 22 namespace llvm { 23 class Module; 24 namespace orc { 25 26 class IRTransformLayer2 : public IRLayer { 27 public: 28 29 using TransformFunction = 30 std::function<Expected<std::unique_ptr<Module>>(std::unique_ptr<Module>)>; 31 32 IRTransformLayer2(ExecutionSession &ES, IRLayer &BaseLayer, 33 TransformFunction Transform = identityTransform); 34 setTransform(TransformFunction Transform)35 void setTransform(TransformFunction Transform) { 36 this->Transform = std::move(Transform); 37 } 38 39 void emit(MaterializationResponsibility R, VModuleKey K, 40 std::unique_ptr<Module> M) override; 41 identityTransform(std::unique_ptr<Module> M)42 static std::unique_ptr<Module> identityTransform(std::unique_ptr<Module> M) { 43 return M; 44 } 45 46 private: 47 IRLayer &BaseLayer; 48 TransformFunction Transform; 49 }; 50 51 /// IR mutating layer. 52 /// 53 /// This layer applies a user supplied transform to each module that is added, 54 /// then adds the transformed module to the layer below. 55 template <typename BaseLayerT, typename TransformFtor> 56 class IRTransformLayer { 57 public: 58 59 /// Construct an IRTransformLayer with the given BaseLayer 60 IRTransformLayer(BaseLayerT &BaseLayer, 61 TransformFtor Transform = TransformFtor()) BaseLayer(BaseLayer)62 : BaseLayer(BaseLayer), Transform(std::move(Transform)) {} 63 64 /// Apply the transform functor to the module, then add the module to 65 /// the layer below, along with the memory manager and symbol resolver. 66 /// 67 /// @return A handle for the added modules. addModule(VModuleKey K,std::unique_ptr<Module> M)68 Error addModule(VModuleKey K, std::unique_ptr<Module> M) { 69 return BaseLayer.addModule(std::move(K), Transform(std::move(M))); 70 } 71 72 /// Remove the module associated with the VModuleKey K. removeModule(VModuleKey K)73 Error removeModule(VModuleKey K) { return BaseLayer.removeModule(K); } 74 75 /// Search for the given named symbol. 76 /// @param Name The name of the symbol to search for. 77 /// @param ExportedSymbolsOnly If true, search only for exported symbols. 78 /// @return A handle for the given named symbol, if it exists. findSymbol(const std::string & Name,bool ExportedSymbolsOnly)79 JITSymbol findSymbol(const std::string &Name, bool ExportedSymbolsOnly) { 80 return BaseLayer.findSymbol(Name, ExportedSymbolsOnly); 81 } 82 83 /// Get the address of the given symbol in the context of the module 84 /// represented by the VModuleKey K. This call is forwarded to the base 85 /// layer's implementation. 86 /// @param K The VModuleKey for the module to search in. 87 /// @param Name The name of the symbol to search for. 88 /// @param ExportedSymbolsOnly If true, search only for exported symbols. 89 /// @return A handle for the given named symbol, if it is found in the 90 /// given module. findSymbolIn(VModuleKey K,const std::string & Name,bool ExportedSymbolsOnly)91 JITSymbol findSymbolIn(VModuleKey K, const std::string &Name, 92 bool ExportedSymbolsOnly) { 93 return BaseLayer.findSymbolIn(K, Name, ExportedSymbolsOnly); 94 } 95 96 /// Immediately emit and finalize the module represented by the given 97 /// VModuleKey. 98 /// @param K The VModuleKey for the module to emit/finalize. emitAndFinalize(VModuleKey K)99 Error emitAndFinalize(VModuleKey K) { return BaseLayer.emitAndFinalize(K); } 100 101 /// Access the transform functor directly. getTransform()102 TransformFtor& getTransform() { return Transform; } 103 104 /// Access the mumate functor directly. getTransform()105 const TransformFtor& getTransform() const { return Transform; } 106 107 private: 108 BaseLayerT &BaseLayer; 109 TransformFtor Transform; 110 }; 111 112 } // end namespace orc 113 } // end namespace llvm 114 115 #endif // LLVM_EXECUTIONENGINE_ORC_IRTRANSFORMLAYER_H 116