Skip to content

Commit b9d4d38

Browse files
committed
C++: Do not generate conversions which only modify specifiers.
1 parent 1fab97b commit b9d4d38

1 file changed

Lines changed: 40 additions & 12 deletions

File tree

cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedExpr.qll

Lines changed: 40 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -917,7 +917,8 @@ class TranslatedTransparentConversion extends TranslatedTransparentExpr {
917917
expr instanceof ParenthesisExpr or
918918
expr instanceof ReferenceDereferenceExpr or
919919
expr instanceof ReferenceToExpr or
920-
expr instanceof C11GenericExpr
920+
expr instanceof C11GenericExpr or
921+
expr instanceof TransparentSimpleConversion
921922
)
922923
}
923924

@@ -1622,22 +1623,49 @@ abstract class TranslatedSingleInstructionConversion extends TranslatedConversio
16221623
abstract Opcode getOpcode();
16231624
}
16241625

1626+
/** A conversion which can be translated to a single `Convert` instruction. */
1627+
class SimpleConversion extends Conversion {
1628+
SimpleConversion() {
1629+
this instanceof ArithmeticConversion or
1630+
this instanceof PointerConversion or
1631+
this instanceof PointerToMemberConversion or
1632+
this instanceof PointerToIntegralConversion or
1633+
this instanceof IntegralToPointerConversion or
1634+
this instanceof GlvalueConversion or
1635+
this instanceof ArrayToPointerConversion or
1636+
this instanceof PrvalueAdjustmentConversion or
1637+
this instanceof VoidConversion
1638+
}
1639+
}
1640+
1641+
/**
1642+
* A simple conversion which only modifies the specifiers of a type. For
1643+
* example, a cast from `int` to `const int`.
1644+
*
1645+
* Such conversions do generate `Convert` instructions.
1646+
*/
1647+
class TransparentSimpleConversion extends SimpleConversion {
1648+
TransparentSimpleConversion() {
1649+
pragma[only_bind_out](this.getUnspecifiedType()) =
1650+
pragma[only_bind_out](this.getExpr().getUnspecifiedType())
1651+
}
1652+
}
1653+
1654+
/**
1655+
* A simple conversion which converts more than just specifiers.
1656+
*
1657+
* Such conversions generate a `Convert` instruction when translated to IR.
1658+
*/
1659+
class NonTransparentSimpleConversion extends SimpleConversion {
1660+
NonTransparentSimpleConversion() { not this instanceof TransparentSimpleConversion }
1661+
}
1662+
16251663
/**
16261664
* Represents the translation of a conversion expression that generates a
16271665
* `Convert` instruction.
16281666
*/
16291667
class TranslatedSimpleConversion extends TranslatedSingleInstructionConversion {
1630-
TranslatedSimpleConversion() {
1631-
expr instanceof ArithmeticConversion or
1632-
expr instanceof PointerConversion or
1633-
expr instanceof PointerToMemberConversion or
1634-
expr instanceof PointerToIntegralConversion or
1635-
expr instanceof IntegralToPointerConversion or
1636-
expr instanceof GlvalueConversion or
1637-
expr instanceof ArrayToPointerConversion or
1638-
expr instanceof PrvalueAdjustmentConversion or
1639-
expr instanceof VoidConversion
1640-
}
1668+
override NonTransparentSimpleConversion expr;
16411669

16421670
override Opcode getOpcode() { result instanceof Opcode::Convert }
16431671
}

0 commit comments

Comments
 (0)