@@ -7,60 +7,21 @@ private import NewIR
77private class OldBlock = Reachability:: ReachableBlock ;
88private class OldInstruction = Reachability:: ReachableInstruction ;
99
10- InstructionTag getInstructionTag ( Instruction instruction ) {
11- instruction = MkInstruction ( _, _, _, result , _, _)
12- }
13-
14- Locatable getInstructionAST ( Instruction instruction ) {
15- instruction = MkInstruction ( _, _, result , _, _, _)
16- }
17-
18- predicate instructionHasType ( Instruction instruction , Type type , boolean isGLValue ) {
19- instruction = MkInstruction ( _, _, _, _, type , isGLValue )
20- }
21-
22- Opcode getInstructionOpcode ( Instruction instruction ) {
23- instruction = MkInstruction ( _, result , _, _, _, _)
24- }
25-
26- FunctionIR getInstructionEnclosingFunctionIR ( Instruction instruction ) {
27- instruction = MkInstruction ( result , _, _, _, _, _)
28- }
29-
3010import Cached
3111cached private module Cached {
3212
3313 private IRBlock getNewBlock ( OldBlock oldBlock ) {
3414 result .getFirstInstruction ( ) = getNewInstruction ( oldBlock .getFirstInstruction ( ) )
3515 }
3616
37- cached newtype TInstructionTag =
38- WrappedInstructionTag ( OldInstruction oldInstruction ) {
39- not oldInstruction instanceof OldIR:: PhiInstruction
40- } or
41- PhiTag ( Alias:: VirtualVariable vvar , OldBlock block ) {
42- hasPhiNode ( vvar , block )
43- } or
44- ChiTag ( OldInstruction oldInstruction ) {
45- not oldInstruction instanceof OldIR:: PhiInstruction and
46- hasChiNode ( _, oldInstruction )
47- } or
48- UnreachedTag ( )
49-
50- cached class InstructionTagType extends TInstructionTag {
51- cached final string toString ( ) {
52- result = "Tag"
53- }
54- }
55-
5617 cached predicate functionHasIR ( Function func ) {
5718 exists ( OldIR:: FunctionIR funcIR |
5819 funcIR .getFunction ( ) = func
5920 )
6021 }
6122
6223 cached OldInstruction getOldInstruction ( Instruction instr ) {
63- instr . getTag ( ) = WrappedInstructionTag ( result )
24+ instr = WrappedInstruction ( result )
6425 }
6526
6627 private Instruction getNewInstruction ( OldInstruction instr ) {
@@ -72,24 +33,12 @@ cached private module Cached {
7233 * corresponding to `instr` if there is no `Chi` node.
7334 */
7435 private Instruction getNewFinalInstruction ( OldInstruction instr ) {
75- result = getChiInstruction ( instr )
36+ result = Chi ( instr )
7637 or
77- not exists ( getChiInstruction ( instr ) ) and
38+ not exists ( Chi ( instr ) ) and
7839 result = getNewInstruction ( instr )
7940 }
8041
81- private PhiInstruction getPhiInstruction ( Function func , OldBlock oldBlock ,
82- Alias:: VirtualVariable vvar ) {
83- result .getFunction ( ) = func and
84- result .getAST ( ) = oldBlock .getFirstInstruction ( ) .getAST ( ) and
85- result .getTag ( ) = PhiTag ( vvar , oldBlock )
86- }
87-
88- private ChiInstruction getChiInstruction ( OldInstruction instr ) {
89- hasChiNode ( _, instr ) and
90- result .getTag ( ) = ChiTag ( instr )
91- }
92-
9342 private IRVariable getNewIRVariable ( OldIR:: IRVariable var ) {
9443 result .getFunction ( ) = var .getFunction ( ) and
9544 (
@@ -108,54 +57,23 @@ cached private module Cached {
10857 }
10958
11059 cached newtype TInstruction =
111- MkInstruction ( FunctionIR funcIR , Opcode opcode , Locatable ast ,
112- InstructionTag tag , Type resultType , boolean isGLValue ) {
113- hasInstruction ( funcIR .getFunction ( ) , opcode , ast , tag ,
114- resultType , isGLValue )
60+ WrappedInstruction ( OldInstruction oldInstruction ) {
61+ not oldInstruction instanceof OldIR:: PhiInstruction
62+ } or
63+ Phi ( OldBlock block , Alias:: VirtualVariable vvar ) {
64+ hasPhiNode ( vvar , block )
65+ } or
66+ Chi ( OldInstruction oldInstruction ) {
67+ not oldInstruction instanceof OldIR:: PhiInstruction and
68+ hasChiNode ( _, oldInstruction )
69+ } or
70+ Unreached ( Function function ) {
71+ exists ( OldInstruction oldInstruction |
72+ function = oldInstruction .getFunction ( ) and
73+ Reachability:: isInfeasibleInstructionSuccessor ( oldInstruction , _)
74+ )
11575 }
11676
117- private predicate hasInstruction ( Function func , Opcode opcode , Locatable ast ,
118- InstructionTag tag , Type resultType , boolean isGLValue ) {
119- exists ( OldInstruction instr |
120- instr .getFunction ( ) = func and
121- instr .getOpcode ( ) = opcode and
122- instr .getAST ( ) = ast and
123- WrappedInstructionTag ( instr ) = tag and
124- instr .getResultType ( ) = resultType and
125- if instr .isGLValue ( ) then
126- isGLValue = true
127- else
128- isGLValue = false
129- ) or
130- exists ( OldBlock block , Alias:: VirtualVariable vvar |
131- hasPhiNode ( vvar , block ) and
132- block .getFunction ( ) = func and
133- opcode instanceof Opcode:: Phi and
134- ast = block .getFirstInstruction ( ) .getAST ( ) and
135- tag = PhiTag ( vvar , block ) and
136- resultType = vvar .getType ( ) and
137- isGLValue = false
138- ) or
139- exists ( OldInstruction instr , Alias:: VirtualVariable vvar |
140- hasChiNode ( vvar , instr ) and
141- instr .getFunction ( ) = func and
142- opcode instanceof Opcode:: Chi and
143- ast = instr .getAST ( ) and
144- tag = ChiTag ( instr ) and
145- resultType = vvar .getType ( ) and
146- isGLValue = false
147- ) or
148- exists ( OldInstruction oldInstruction |
149- func = oldInstruction .getFunction ( ) and
150- Reachability:: isInfeasibleInstructionSuccessor ( oldInstruction , _) and
151- tag = UnreachedTag ( ) and
152- opcode instanceof Opcode:: Unreached and
153- ast = func and
154- resultType instanceof VoidType and
155- isGLValue = false
156- )
157- }
158-
15977 cached predicate hasTempVariable ( Function func , Locatable ast , TempVariableTag tag ,
16078 Type type ) {
16179 exists ( OldIR:: IRTempVariable var |
@@ -189,7 +107,7 @@ cached private module Cached {
189107 if defIndex >= 0 then
190108 result = getNewFinalInstruction ( defBlock .getInstruction ( defIndex ) )
191109 else
192- result = getPhiInstruction ( instruction . getFunction ( ) , defBlock , vvar )
110+ result = Phi ( defBlock , vvar )
193111 )
194112 )
195113 else (
@@ -209,7 +127,7 @@ cached private module Cached {
209127 else
210128 result = getNewInstruction ( oldOperand .getDefinitionInstruction ( ) )
211129 ) or
212- instruction . getTag ( ) = ChiTag ( getOldInstruction ( result ) ) and
130+ instruction = Chi ( getOldInstruction ( result ) ) and
213131 tag instanceof ChiPartialOperandTag
214132 or
215133 exists ( FunctionIR f |
@@ -228,35 +146,35 @@ cached private module Cached {
228146 OldBlock defBlock , int defRank , int defIndex , OldBlock predBlock |
229147 hasPhiNode ( vvar , phiBlock ) and
230148 predBlock = phiBlock .getAFeasiblePredecessor ( ) and
231- instr . getTag ( ) = PhiTag ( vvar , phiBlock ) and
149+ instr = Phi ( phiBlock , vvar ) and
232150 newPredecessorBlock = getNewBlock ( predBlock ) and
233151 hasDefinitionAtRank ( vvar , defBlock , defRank , defIndex ) and
234152 definitionReachesEndOfBlock ( vvar , defBlock , defRank , predBlock ) and
235153 if defIndex >= 0 then
236154 result = getNewFinalInstruction ( defBlock .getInstruction ( defIndex ) )
237155 else
238- result = getPhiInstruction ( instr . getFunction ( ) , defBlock , vvar )
156+ result = Phi ( defBlock , vvar )
239157 )
240158 }
241159
242160 cached Instruction getChiInstructionTotalOperand ( ChiInstruction chiInstr ) {
243161 exists ( Alias:: VirtualVariable vvar , OldInstruction oldInstr , OldBlock defBlock ,
244162 int defRank , int defIndex , OldBlock useBlock , int useRank |
245- ChiTag ( oldInstr ) = chiInstr . getTag ( ) and
163+ chiInstr = Chi ( oldInstr ) and
246164 vvar = Alias:: getResultMemoryAccess ( oldInstr ) .getVirtualVariable ( ) and
247165 hasDefinitionAtRank ( vvar , defBlock , defRank , defIndex ) and
248166 hasUseAtRank ( vvar , useBlock , useRank , oldInstr ) and
249167 definitionReachesUse ( vvar , defBlock , defRank , useBlock , useRank ) and
250168 if defIndex >= 0 then
251169 result = getNewFinalInstruction ( defBlock .getInstruction ( defIndex ) )
252170 else
253- result = getPhiInstruction ( chiInstr . getFunction ( ) , defBlock , vvar )
171+ result = Phi ( defBlock , vvar )
254172 )
255173 }
256174
257175 cached Instruction getPhiInstructionBlockStart ( PhiInstruction instr ) {
258176 exists ( OldBlock oldBlock |
259- instr . getTag ( ) = PhiTag ( _ , oldBlock ) and
177+ instr = Phi ( oldBlock , _ ) and
260178 result = getNewInstruction ( oldBlock .getFirstInstruction ( ) )
261179 )
262180 }
@@ -277,23 +195,22 @@ cached private module Cached {
277195 cached Instruction getInstructionSuccessor ( Instruction instruction , EdgeKind kind ) {
278196 if ( hasChiNode ( _, getOldInstruction ( instruction ) ) )
279197 then
280- result = getChiInstruction ( getOldInstruction ( instruction ) ) and
198+ result = Chi ( getOldInstruction ( instruction ) ) and
281199 kind instanceof GotoEdge
282200 else (
283201 exists ( OldInstruction oldInstruction |
284202 oldInstruction = getOldInstruction ( instruction ) and
285203 (
286204 if Reachability:: isInfeasibleInstructionSuccessor ( oldInstruction , kind ) then (
287- result .getTag ( ) = UnreachedTag ( ) and
288- result .getFunction ( ) = instruction .getFunction ( )
205+ result = Unreached ( instruction .getFunction ( ) )
289206 )
290207 else (
291208 result = getNewInstruction ( oldInstruction .getSuccessor ( kind ) )
292209 )
293210 )
294211 ) or
295212 exists ( OldInstruction oldInstruction |
296- instruction = getChiInstruction ( oldInstruction ) and
213+ instruction = Chi ( oldInstruction ) and
297214 result = getNewInstruction ( oldInstruction .getSuccessor ( kind ) )
298215 )
299216 )
@@ -311,11 +228,88 @@ cached private module Cached {
311228 // `oldInstruction`, in which case the back edge should come out of the
312229 // chi node instead.
313230 if hasChiNode ( _, oldInstruction )
314- then instruction = getChiInstruction ( oldInstruction )
231+ then instruction = Chi ( oldInstruction )
315232 else instruction = getNewInstruction ( oldInstruction )
316233 )
317234 }
318235
236+ cached Locatable getInstructionAST ( Instruction instruction ) {
237+ exists ( OldInstruction oldInstruction |
238+ instruction = WrappedInstruction ( oldInstruction )
239+ or
240+ instruction = Chi ( oldInstruction )
241+ |
242+ result = oldInstruction .getAST ( )
243+ )
244+ or
245+ exists ( OldBlock block |
246+ instruction = Phi ( block , _) and
247+ result = block .getFirstInstruction ( ) .getAST ( )
248+ )
249+ or
250+ instruction = Unreached ( result )
251+ }
252+
253+ cached predicate instructionHasType ( Instruction instruction , Type type , boolean isGLValue ) {
254+ exists ( OldInstruction oldInstruction |
255+ instruction = WrappedInstruction ( oldInstruction ) and
256+ type = oldInstruction .getResultType ( ) and
257+ if oldInstruction .isGLValue ( )
258+ then isGLValue = true
259+ else isGLValue = false
260+ )
261+ or
262+ exists ( OldInstruction oldInstruction , Alias:: VirtualVariable vvar |
263+ instruction = Chi ( oldInstruction ) and
264+ hasChiNode ( vvar , oldInstruction ) and
265+ type = vvar .getType ( ) and
266+ isGLValue = false
267+ )
268+ or
269+ exists ( Alias:: VirtualVariable vvar |
270+ instruction = Phi ( _, vvar ) and
271+ type = vvar .getType ( ) and
272+ isGLValue = false
273+ )
274+ or
275+ instruction = Unreached ( _) and
276+ type instanceof VoidType and
277+ isGLValue = false
278+ }
279+
280+ cached Opcode getInstructionOpcode ( Instruction instruction ) {
281+ exists ( OldInstruction oldInstruction |
282+ instruction = WrappedInstruction ( oldInstruction ) and
283+ result = oldInstruction .getOpcode ( )
284+ )
285+ or
286+ instruction instanceof Chi and
287+ result instanceof Opcode:: Chi
288+ or
289+ instruction instanceof Phi and
290+ result instanceof Opcode:: Phi
291+ or
292+ instruction instanceof Unreached and
293+ result instanceof Opcode:: Unreached
294+ }
295+
296+ cached FunctionIR getInstructionEnclosingFunctionIR ( Instruction instruction ) {
297+ exists ( OldInstruction oldInstruction |
298+ instruction = WrappedInstruction ( oldInstruction )
299+ or
300+ instruction = Chi ( oldInstruction )
301+ |
302+ result .getFunction ( ) = oldInstruction .getFunction ( )
303+ )
304+ or
305+ exists ( OldBlock block |
306+ instruction = Phi ( block , _) and
307+ result .getFunction ( ) = block .getFunction ( )
308+ )
309+ or
310+ instruction = Unreached ( result .getFunction ( ) )
311+ }
312+
319313 cached IRVariable getInstructionVariable ( Instruction instruction ) {
320314 result = getNewIRVariable ( getOldInstruction ( instruction ) .( OldIR:: VariableInstruction ) .getVariable ( ) )
321315 }
@@ -366,7 +360,7 @@ cached private module Cached {
366360 )
367361 or
368362 exists ( OldIR:: Instruction oldInstruction |
369- instruction . getTag ( ) = ChiTag ( oldInstruction ) and
363+ instruction = Chi ( oldInstruction ) and
370364 result = getNewInstruction ( oldInstruction )
371365 )
372366 }
@@ -555,11 +549,11 @@ cached private module CachedForDebugging {
555549 result = "NonSSA: " + oldInstr .getUniqueId ( )
556550 ) or
557551 exists ( Alias:: VirtualVariable vvar , OldBlock phiBlock |
558- instr . getTag ( ) = PhiTag ( vvar , phiBlock ) and
552+ instr = Phi ( phiBlock , vvar ) and
559553 result = "Phi Block(" + phiBlock .getUniqueId ( ) + "): " + vvar .getUniqueId ( )
560554 ) or
561555 (
562- instr . getTag ( ) = UnreachedTag ( ) and
556+ instr = Unreached ( _ ) and
563557 result = "Unreached"
564558 )
565559 }
0 commit comments