blob: 6d925c4a7e08800769a0b73e558cb83bbdd06c7a [file] [log] [blame]
Ruchira Sasanka683847f2001-07-24 17:14:13 +00001#include "llvm/Analysis/LiveVar/BBLiveVar.h"
Ruchira Sasankae27c3442001-08-20 21:12:49 +00002#include "llvm/Analysis/LiveVar/MethodLiveVarInfo.h"
3#include "llvm/CodeGen/MachineInstr.h"
4#include "llvm/CodeGen/Sparc.h"
Ruchira Sasanka683847f2001-07-24 17:14:13 +00005
6
7/********************* Implementation **************************************/
8
Ruchira Sasankae27c3442001-08-20 21:12:49 +00009BBLiveVar::BBLiveVar( const BasicBlock *const baseBB, unsigned int RdfoId)
10 : BaseBB(baseBB), DefSet(), InSet(),
11 OutSet(), PhiArgMap() {
Ruchira Sasanka683847f2001-07-24 17:14:13 +000012 BaseBB = baseBB;
13 InSetChanged = OutSetChanged = false;
14 POId = RdfoId;
15}
16
Ruchira Sasankae27c3442001-08-20 21:12:49 +000017// caluculates def and use sets for each BB
18// There are two passes over operands of a machine instruction. This is
19// because, we can have instructions like V = V + 1, since we no longer
20// assume single definition.
Ruchira Sasanka683847f2001-07-24 17:14:13 +000021
Ruchira Sasankae27c3442001-08-20 21:12:49 +000022void BBLiveVar::calcDefUseSets()
Ruchira Sasanka683847f2001-07-24 17:14:13 +000023{
Ruchira Sasankae27c3442001-08-20 21:12:49 +000024 // get the iterator for machine instructions
25 const MachineCodeForBasicBlock& MIVec = BaseBB->getMachineInstrVec();
26 MachineCodeForBasicBlock::const_reverse_iterator
27 MInstIterator = MIVec.rbegin();
Ruchira Sasanka683847f2001-07-24 17:14:13 +000028
Ruchira Sasankae27c3442001-08-20 21:12:49 +000029 // iterate over all the machine instructions in BB
30 for( ; MInstIterator != MIVec.rend(); ++MInstIterator) {
Ruchira Sasanka683847f2001-07-24 17:14:13 +000031
Ruchira Sasankae27c3442001-08-20 21:12:49 +000032 const MachineInstr * MInst = *MInstIterator; // MInst is the machine inst
33 assert(MInst);
Ruchira Sasanka683847f2001-07-24 17:14:13 +000034
Ruchira Sasankae27c3442001-08-20 21:12:49 +000035 if( DEBUG_LV > 1) { // debug msg
36 cout << " *Iterating over machine instr ";
37 MInst->dump();
38 cout << endl;
39 }
40
41 // iterate over MI operands to find defs
42 for( MachineInstr::val_op_const_iterator OpI(MInst); !OpI.done() ; ++OpI) {
43
44 const Value *Op = *OpI;
45
46 if( OpI.isDef() ) { // add to Defs only if this operand is a def
47
48 DefSet.add( Op ); // operand is a def - so add to def set
49 InSet.remove( Op); // this definition kills any uses
50 InSetChanged = true;
51
52 if( DEBUG_LV > 1) {
53 cout << " +Def: "; printValue( Op ); cout << endl;
54 }
55 }
56 }
57
58 bool IsPhi = ( MInst->getOpCode() == PHI );
59
60
61 // iterate over MI operands to find uses
62 for(MachineInstr::val_op_const_iterator OpI(MInst); !OpI.done() ; ++OpI) {
63 const Value *Op = *OpI;
64
65 if ( ((Op)->getType())->isLabelType() )
66 continue; // don't process labels
67
68 if(! OpI.isDef() ) { // add to Defs only if this operand is a use
69
70 InSet.add( Op ); // An operand is a use - so add to use set
71 OutSet.remove( Op ); // remove if there is a def below this use
72 InSetChanged = true;
73
74 if( DEBUG_LV > 1) { // debug msg of level 2
75 cout << " Use: "; printValue( Op ); cout << endl;
76 }
77
78 if( IsPhi ) { // for a phi node
79 // put args into the PhiArgMap (Val -> BB)
80
81 const Value * ArgVal = Op;
82 ++OpI; // increment to point to BB of value
83 const Value * BBVal = *OpI;
84
85
86 assert( (BBVal)->getValueType() == Value::BasicBlockVal );
87
88 PhiArgMap[ ArgVal ] = (const BasicBlock *) (BBVal);
89 assert( PhiArgMap[ ArgVal ] );
90
91 if( DEBUG_LV > 1) { // debug msg of level 2
92 cout << " - phi operand ";
93 printValue( ArgVal );
94 cout << " came from BB ";
95 printValue( PhiArgMap[ ArgVal ]);
96 cout<<endl;
97 }
98
99 }
100
101 }
102 }
103
104 } // for all machine instructions
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000105}
106
107
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000108
109bool BBLiveVar::applyTransferFunc() // calculates the InSet in terms of OutSet
110{
111
112 // IMPORTANT: caller should check whether the OutSet changed
113 // (else no point in calling)
114
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000115 LiveVarSet OutMinusDef; // set to hold (Out[B] - Def[B])
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000116 OutMinusDef.setDifference( &OutSet, &DefSet);
117 InSetChanged = InSet.setUnion( &OutMinusDef );
118
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000119 OutSetChanged = false; // no change to OutSet since transf func applied
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000120
121 return InSetChanged;
122}
123
124
125
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000126// calculates Out set using In sets of the predecessors
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000127bool BBLiveVar::setPropagate( LiveVarSet *const OutSet,
128 const LiveVarSet *const InSet,
129 const BasicBlock *const PredBB) {
130
131 LiveVarSet::const_iterator InIt;
132 pair<LiveVarSet::iterator, bool> result;
133 bool changed = false;
134 const BasicBlock *PredBBOfPhiArg;
135
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000136 // for all all elements in InSet
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000137 for( InIt = InSet->begin() ; InIt != InSet->end(); InIt++) {
138 PredBBOfPhiArg = PhiArgMap[ *InIt ];
139
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000140 // if this var is not a phi arg OR
141 // it's a phi arg and the var went down from this BB
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000142 if( !PredBBOfPhiArg || PredBBOfPhiArg == PredBB) {
143 result = OutSet->insert( *InIt ); // insert to this set
144 if( result.second == true) changed = true;
145 }
146 }
147
148 return changed;
149}
150
151
152
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000153// propogates in set to OutSets of PREDECESSORs
154
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000155bool BBLiveVar::applyFlowFunc(BBToBBLiveVarMapType LVMap)
156{
157
158 // IMPORTANT: caller should check whether inset changed
159 // (else no point in calling)
160
161 bool needAnotherIt= false; // did this BB change any OutSets of pred.s
162 // whose POId is lower
163
164
165 cfg::pred_const_iterator PredBBI = cfg::pred_begin(BaseBB);
166
167 for( ; PredBBI != cfg::pred_end(BaseBB) ; PredBBI++) {
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000168 assert( *PredBBI ); // assert that the predecessor is valid
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000169 BBLiveVar *PredLVBB = LVMap[*PredBBI];
170
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000171 // do set union
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000172 if( setPropagate( &(PredLVBB->OutSet), &InSet, *PredBBI ) == true) {
173 PredLVBB->OutSetChanged = true;
174
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000175 // if the predec POId is lower than mine
176 if( PredLVBB->getPOId() <= POId)
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000177 needAnotherIt = true;
178 }
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000179
180 } // for
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000181
182 return needAnotherIt;
183
184}
185
186
187
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000188/* ----------------- Methods For Debugging (Printing) ----------------- */
189
190void BBLiveVar::printAllSets() const
191{
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000192 cout << " Defs: "; DefSet.printSet(); cout << endl;
193 cout << " In: "; InSet.printSet(); cout << endl;
194 cout << " Out: "; OutSet.printSet(); cout << endl;
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000195}
196
197void BBLiveVar::printInOutSets() const
198{
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000199 cout << " In: "; InSet.printSet(); cout << endl;
200 cout << " Out: "; OutSet.printSet(); cout << endl;
Ruchira Sasanka683847f2001-07-24 17:14:13 +0000201}
Ruchira Sasankae27c3442001-08-20 21:12:49 +0000202
203
204
205