Skip to content

Commit 50b332c

Browse files
committed
C++: Insert int-to-bool conversions at binary conditional expressions.
1 parent 9dd6678 commit 50b332c

File tree

2 files changed

+51
-2
lines changed

2 files changed

+51
-2
lines changed

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

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,8 @@ newtype TInstructionTag =
4141
ValueConditionCompareTag() or
4242
ValueConditionConstantTag() or
4343
ValueConditionConditionalBranchTag() or
44+
ValueConditionConditionalConstantTag() or
45+
ValueConditionConditionalCompareTag() or
4446
ConditionValueTrueTempAddressTag() or
4547
ConditionValueTrueConstantTag() or
4648
ConditionValueTrueStoreTag() or
@@ -172,6 +174,10 @@ string getInstructionTagId(TInstructionTag tag) {
172174
or
173175
tag = ValueConditionConditionalBranchTag() and result = "ValCondCondBranch"
174176
or
177+
tag = ValueConditionConditionalConstantTag() and result = "ValueConditionConditionalConstant"
178+
or
179+
tag = ValueConditionConditionalCompareTag() and result = "ValueConditionConditionalCompare"
180+
or
175181
tag = ValueConditionCompareTag() and result = "ValCondCondCompare"
176182
or
177183
tag = ValueConditionConstantTag() and result = "ValCondConstant"

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

Lines changed: 45 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2957,18 +2957,42 @@ class TranslatedBinaryConditionalExpr extends TranslatedConditionalExpr {
29572957
result = this.getCondition().getFirstInstruction(kind)
29582958
}
29592959

2960+
private Type getConditionType() { result = this.getCondition().getExprType() }
2961+
29602962
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
29612963
super.hasInstruction(opcode, tag, resultType)
29622964
or
29632965
// For the binary variant, we create our own conditional branch.
29642966
tag = ValueConditionConditionalBranchTag() and
29652967
opcode instanceof Opcode::ConditionalBranch and
29662968
resultType = getVoidType()
2969+
or
2970+
not this.getConditionType() instanceof BoolType and
2971+
(
2972+
tag = ValueConditionConditionalConstantTag() and
2973+
opcode instanceof Opcode::Constant and
2974+
resultType = getIntType()
2975+
or
2976+
tag = ValueConditionConditionalCompareTag() and
2977+
opcode instanceof Opcode::CompareNE and
2978+
resultType = getBoolType()
2979+
)
29672980
}
29682981

29692982
override Instruction getInstructionSuccessorInternal(InstructionTag tag, EdgeKind kind) {
29702983
result = super.getInstructionSuccessorInternal(tag, kind)
29712984
or
2985+
not this.getConditionType() instanceof BoolType and
2986+
(
2987+
tag = ValueConditionConditionalConstantTag() and
2988+
kind instanceof GotoEdge and
2989+
result = this.getInstruction(ValueConditionConditionalCompareTag())
2990+
or
2991+
tag = ValueConditionConditionalCompareTag() and
2992+
kind instanceof GotoEdge and
2993+
result = this.getInstruction(ValueConditionConditionalBranchTag())
2994+
)
2995+
or
29722996
tag = ValueConditionConditionalBranchTag() and
29732997
(
29742998
kind instanceof TrueEdge and
@@ -2984,15 +3008,29 @@ class TranslatedBinaryConditionalExpr extends TranslatedConditionalExpr {
29843008
or
29853009
tag = ValueConditionConditionalBranchTag() and
29863010
operandTag instanceof ConditionOperandTag and
2987-
result = this.getCondition().getResult()
3011+
if this.getConditionType() instanceof BoolType
3012+
then result = this.getCondition().getResult()
3013+
else result = this.getInstruction(ValueConditionConditionalCompareTag())
3014+
or
3015+
not this.getConditionType() instanceof BoolType and
3016+
tag = ValueConditionConditionalCompareTag() and
3017+
(
3018+
operandTag instanceof LeftOperandTag and
3019+
result = this.getCondition().getResult()
3020+
or
3021+
operandTag instanceof RightOperandTag and
3022+
result = this.getInstruction(ValueConditionConditionalConstantTag())
3023+
)
29883024
}
29893025

29903026
override Instruction getChildSuccessorInternal(TranslatedElement child, EdgeKind kind) {
29913027
result = super.getChildSuccessorInternal(child, kind)
29923028
or
29933029
kind instanceof GotoEdge and
29943030
child = this.getCondition() and
2995-
result = this.getInstruction(ValueConditionConditionalBranchTag())
3031+
if this.getConditionType() instanceof BoolType
3032+
then result = this.getInstruction(ValueConditionConditionalBranchTag())
3033+
else result = this.getInstruction(ValueConditionConditionalConstantTag())
29963034
}
29973035

29983036
private TranslatedExpr getCondition() {
@@ -3009,6 +3047,11 @@ class TranslatedBinaryConditionalExpr extends TranslatedConditionalExpr {
30093047
// always converting the "then" operand to `bool`, which is almost always the wrong type.
30103048
result = getTranslatedExpr(expr.getThen().getExplicitlyConverted())
30113049
}
3050+
3051+
override string getInstructionConstantValue(InstructionTag tag) {
3052+
tag = ValueConditionConditionalConstantTag() and
3053+
result = "0"
3054+
}
30123055
}
30133056

30143057
/**

0 commit comments

Comments
 (0)