@@ -13,33 +13,36 @@ private import semmle.code.csharp.ir.internal.IRCSharpLanguage as Language
1313 * of a higher-level constructor (e.g. the allocator call in a `NewExpr`).
1414 */
1515abstract class TranslatedCall extends TranslatedExpr {
16- override final TranslatedElement getChild ( int id ) {
16+ final override TranslatedElement getChild ( int id ) {
1717 // We choose the child's id in the order of evaluation.
1818 // The qualifier is evaluated before the call target, because the value of
1919 // the call target may depend on the value of the qualifier for virtual
2020 // calls.
21- id = - 2 and result = getQualifier ( ) or
22- id = - 1 and result = getCallTarget ( ) or
21+ id = - 2 and result = getQualifier ( )
22+ or
23+ id = - 1 and result = getCallTarget ( )
24+ or
2325 result = getArgument ( id )
2426 }
2527
26- override final Instruction getFirstInstruction ( ) {
27- if exists ( getQualifier ( ) ) then
28- result = getQualifier ( ) .getFirstInstruction ( )
29- else
30- result = getFirstCallTargetInstruction ( )
28+ final override Instruction getFirstInstruction ( ) {
29+ if exists ( getQualifier ( ) )
30+ then result = getQualifier ( ) .getFirstInstruction ( )
31+ else result = getFirstCallTargetInstruction ( )
3132 }
3233
33- override predicate hasInstruction ( Opcode opcode , InstructionTag tag ,
34- Type resultType , boolean isLValue ) {
35- (
36- tag = CallTag ( ) and
37- opcode instanceof Opcode:: Call and
38- resultType = getCallResultType ( ) and
39- isLValue = false
40- ) or
41- // TODO: Fix side effects,
34+ override predicate hasInstruction (
35+ Opcode opcode , InstructionTag tag , Type resultType , boolean isLValue
36+ ) {
37+ tag = CallTag ( ) and
38+ opcode instanceof Opcode:: Call and
39+ resultType = getCallResultType ( ) and
40+ isLValue = false
41+ or
42+ // TODO: Fix side effects,
4243 // understand why CallSideEffect breaks things if it is not present
44+ hasSideEffect ( ) and
45+ tag = CallSideEffectTag ( ) and
4346 (
4447 hasSideEffect ( ) and
4548 tag = CallSideEffectTag ( ) and
@@ -56,82 +59,67 @@ abstract class TranslatedCall extends TranslatedExpr {
5659 isLValue = false
5760 )
5861 }
59-
62+
6063 override Instruction getChildSuccessor ( TranslatedElement child ) {
61- (
62- child = getQualifier ( ) and
63- result = getFirstCallTargetInstruction ( )
64- ) or
65- (
66- child = getCallTarget ( ) and
67- result = getFirstArgumentOrCallInstruction ( )
68- ) or
64+ child = getQualifier ( ) and
65+ result = getFirstCallTargetInstruction ( )
66+ or
67+ child = getCallTarget ( ) and
68+ result = getFirstArgumentOrCallInstruction ( )
69+ or
6970 exists ( int argIndex |
7071 child = getArgument ( argIndex ) and
71- if exists ( getArgument ( argIndex + 1 ) ) then
72- result = getArgument ( argIndex + 1 ) .getFirstInstruction ( )
73- else
74- result = getInstruction ( CallTag ( ) )
72+ if exists ( getArgument ( argIndex + 1 ) )
73+ then result = getArgument ( argIndex + 1 ) .getFirstInstruction ( )
74+ else result = getInstruction ( CallTag ( ) )
7575 )
7676 }
7777
78- override Instruction getInstructionSuccessor ( InstructionTag tag ,
79- EdgeKind kind ) {
78+ override Instruction getInstructionSuccessor ( InstructionTag tag , EdgeKind kind ) {
8079 kind instanceof GotoEdge and
8180 (
8281 (
8382 tag = CallTag ( ) and
84- if hasSideEffect ( ) then
85- result = getInstruction ( CallSideEffectTag ( ) )
86- else
87- result = getParent ( ) .getChildSuccessor ( this )
88- ) or
89- (
90- hasSideEffect ( ) and
91- tag = CallSideEffectTag ( ) and
92- result = getParent ( ) .getChildSuccessor ( this )
83+ if hasSideEffect ( )
84+ then result = getInstruction ( CallSideEffectTag ( ) )
85+ else result = getParent ( ) .getChildSuccessor ( this )
9386 )
87+ or
88+ hasSideEffect ( ) and
89+ tag = CallSideEffectTag ( ) and
90+ result = getParent ( ) .getChildSuccessor ( this )
9491 )
9592 }
9693
97- override Instruction getInstructionOperand ( InstructionTag tag ,
98- OperandTag operandTag ) {
94+ override Instruction getInstructionOperand ( InstructionTag tag , OperandTag operandTag ) {
95+ tag = CallTag ( ) and
9996 (
100- tag = CallTag ( ) and
101- (
102- (
103- operandTag instanceof CallTargetOperandTag and
104- result = getCallTargetResult ( )
105- ) or
106- (
107- operandTag instanceof ThisArgumentOperandTag and
108- result = getQualifierResult ( )
109- ) or
110- exists ( PositionalArgumentOperandTag argTag |
111- argTag = operandTag and
112- result = getArgument ( argTag .getArgIndex ( ) ) .getResult ( )
113- )
97+ operandTag instanceof CallTargetOperandTag and
98+ result = getCallTargetResult ( )
99+ or
100+ operandTag instanceof ThisArgumentOperandTag and
101+ result = getQualifierResult ( )
102+ or
103+ exists ( PositionalArgumentOperandTag argTag |
104+ argTag = operandTag and
105+ result = getArgument ( argTag .getArgIndex ( ) ) .getResult ( )
114106 )
115- ) or
116- (
117- tag = CallSideEffectTag ( ) and
118- hasSideEffect ( ) and
119- operandTag instanceof SideEffectOperandTag and
120- result = getEnclosingFunction ( ) .getUnmodeledDefinitionInstruction ( )
121107 )
108+ or
109+ tag = CallSideEffectTag ( ) and
110+ hasSideEffect ( ) and
111+ operandTag instanceof SideEffectOperandTag and
112+ result = getEnclosingFunction ( ) .getUnmodeledDefinitionInstruction ( )
122113 }
123114
124- override final Type getInstructionOperandType ( InstructionTag tag ,
125- TypedOperandTag operandTag ) {
115+ final override Type getInstructionOperandType ( InstructionTag tag , TypedOperandTag operandTag ) {
126116 tag = CallSideEffectTag ( ) and
127117 hasSideEffect ( ) and
128118 operandTag instanceof SideEffectOperandTag and
129119 result instanceof Language:: UnknownType
130120 }
131121
132- override final Instruction getResult ( ) {
133- result = getInstruction ( CallTag ( ) )
134- }
122+ final override Instruction getResult ( ) { result = getInstruction ( CallTag ( ) ) }
135123
136124 /**
137125 * Gets the result type of the call.
@@ -141,36 +129,28 @@ abstract class TranslatedCall extends TranslatedExpr {
141129 /**
142130 * Holds if the call has a `this` argument.
143131 */
144- predicate hasQualifier ( ) {
145- exists ( getQualifier ( ) )
146- }
132+ predicate hasQualifier ( ) { exists ( getQualifier ( ) ) }
147133
148134 /**
149135 * Gets the `TranslatedExpr` for the indirect target of the call, if any.
150136 */
151- TranslatedExpr getCallTarget ( ) {
152- none ( )
153- }
137+ TranslatedExpr getCallTarget ( ) { none ( ) }
154138
155139 /**
156140 * Gets the first instruction of the sequence to evaluate the call target.
157141 * By default, this is just the first instruction of `getCallTarget()`, but
158142 * it can be overridden by a subclass for cases where there is a call target
159143 * that is not computed from an expression (e.g. a direct call).
160144 */
161- Instruction getFirstCallTargetInstruction ( ) {
162- result = getCallTarget ( ) .getFirstInstruction ( )
163- }
145+ Instruction getFirstCallTargetInstruction ( ) { result = getCallTarget ( ) .getFirstInstruction ( ) }
164146
165147 /**
166148 * Gets the instruction whose result value is the target of the call. By
167149 * default, this is just the result of `getCallTarget()`, but it can be
168150 * overridden by a subclass for cases where there is a call target that is not
169151 * computed from an expression (e.g. a direct call).
170152 */
171- Instruction getCallTargetResult ( ) {
172- result = getCallTarget ( ) .getResult ( )
173- }
153+ Instruction getCallTargetResult ( ) { result = getCallTarget ( ) .getResult ( ) }
174154
175155 /**
176156 * Gets the `TranslatedExpr` for the qualifier of the call (i.e. the value
@@ -184,9 +164,7 @@ abstract class TranslatedCall extends TranslatedExpr {
184164 * overridden by a subclass for cases where there is a `this` argument that is
185165 * not computed from a child expression (e.g. a constructor call).
186166 */
187- Instruction getQualifierResult ( ) {
188- result = getQualifier ( ) .getResult ( )
189- }
167+ Instruction getQualifierResult ( ) { result = getQualifier ( ) .getResult ( ) }
190168
191169 /**
192170 * Gets the argument with the specified `index`. Does not include the `this`
@@ -199,10 +177,9 @@ abstract class TranslatedCall extends TranslatedExpr {
199177 * argument. Otherwise, returns the call instruction.
200178 */
201179 final Instruction getFirstArgumentOrCallInstruction ( ) {
202- if hasArguments ( ) then
203- result = getArgument ( 0 ) .getFirstInstruction ( )
204- else
205- result = getInstruction ( CallTag ( ) )
180+ if hasArguments ( )
181+ then result = getArgument ( 0 ) .getFirstInstruction ( )
182+ else result = getInstruction ( CallTag ( ) )
206183 }
207184
208185 /**
@@ -211,22 +188,16 @@ abstract class TranslatedCall extends TranslatedExpr {
211188 abstract predicate hasArguments ( ) ;
212189
213190 // TODO: Fix side effects
214- predicate hasReadSideEffect ( ) {
215- any ( )
216- }
191+ predicate hasReadSideEffect ( ) { any ( ) }
217192
218- predicate hasWriteSideEffect ( ) {
219- any ( )
220- }
193+ predicate hasWriteSideEffect ( ) { any ( ) }
221194
222- private predicate hasSideEffect ( ) {
223- hasReadSideEffect ( ) or hasWriteSideEffect ( )
224- }
195+ private predicate hasSideEffect ( ) { hasReadSideEffect ( ) or hasWriteSideEffect ( ) }
225196
226197 override Instruction getPrimaryInstructionForSideEffect ( InstructionTag tag ) {
227- hasSideEffect ( ) and
228- tag = CallSideEffectTag ( ) and
229- result = getResult ( )
198+ hasSideEffect ( ) and
199+ tag = CallSideEffectTag ( ) and
200+ result = getResult ( )
230201 }
231202}
232203
@@ -236,58 +207,45 @@ abstract class TranslatedCall extends TranslatedExpr {
236207 * (`TranslatedAllocatorCall`).
237208 */
238209abstract class TranslatedDirectCall extends TranslatedCall {
239- override final Instruction getFirstCallTargetInstruction ( ) {
210+ final override Instruction getFirstCallTargetInstruction ( ) {
240211 result = getInstruction ( CallTargetTag ( ) )
241212 }
242213
243- override final Instruction getCallTargetResult ( ) {
244- result = getInstruction ( CallTargetTag ( ) )
245- }
214+ final override Instruction getCallTargetResult ( ) { result = getInstruction ( CallTargetTag ( ) ) }
246215
247- override predicate hasInstruction ( Opcode opcode , InstructionTag tag ,
248- Type resultType , boolean isLValue ) {
249- TranslatedCall . super . hasInstruction ( opcode , tag , resultType , isLValue ) or
250- (
251- tag = CallTargetTag ( ) and
252- opcode instanceof Opcode :: FunctionAddress and
253- resultType = expr . getType ( ) and
254- isLValue = true
255- )
216+ override predicate hasInstruction (
217+ Opcode opcode , InstructionTag tag , Type resultType , boolean isLValue
218+ ) {
219+ TranslatedCall . super . hasInstruction ( opcode , tag , resultType , isLValue )
220+ or
221+ tag = CallTargetTag ( ) and
222+ opcode instanceof Opcode :: FunctionAddress and
223+ resultType = expr . getType ( ) and
224+ isLValue = true
256225 }
257-
258- override Instruction getInstructionSuccessor ( InstructionTag tag ,
259- EdgeKind kind ) {
260- result = TranslatedCall .super .getInstructionSuccessor ( tag , kind ) or
261- (
262- tag = CallTargetTag ( ) and
263- kind instanceof GotoEdge and
264- result = getFirstArgumentOrCallInstruction ( )
265- )
226+
227+ override Instruction getInstructionSuccessor ( InstructionTag tag , EdgeKind kind ) {
228+ result = TranslatedCall .super .getInstructionSuccessor ( tag , kind )
229+ or
230+ tag = CallTargetTag ( ) and
231+ kind instanceof GotoEdge and
232+ result = getFirstArgumentOrCallInstruction ( )
266233 }
267234}
268235
269236/**
270237 * The IR translation of a call to a function.
271238 */
272- abstract class TranslatedCallExpr extends TranslatedNonConstantExpr ,
273- TranslatedCall {
239+ abstract class TranslatedCallExpr extends TranslatedNonConstantExpr , TranslatedCall {
274240 override Call expr ;
275241
276- override final Type getCallResultType ( ) {
277- result = getResultType ( )
278- }
242+ final override Type getCallResultType ( ) { result = getResultType ( ) }
279243
280- override final predicate hasArguments ( ) {
281- exists ( expr .getArgument ( 0 ) )
282- }
244+ final override predicate hasArguments ( ) { exists ( expr .getArgument ( 0 ) ) }
283245
284- override final TranslatedExpr getQualifier ( ) {
285- // TODO: Was getQualifier in the C++ implementation, make sure
286- // meaning is kept
287- result = getTranslatedExpr ( expr .getChild ( - 1 ) )
288- }
246+ final override TranslatedExpr getQualifier ( ) { none ( ) }
289247
290- override final TranslatedExpr getArgument ( int index ) {
248+ final override TranslatedExpr getArgument ( int index ) {
291249 result = getTranslatedExpr ( expr .getArgument ( index ) )
292250 }
293251}
@@ -312,12 +270,12 @@ class TranslatedFunctionCall extends TranslatedCallExpr, TranslatedDirectCall {
312270}
313271
314272/**
315- * Represents the IR translation of a call to a constructor (can't call destructor explicitly in C#.
273+ * Represents the IR translation of a call to a constructor.
274+ * The target of the call is a newly allocated object whose address, after
275+ * the constructor call, address will be passed to a variable declaration.
316276 */
317277class TranslatedConstructorCall extends TranslatedFunctionCall {
318- TranslatedConstructorCall ( ) {
319- expr instanceof ObjectCreation
320- }
278+ TranslatedConstructorCall ( ) { expr instanceof ObjectCreation }
321279
322280 override Instruction getQualifierResult ( ) {
323281 exists ( StructorCallContext context |
@@ -326,7 +284,5 @@ class TranslatedConstructorCall extends TranslatedFunctionCall {
326284 )
327285 }
328286
329- override predicate hasQualifier ( ) {
330- any ( )
331- }
287+ override predicate hasQualifier ( ) { any ( ) }
332288}
0 commit comments