@@ -21,7 +21,11 @@ private module Impl {
2121 /** Holds if SSA definition `def` equals `e + delta`. */
2222 predicate ssaUpdateStep ( ExplicitDefinition def , ExprNode e , int delta ) {
2323 exists ( ControlFlow:: Node cfn | cfn = def .getControlFlowNode ( ) |
24- e = cfn .( ExprNode:: Assignment ) .getRValue ( ) and delta = 0
24+ e = cfn .( ExprNode:: Assignment ) .getRValue ( ) and
25+ delta = 0 and
26+ not cfn instanceof ExprNode:: AssignOperation
27+ or
28+ e = cfn .( ExprNode:: AssignOperation ) and delta = 0
2529 or
2630 e = cfn .( ExprNode:: PostIncrExpr ) .getOperand ( ) and delta = 1
2731 or
@@ -218,6 +222,11 @@ module ExprNode {
218222 override CS:: AssignExpr e ;
219223 }
220224
225+ /** A compound assignment operation. */
226+ class AssignOperation extends Assignment , BinaryOperation {
227+ override CS:: AssignOperation e ;
228+ }
229+
221230 /** A unary operation. */
222231 class UnaryOperation extends ExprNode {
223232 override CS:: UnaryOperation e ;
@@ -309,80 +318,168 @@ module ExprNode {
309318 }
310319
311320 /** An addition operation. */
312- class AddExpr extends BinaryOperation {
321+ abstract private class AddExprImpl extends BinaryOperation {
322+ override TAddOp getOp ( ) { any ( ) }
323+ }
324+
325+ final class AddExpr = AddExprImpl ;
326+
327+ private class AddAddExpr extends AddExprImpl {
313328 override CS:: AddExpr e ;
329+ }
314330
315- override TAddOp getOp ( ) { any ( ) }
331+ private class AddAssignAddExpr extends AddExprImpl , AssignOperation {
332+ override CS:: AssignAddExpr e ;
316333 }
317334
318335 /** A subtraction operation. */
319- class SubExpr extends BinaryOperation {
336+ abstract private class SubExprImpl extends BinaryOperation {
337+ override TSubOp getOp ( ) { any ( ) }
338+ }
339+
340+ final class SubExpr = SubExprImpl ;
341+
342+ private class AddSubExpr extends SubExprImpl {
320343 override CS:: SubExpr e ;
344+ }
321345
322- override TSubOp getOp ( ) { any ( ) }
346+ private class AddAssignSubExpr extends SubExprImpl , AssignOperation {
347+ override CS:: AssignSubExpr e ;
323348 }
324349
325350 /** A multiplication operation. */
326- class MulExpr extends BinaryOperation {
351+ abstract private class MulExprImpl extends BinaryOperation {
352+ override TMulOp getOp ( ) { any ( ) }
353+ }
354+
355+ final class MulExpr = MulExprImpl ;
356+
357+ private class AddMulExpr extends MulExprImpl {
327358 override CS:: MulExpr e ;
359+ }
328360
329- override TMulOp getOp ( ) { any ( ) }
361+ private class AddAssignMulExpr extends MulExprImpl , AssignOperation {
362+ override CS:: AssignMulExpr e ;
330363 }
331364
332365 /** A division operation. */
333- class DivExpr extends BinaryOperation {
366+ abstract private class DivExprImpl extends BinaryOperation {
367+ override TDivOp getOp ( ) { any ( ) }
368+ }
369+
370+ final class DivExpr = DivExprImpl ;
371+
372+ private class AddDivExpr extends DivExprImpl {
334373 override CS:: DivExpr e ;
374+ }
335375
336- override TDivOp getOp ( ) { any ( ) }
376+ private class AddAssignDivExpr extends DivExprImpl , AssignOperation {
377+ override CS:: AssignDivExpr e ;
337378 }
338379
339380 /** A remainder operation. */
340- class RemExpr extends BinaryOperation {
381+ abstract private class RemExprImpl extends BinaryOperation {
382+ override TRemOp getOp ( ) { any ( ) }
383+ }
384+
385+ final class RemExpr = RemExprImpl ;
386+
387+ private class AddRemExpr extends RemExprImpl {
341388 override CS:: RemExpr e ;
389+ }
342390
343- override TRemOp getOp ( ) { any ( ) }
391+ private class AddAssignRemExpr extends RemExprImpl , AssignOperation {
392+ override CS:: AssignRemExpr e ;
344393 }
345394
346395 /** A bitwise-and operation. */
347- class BitwiseAndExpr extends BinaryOperation {
396+ abstract private class BitwiseAndExprImpl extends BinaryOperation {
397+ override TBitAndOp getOp ( ) { any ( ) }
398+ }
399+
400+ final class BitwiseAndExpr = BitwiseAndExprImpl ;
401+
402+ private class AddBitwiseAndExpr extends BitwiseAndExprImpl {
348403 override CS:: BitwiseAndExpr e ;
404+ }
349405
350- override TBitAndOp getOp ( ) { any ( ) }
406+ private class AddAssignAndExpr extends BitwiseAndExprImpl , AssignOperation {
407+ override CS:: AssignAndExpr e ;
351408 }
352409
353410 /** A bitwise-or operation. */
354- class BitwiseOrExpr extends BinaryOperation {
411+ abstract private class BitwiseOrExprImpl extends BinaryOperation {
412+ override TBitOrOp getOp ( ) { any ( ) }
413+ }
414+
415+ final class BitwiseOrExpr = BitwiseOrExprImpl ;
416+
417+ private class AddBitwiseOrExpr extends BitwiseOrExprImpl {
355418 override CS:: BitwiseOrExpr e ;
419+ }
356420
357- override TBitOrOp getOp ( ) { any ( ) }
421+ private class AddAssignOrExpr extends BitwiseOrExprImpl , AssignOperation {
422+ override CS:: AssignOrExpr e ;
358423 }
359424
360425 /** A bitwise-xor operation. */
361- class BitwiseXorExpr extends BinaryOperation {
426+ abstract private class BitwiseXorExprImpl extends BinaryOperation {
427+ override TBitXorOp getOp ( ) { any ( ) }
428+ }
429+
430+ final class BitwiseXorExpr = BitwiseXorExprImpl ;
431+
432+ private class AddBitwiseXorExpr extends BitwiseXorExprImpl {
362433 override CS:: BitwiseXorExpr e ;
434+ }
363435
364- override TBitXorOp getOp ( ) { any ( ) }
436+ private class AddAssignXorExpr extends BitwiseXorExprImpl , AssignOperation {
437+ override CS:: AssignXorExpr e ;
365438 }
366439
367440 /** A left-shift operation. */
368- class LeftShiftExpr extends BinaryOperation {
441+ abstract private class LeftShiftExprImpl extends BinaryOperation {
442+ override TLeftShiftOp getOp ( ) { any ( ) }
443+ }
444+
445+ final class LeftShiftExpr = LeftShiftExprImpl ;
446+
447+ private class AddLeftShiftExpr extends LeftShiftExprImpl {
369448 override CS:: LeftShiftExpr e ;
449+ }
370450
371- override TLeftShiftOp getOp ( ) { any ( ) }
451+ private class AddAssignLeftShiftExpr extends LeftShiftExprImpl , AssignOperation {
452+ override CS:: AssignLeftShiftExpr e ;
372453 }
373454
374455 /** A right-shift operation. */
375- class RightShiftExpr extends BinaryOperation {
456+ abstract private class RightShiftExprImpl extends BinaryOperation {
457+ override TRightShiftOp getOp ( ) { any ( ) }
458+ }
459+
460+ final class RightShiftExpr = RightShiftExprImpl ;
461+
462+ private class AddRightShiftExpr extends RightShiftExprImpl {
376463 override CS:: RightShiftExpr e ;
464+ }
377465
378- override TRightShiftOp getOp ( ) { any ( ) }
466+ private class AddAssignRightShiftExpr extends RightShiftExprImpl , AssignOperation {
467+ override CS:: AssignRightShiftExpr e ;
379468 }
380469
381470 /** An unsigned right-shift operation. */
382- class UnsignedRightShiftExpr extends BinaryOperation {
471+ abstract private class UnsignedRightShiftExprImpl extends BinaryOperation {
472+ override TUnsignedRightShiftOp getOp ( ) { any ( ) }
473+ }
474+
475+ final class UnsignedRightShiftExpr = UnsignedRightShiftExprImpl ;
476+
477+ private class AddUnsignedRightShiftExpr extends UnsignedRightShiftExprImpl {
383478 override CS:: UnsignedRightShiftExpr e ;
479+ }
384480
385- override TUnsignedRightShiftOp getOp ( ) { any ( ) }
481+ private class AddAssignUnsignedRightShiftExpr extends UnsignedRightShiftExprImpl , AssignOperation {
482+ override CS:: AssignUnsighedRightShiftExpr e ;
386483 }
387484
388485 /** A conditional expression. */
0 commit comments