X-Git-Url: http://demsky.eecs.uci.edu/git/?a=blobdiff_plain;f=docs%2FWritingAnLLVMPass.html;h=58bea1a0cad4cce106158fb54808e40c73d6a012;hb=b361ec31979b2ac40af00d5258b9571239954103;hp=0c362d0e7c6a4f7a93f768181afc04e0e966c475;hpb=832171cb9724d2d31c8dfb73172e2be8f6dd13ee;p=oota-llvm.git diff --git a/docs/WritingAnLLVMPass.html b/docs/WritingAnLLVMPass.html index 0c362d0e7c6..58bea1a0cad 100644 --- a/docs/WritingAnLLVMPass.html +++ b/docs/WritingAnLLVMPass.html @@ -29,10 +29,10 @@
+ static char ID; + Hello() : FunctionPass((intptr_t)&ID) {} +
+ +
This declares pass identifier used by LLVM to identify pass. This allows LLVM to +avoid using expensive C++ runtime information.
+virtual bool runOnFunction(Function &F) { llvm::cerr << "Hello: " << F.getName() << "\n"; @@ -269,6 +284,13 @@ href="#FunctionPass">FunctionPass. This is where we are supposed to do our thing, so we just print out our message with the name of each function. ++ ++ char Hello::ID = 0; +We initialize pass ID here. LLVM uses ID's address to identify pass so +initialization value is not important.
+@@ -321,8 +348,8 @@ use the opt tool to access it, once loaded.RegisterPass<Hello> X("hello", "Hello World Pass"); } // end of anonymous namespace @@ -288,12 +310,17 @@ argument "hello", and a name "Hello World Pass". namespace { struct Hello : public FunctionPass { + + static char ID; + Hello() : FunctionPass((intptr_t)&ID) {} + virtual bool runOnFunction(Function &F) { llvm::cerr << "Hello: " << F.getName() << "\n"; return false; } }; + char Hello::ID = 0; RegisterPass<Hello> X("hello", "Hello World Pass"); }To test it, follow the example at the end of the Getting Started Guide to compile "Hello World" to -LLVM. We can now run the bytecode file (hello.bc) for the program -through our transformation like this (or course, any bytecode file will +LLVM. We can now run the bitcode file (hello.bc) for the program +through our transformation like this (or course, any bitcode file will work):
- - - -@@ -346,7 +373,7 @@ interesting way, we just throw away the result of opt (sending it to $ opt -load ../../../Debug/lib/Hello.so --help OVERVIEW: llvm .bc -> .bc modular optimizer -USAGE: opt [options] <input bytecode> +USAGE: opt [options] <input bitcode> OPTIONS: Optimizations available: @@ -381,7 +408,7 @@ Hello: main Total Execution Time: 0.02 seconds (0.0479059 wall clock) ---User Time--- --System Time-- --User+System-- ---Wall Time--- --- Pass Name --- - 0.0100 (100.0%) 0.0000 ( 0.0%) 0.0100 ( 50.0%) 0.0402 ( 84.0%) Bytecode Writer + 0.0100 (100.0%) 0.0000 ( 0.0%) 0.0100 ( 50.0%) 0.0402 ( 84.0%) Bitcode Writer 0.0000 ( 0.0%) 0.0100 (100.0%) 0.0100 ( 50.0%) 0.0031 ( 6.4%) Dominator Set Construction 0.0000 ( 0.0%) 0.0000 ( 0.0%) 0.0000 ( 0.0%) 0.0013 ( 2.7%) Module Verifier 0.0000 ( 0.0%) 0.0000 ( 0.0%) 0.0000 ( 0.0%) 0.0033 ( 6.9%) Hello World Pass @@ -457,7 +484,9 @@ class is the most general of all superclasses that you can use. Deriving from ModulePass indicates that your pass uses the entire program as a unit, refering to function bodies in no predictable order, or adding and removing functions. Because nothing is known about the behavior of ModulePass -subclasses, no optimization can be done for their execution. +subclasses, no optimization can be done for their execution. A module pass +can use function level passes (e.g. dominators) using getAnalysis interface + getAnalysis<DominatorTree>(Function).To write a correct ModulePass subclass, derive from ModulePass and overload the runOnModule method with the @@ -509,7 +538,7 @@ href="#BasicBlockPass">BasicBlockPass, you should derive from
- ... not allowed to modify any Functions that are not in the current SCC.
-- ... allowed to inspect any Function's other than those in the +
- ... not allowed to inspect any Function's other than those in the current SCC and the direct callees of the SCC.
- ... required to preserve the current CallGraph object, updating it @@ -534,14 +563,14 @@ false if they didn't.
- virtual bool doInitialization(Module &M); + virtual bool doInitialization(CallGraph &CG);The doIninitialize method is allowed to do most of the things that @@ -573,14 +602,14 @@ otherwise.
+ + + +- virtual bool doFinalization(Module &M); + virtual bool doFinalization(CallGraph &CG);The doFinalization method is an infrequently used method that is @@ -687,6 +716,85 @@ program being compiled.
+ ++ + + + +All LoopPass execute on each loop in the function independent of +all of the other loops in the function. LoopPass processes loops in +loop nest order such that outer most loop is processed last.
+ +LoopPass subclasses are allowed to update loop nest using +LPPassManager interface. Implementing a loop pass is usually +straightforward. Looppass's may overload three virtual methods to +do their work. All these methods should return true if they modified the +program, or false if they didn't.
++ ++ + + + + ++ ++ virtual bool doInitialization(Loop *, LPPassManager &LPM); +The doInitialization method is designed to do simple initialization +type of stuff that does not depend on the functions being processed. The +doInitialization method call is not scheduled to overlap with any +other pass executions (thus it should be very fast). LPPassManager +interface should be used to access Function or Module level analysis +information.
+ ++ ++ + + + ++ virtual bool runOnLoop(Loop *, LPPassManager &LPM) = 0; ++ +
The runOnLoop method must be implemented by your subclass to do +the transformation or analysis work of your pass. As usual, a true value should +be returned if the function is modified. LPPassManager interface +should be used to update loop nest.
+ ++ ++ + ++ ++ virtual bool doFinalization(); +The doFinalization method is an infrequently used method that is +called when the pass framework has finished calling runOnLoop for every loop in the +program being compiled.
+ +The BasicBlockPass class @@ -1039,7 +1147,21 @@ runtime assertion failure if you attempt to get an analysis that you did not declare as required in your getAnalysisUsage implementation. This method can be called by your run* method implementation, or by any -other local method invoked by your run* method. +other local method invoked by your run* method. + +A module level pass can use function level analysis info using this interface. +For example: + +@@ -1291,8 +1414,8 @@ Module Pass Manager Module Verifier -- Dominator Set Construction -- Module Verifier - Bytecode Writer ---Bytecode Writer + Bitcode Writer +--Bitcode Writer+ ++ bool ModuleLevelPass::runOnModule(Module &M) { + ... + DominatorTree &DT = getAnalysis<DominatorTree>(Func); + ... + } +In above example, runOnFunction for DominatorTree is called by pass manager +before returning a reference to the desired pass.
If your pass is capable of updating analyses if they exist (e.g., @@ -1187,8 +1309,9 @@ no problem.
Here we show how the default implementation is specified (using the extra argument to the RegisterAnalysisGroup template). There must be exactly one default implementation available at all times for an Analysis Group to be -used. Here we declare that the BasicAliasAnalysis +used. Only default implementation can derive from ImmutablePass. +Here we declare that the + BasicAliasAnalysis pass is the default implementation for the interface.
This output shows us when passes are constructed and when the analysis @@ -1332,8 +1455,8 @@ Module Pass Manager Module Verifier -- Dominator Set Construction -- Module Verifier - Bytecode Writer ---Bytecode Writer + Bitcode Writer +--Bitcode Writer Hello: __main Hello: puts Hello: main @@ -1372,8 +1495,8 @@ Module Pass Manager Module Verifier -- Dominator Set Construction -- Module Verifier - Bytecode Writer ---Bytecode Writer + Bitcode Writer +--Bitcode Writer Hello: __main Hello: puts Hello: main @@ -1678,29 +1801,6 @@ Despite that, we have kept the LLVM passes SMP ready, and you should too.
- --Currently it is illegal for a ModulePass -to require a FunctionPass. This is because -there is only one instance of the FunctionPass object ever created, thus nowhere -to store information for all of the functions in the program at the same time. -Although this has come up a couple of times before, this has always been worked -around by factoring one big complicated pass into a global and an -interprocedural part, both of which are distinct. In the future, it would be -nice to have this though.
- -Note that it is no problem for a FunctionPass to require the results of a ModulePass, only the other way around.
- -