1
1
/**
2
2
* Provides different types of control flow successor types. These are used as
3
3
* edge labels in the control flow graph.
4
- */
5
- overlay [ local]
6
- module ;
7
-
8
- private import codeql.util.Boolean
9
-
10
- /*
4
+ *
5
+ * ```text
11
6
* SuccessorType
12
7
* |- NormalSuccessor
13
8
* | |- DirectSuccessor
@@ -25,9 +20,13 @@ private import codeql.util.Boolean
25
20
* |- ContinueSuccessor
26
21
* |- GotoSuccessor
27
22
* |- RedoSuccessor // rare, used in Ruby
28
- * | - RetrySuccessor // rare, used in Ruby
29
- * \- JavaYieldSuccessor
23
+ * \ - RetrySuccessor // rare, used in Ruby
24
+ * ```
30
25
*/
26
+ overlay [ local]
27
+ module ;
28
+
29
+ private import codeql.util.Boolean
31
30
32
31
private newtype TSuccessorType =
33
32
TDirectSuccessor( ) or
@@ -42,8 +41,7 @@ private newtype TSuccessorType =
42
41
TContinueSuccessor( ) or
43
42
TGotoSuccessor( ) or
44
43
TRedoSuccessor( ) or
45
- TRetrySuccessor( ) or
46
- TJavaYieldSuccessor( )
44
+ TRetrySuccessor( )
47
45
48
46
/**
49
47
* The type of a control flow successor.
@@ -52,21 +50,25 @@ private newtype TSuccessorType =
52
50
* successors, or abrupt, which covers all other types of successors including
53
51
* for example exceptions, returns, and other jumps.
54
52
*/
55
- class SuccessorType extends TSuccessorType {
53
+ private class SuccessorTypeImpl extends TSuccessorType {
56
54
/** Gets a textual representation of this successor type. */
57
55
abstract string toString ( ) ;
58
56
}
59
57
58
+ final class SuccessorType = SuccessorTypeImpl ;
59
+
60
60
private class TNormalSuccessor = TDirectSuccessor or TConditionalSuccessor ;
61
61
62
62
/**
63
63
* A normal control flow successor. This is either a direct or a conditional
64
64
* successor.
65
65
*/
66
- abstract class NormalSuccessor extends SuccessorType , TNormalSuccessor { }
66
+ abstract private class NormalSuccessorImpl extends SuccessorTypeImpl , TNormalSuccessor { }
67
+
68
+ final class NormalSuccessor = NormalSuccessorImpl ;
67
69
68
70
/** A direct control flow successor. */
69
- class DirectSuccessor extends NormalSuccessor , TDirectSuccessor {
71
+ class DirectSuccessor extends NormalSuccessorImpl , TDirectSuccessor {
70
72
override string toString ( ) { result = "successor" }
71
73
}
72
74
@@ -78,11 +80,13 @@ private class TConditionalSuccessor =
78
80
* a nullness successor (`NullnessSuccessor`), a matching successor (`MatchingSuccessor`),
79
81
* or an emptiness successor (`EmptinessSuccessor`).
80
82
*/
81
- abstract class ConditionalSuccessor extends NormalSuccessor , TConditionalSuccessor {
83
+ abstract private class ConditionalSuccessorImpl extends NormalSuccessorImpl , TConditionalSuccessor {
82
84
/** Gets the Boolean value of this successor. */
83
85
abstract boolean getValue ( ) ;
84
86
}
85
87
88
+ final class ConditionalSuccessor = ConditionalSuccessorImpl ;
89
+
86
90
/**
87
91
* A Boolean control flow successor.
88
92
*
@@ -97,7 +101,7 @@ abstract class ConditionalSuccessor extends NormalSuccessor, TConditionalSuccess
97
101
*
98
102
* has a control flow graph containing Boolean successors:
99
103
*
100
- * ```
104
+ * ```text
101
105
* if
102
106
* |
103
107
* x < 0
@@ -109,7 +113,7 @@ abstract class ConditionalSuccessor extends NormalSuccessor, TConditionalSuccess
109
113
* return 0 return 1
110
114
* ```
111
115
*/
112
- class BooleanSuccessor extends ConditionalSuccessor , TBooleanSuccessor {
116
+ class BooleanSuccessor extends ConditionalSuccessorImpl , TBooleanSuccessor {
113
117
override boolean getValue ( ) { this = TBooleanSuccessor ( result ) }
114
118
115
119
override string toString ( ) { result = this .getValue ( ) .toString ( ) }
@@ -126,7 +130,7 @@ class BooleanSuccessor extends ConditionalSuccessor, TBooleanSuccessor {
126
130
*
127
131
* has a control flow graph containing nullness successors:
128
132
*
129
- * ```
133
+ * ```text
130
134
* enter M
131
135
* |
132
136
* s
@@ -141,7 +145,7 @@ class BooleanSuccessor extends ConditionalSuccessor, TBooleanSuccessor {
141
145
* exit M
142
146
* ```
143
147
*/
144
- class NullnessSuccessor extends ConditionalSuccessor , TNullnessSuccessor {
148
+ class NullnessSuccessor extends ConditionalSuccessorImpl , TNullnessSuccessor {
145
149
/** Holds if this is a `null` successor. */
146
150
predicate isNull ( ) { this = TNullnessSuccessor ( true ) }
147
151
@@ -166,7 +170,7 @@ class NullnessSuccessor extends ConditionalSuccessor, TNullnessSuccessor {
166
170
*
167
171
* has a control flow graph containing matching successors:
168
172
*
169
- * ```
173
+ * ```text
170
174
* switch
171
175
* |
172
176
* x
@@ -182,7 +186,7 @@ class NullnessSuccessor extends ConditionalSuccessor, TNullnessSuccessor {
182
186
* return 1
183
187
* ```
184
188
*/
185
- class MatchingSuccessor extends ConditionalSuccessor , TMatchingSuccessor {
189
+ class MatchingSuccessor extends ConditionalSuccessorImpl , TMatchingSuccessor {
186
190
/** Holds if this is a match successor. */
187
191
predicate isMatch ( ) { this = TMatchingSuccessor ( true ) }
188
192
@@ -206,7 +210,7 @@ class MatchingSuccessor extends ConditionalSuccessor, TMatchingSuccessor {
206
210
*
207
211
* has a control flow graph containing emptiness successors:
208
212
*
209
- * ```
213
+ * ```text
210
214
* args
211
215
* |
212
216
* loop-header------<-----
@@ -223,7 +227,7 @@ class MatchingSuccessor extends ConditionalSuccessor, TMatchingSuccessor {
223
227
* \_________/
224
228
* ```
225
229
*/
226
- class EmptinessSuccessor extends ConditionalSuccessor , TEmptinessSuccessor {
230
+ class EmptinessSuccessor extends ConditionalSuccessorImpl , TEmptinessSuccessor {
227
231
/** Holds if this is an empty successor. */
228
232
predicate isEmpty ( ) { this = TEmptinessSuccessor ( true ) }
229
233
@@ -236,7 +240,9 @@ private class TAbruptSuccessor =
236
240
TExceptionSuccessor or TReturnSuccessor or TExitSuccessor or TJumpSuccessor ;
237
241
238
242
/** An abrupt control flow successor. */
239
- abstract class AbruptSuccessor extends SuccessorType , TAbruptSuccessor { }
243
+ abstract private class AbruptSuccessorImpl extends SuccessorTypeImpl , TAbruptSuccessor { }
244
+
245
+ final class AbruptSuccessor = AbruptSuccessorImpl ;
240
246
241
247
/**
242
248
* An exceptional control flow successor.
@@ -255,7 +261,7 @@ abstract class AbruptSuccessor extends SuccessorType, TAbruptSuccessor { }
255
261
* The callable exit node of `M` is an exceptional successor of the node
256
262
* `throw new ArgumentNullException(nameof(s));`.
257
263
*/
258
- class ExceptionSuccessor extends AbruptSuccessor , TExceptionSuccessor {
264
+ class ExceptionSuccessor extends AbruptSuccessorImpl , TExceptionSuccessor {
259
265
override string toString ( ) { result = "exception" }
260
266
}
261
267
@@ -274,7 +280,7 @@ class ExceptionSuccessor extends AbruptSuccessor, TExceptionSuccessor {
274
280
* The callable exit node of `M` is a `return` successor of the `return;`
275
281
* statement.
276
282
*/
277
- class ReturnSuccessor extends AbruptSuccessor , TReturnSuccessor {
283
+ class ReturnSuccessor extends AbruptSuccessorImpl , TReturnSuccessor {
278
284
override string toString ( ) { result = "return" }
279
285
}
280
286
@@ -294,54 +300,44 @@ class ReturnSuccessor extends AbruptSuccessor, TReturnSuccessor {
294
300
*
295
301
* The callable exit node of `M` is an exit successor of the node on line 4.
296
302
*/
297
- class ExitSuccessor extends AbruptSuccessor , TExitSuccessor {
303
+ class ExitSuccessor extends AbruptSuccessorImpl , TExitSuccessor {
298
304
override string toString ( ) { result = "exit" }
299
305
}
300
306
301
307
private class TJumpSuccessor =
302
- TBreakSuccessor or TContinueSuccessor or TGotoSuccessor or TRedoSuccessor or TRetrySuccessor or
303
- TJavaYieldSuccessor ;
308
+ TBreakSuccessor or TContinueSuccessor or TGotoSuccessor or TRedoSuccessor or TRetrySuccessor ;
304
309
305
310
/**
306
311
* A jump control flow successor.
307
312
*
308
313
* This covers non-exceptional, non-local control flow, such as `break`,
309
314
* `continue`, and `goto`.
310
315
*/
311
- abstract class JumpSuccessor extends AbruptSuccessor , TJumpSuccessor { }
316
+ abstract private class JumpSuccessorImpl extends AbruptSuccessorImpl , TJumpSuccessor { }
317
+
318
+ final class JumpSuccessor = JumpSuccessorImpl ;
312
319
313
320
/** A `break` control flow successor. */
314
- class BreakSuccessor extends JumpSuccessor , TBreakSuccessor {
321
+ class BreakSuccessor extends JumpSuccessorImpl , TBreakSuccessor {
315
322
override string toString ( ) { result = "break" }
316
323
}
317
324
318
325
/** A `continue` control flow successor. */
319
- class ContinueSuccessor extends JumpSuccessor , TContinueSuccessor {
326
+ class ContinueSuccessor extends JumpSuccessorImpl , TContinueSuccessor {
320
327
override string toString ( ) { result = "continue" }
321
328
}
322
329
323
330
/** A `goto` control flow successor. */
324
- class GotoSuccessor extends JumpSuccessor , TGotoSuccessor {
331
+ class GotoSuccessor extends JumpSuccessorImpl , TGotoSuccessor {
325
332
override string toString ( ) { result = "goto" }
326
333
}
327
334
328
335
/** A `redo` control flow successor (rare, used in Ruby). */
329
- class RedoSuccessor extends JumpSuccessor , TRedoSuccessor {
336
+ class RedoSuccessor extends JumpSuccessorImpl , TRedoSuccessor {
330
337
override string toString ( ) { result = "redo" }
331
338
}
332
339
333
340
/** A `retry` control flow successor (rare, used in Ruby). */
334
- class RetrySuccessor extends JumpSuccessor , TRetrySuccessor {
341
+ class RetrySuccessor extends JumpSuccessorImpl , TRetrySuccessor {
335
342
override string toString ( ) { result = "retry" }
336
343
}
337
-
338
- /** A Java `yield` control flow successor. */
339
- class JavaYieldSuccessor extends JumpSuccessor , TJavaYieldSuccessor {
340
- override string toString ( ) { result = "yield" }
341
- }
342
-
343
- /** Holds if `t` is an abnormal exit type out of a CFG scope. */
344
- predicate isAbnormalExitType ( SuccessorType t ) {
345
- t instanceof ExceptionSuccessor or
346
- t instanceof ExitSuccessor
347
- }
0 commit comments