mirror of
https://github.com/github/codeql.git
synced 2025-12-16 16:53:25 +01:00
C++: treat constant-valued exprs structurally
This commit is contained in:
@@ -41,9 +41,11 @@ import cpp
|
||||
|
||||
/** Used to represent the hash-cons of an expression. */
|
||||
private cached newtype HCBase =
|
||||
HC_IntConst(int val, Type t) { mk_IntConst(val,t,_) }
|
||||
HC_IntLiteral(int val, Type t) { mk_IntLiteral(val,t,_) }
|
||||
or
|
||||
HC_FloatConst(float val, Type t) { mk_FloatConst(val,t,_) }
|
||||
HC_FloatLiteral(float val, Type t) { mk_FloatLiteral(val,t,_) }
|
||||
or
|
||||
HC_StringLiteral(string val, Type t) {mk_StringLiteral(val,t,_)}
|
||||
or
|
||||
HC_Variable(Variable x) {
|
||||
mk_Variable(x, _)
|
||||
@@ -106,8 +108,9 @@ class HC extends HCBase {
|
||||
|
||||
/** Gets the kind of the HC. This can be useful for debugging. */
|
||||
string getKind() {
|
||||
if this instanceof HC_IntConst then result = "IntConst" else
|
||||
if this instanceof HC_FloatConst then result = "FloatConst" else
|
||||
if this instanceof HC_IntLiteral then result = "IntLiteral" else
|
||||
if this instanceof HC_FloatLiteral then result = "FloatLiteral" else
|
||||
if this instanceof HC_StringLiteral then result = "StringLiteral" else
|
||||
if this instanceof HC_Variable then result = "Variable" else
|
||||
if this instanceof HC_FieldAccess then result = "FieldAccess" else
|
||||
if this instanceof HC_Deref then result = "Deref" else
|
||||
@@ -144,33 +147,45 @@ class HC extends HCBase {
|
||||
}
|
||||
}
|
||||
|
||||
private predicate analyzableIntConst(Expr e) {
|
||||
private predicate analyzableIntLiteral(Literal e) {
|
||||
strictcount (e.getValue().toInt()) = 1 and
|
||||
strictcount (e.getType().getUnspecifiedType()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_IntConst(int val, Type t, Expr e) {
|
||||
analyzableIntConst(e) and
|
||||
private predicate mk_IntLiteral(int val, Type t, Expr e) {
|
||||
analyzableIntLiteral(e) and
|
||||
val = e.getValue().toInt() and
|
||||
t = e.getType().getUnspecifiedType()
|
||||
t = e.getType().getUnspecifiedType() and
|
||||
t instanceof IntegralType
|
||||
}
|
||||
|
||||
private predicate analyzableFloatConst(Expr e) {
|
||||
private predicate analyzableFloatLiteral(Literal e) {
|
||||
strictcount (e.getValue().toFloat()) = 1 and
|
||||
strictcount (e.getType().getUnspecifiedType()) = 1 and
|
||||
not analyzableIntConst(e)
|
||||
strictcount (e.getType().getUnspecifiedType()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_FloatConst(float val, Type t, Expr e) {
|
||||
analyzableFloatConst(e) and
|
||||
private predicate mk_FloatLiteral(float val, Type t, Expr e) {
|
||||
analyzableFloatLiteral(e) and
|
||||
val = e.getValue().toFloat() and
|
||||
t = e.getType().getUnspecifiedType()
|
||||
t = e.getType().getUnspecifiedType() and
|
||||
t instanceof FloatingPointType
|
||||
}
|
||||
|
||||
private predicate analyzableStringLiteral(Literal e) {
|
||||
strictcount(e.getValue()) = 1 and
|
||||
strictcount(e.getType().getUnspecifiedType()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_StringLiteral(string val, Type t, Expr e) {
|
||||
analyzableStringLiteral(e) and
|
||||
val = e.getValue() and
|
||||
t = e.getType().getUnspecifiedType() and
|
||||
t.(ArrayType).getBaseType() instanceof CharType
|
||||
|
||||
}
|
||||
|
||||
private predicate analyzableDotFieldAccess(DotFieldAccess access) {
|
||||
strictcount (access.getTarget()) = 1 and
|
||||
strictcount (access.getQualifier().getFullyConverted()) = 1 and
|
||||
not analyzableConst(access)
|
||||
strictcount (access.getQualifier().getFullyConverted()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_DotFieldAccess(
|
||||
@@ -182,8 +197,7 @@ private predicate mk_DotFieldAccess(
|
||||
|
||||
private predicate analyzablePointerFieldAccess(PointerFieldAccess access) {
|
||||
strictcount (access.getTarget()) = 1 and
|
||||
strictcount (access.getQualifier().getFullyConverted()) = 1 and
|
||||
not analyzableConst(access)
|
||||
strictcount (access.getQualifier().getFullyConverted()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_PointerFieldAccess(
|
||||
@@ -208,8 +222,7 @@ private predicate mk_PointerFieldAccess_with_deref(
|
||||
private predicate analyzableImplicitThisFieldAccess(
|
||||
ImplicitThisFieldAccess access) {
|
||||
strictcount (access.getTarget()) = 1 and
|
||||
strictcount (access.getEnclosingFunction()) = 1 and
|
||||
not analyzableConst(access)
|
||||
strictcount (access.getEnclosingFunction()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_ImplicitThisFieldAccess(
|
||||
@@ -238,8 +251,7 @@ private predicate mk_ImplicitThisFieldAccess_with_deref(
|
||||
|
||||
private predicate analyzableVariable(VariableAccess access) {
|
||||
not (access instanceof FieldAccess) and
|
||||
strictcount (access.getTarget()) = 1 and
|
||||
not analyzableConst(access)
|
||||
strictcount (access.getTarget()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_Variable(Variable x, VariableAccess access) {
|
||||
@@ -249,8 +261,7 @@ private predicate mk_Variable(Variable x, VariableAccess access) {
|
||||
|
||||
private predicate analyzableConversion(Conversion conv) {
|
||||
strictcount (conv.getType().getUnspecifiedType()) = 1 and
|
||||
strictcount (conv.getExpr()) = 1 and
|
||||
not analyzableConst(conv)
|
||||
strictcount (conv.getExpr()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_Conversion(Type t, HC child, Conversion conv) {
|
||||
@@ -263,8 +274,7 @@ private predicate analyzableBinaryOp(BinaryOperation op) {
|
||||
op.isPure() and
|
||||
strictcount (op.getLeftOperand().getFullyConverted()) = 1 and
|
||||
strictcount (op.getRightOperand().getFullyConverted()) = 1 and
|
||||
strictcount (op.getOperator()) = 1 and
|
||||
not analyzableConst(op)
|
||||
strictcount (op.getOperator()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_BinaryOp(
|
||||
@@ -279,8 +289,7 @@ private predicate analyzableUnaryOp(UnaryOperation op) {
|
||||
not (op instanceof PointerDereferenceExpr) and
|
||||
op.isPure() and
|
||||
strictcount (op.getOperand().getFullyConverted()) = 1 and
|
||||
strictcount (op.getOperator()) = 1 and
|
||||
not analyzableConst(op)
|
||||
strictcount (op.getOperator()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_UnaryOp(HC child, string opname, UnaryOperation op) {
|
||||
@@ -290,8 +299,7 @@ private predicate mk_UnaryOp(HC child, string opname, UnaryOperation op) {
|
||||
}
|
||||
|
||||
private predicate analyzableThisExpr(ThisExpr thisExpr) {
|
||||
strictcount(thisExpr.getEnclosingFunction()) = 1 and
|
||||
not analyzableConst(thisExpr)
|
||||
strictcount(thisExpr.getEnclosingFunction()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_ThisExpr(Function fcn, ThisExpr thisExpr) {
|
||||
@@ -301,8 +309,7 @@ private predicate mk_ThisExpr(Function fcn, ThisExpr thisExpr) {
|
||||
|
||||
private predicate analyzableArrayAccess(ArrayExpr ae) {
|
||||
strictcount (ae.getArrayBase().getFullyConverted()) = 1 and
|
||||
strictcount (ae.getArrayOffset().getFullyConverted()) = 1 and
|
||||
not analyzableConst(ae)
|
||||
strictcount (ae.getArrayOffset().getFullyConverted()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_ArrayAccess(
|
||||
@@ -314,8 +321,7 @@ private predicate mk_ArrayAccess(
|
||||
|
||||
private predicate analyzablePointerDereferenceExpr(
|
||||
PointerDereferenceExpr deref) {
|
||||
strictcount (deref.getOperand().getFullyConverted()) = 1 and
|
||||
not analyzableConst(deref)
|
||||
strictcount (deref.getOperand().getFullyConverted()) = 1
|
||||
}
|
||||
|
||||
private predicate mk_Deref(
|
||||
@@ -327,12 +333,16 @@ private predicate mk_Deref(
|
||||
/** Gets the hash-cons of expression `e`. */
|
||||
cached HC hashCons(Expr e) {
|
||||
exists (int val, Type t
|
||||
| mk_IntConst(val, t, e) and
|
||||
result = HC_IntConst(val, t))
|
||||
| mk_IntLiteral(val, t, e) and
|
||||
result = HC_IntLiteral(val, t))
|
||||
or
|
||||
exists (float val, Type t
|
||||
| mk_FloatConst(val, t, e) and
|
||||
result = HC_FloatConst(val, t))
|
||||
| mk_FloatLiteral(val, t, e) and
|
||||
result = HC_FloatLiteral(val, t))
|
||||
or
|
||||
exists (string val, Type t
|
||||
| mk_StringLiteral(val, t, e) and
|
||||
result = HC_StringLiteral(val, t))
|
||||
or
|
||||
// Variable with no SSA information.
|
||||
exists (Variable x
|
||||
@@ -377,12 +387,6 @@ cached HC hashCons(Expr e) {
|
||||
or
|
||||
(not analyzableExpr(e,_) and result = HC_Unanalyzable(e))
|
||||
}
|
||||
|
||||
private predicate analyzableConst(Expr e) {
|
||||
analyzableIntConst(e) or
|
||||
analyzableFloatConst(e)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if the expression is explicitly handled by `hashCons`.
|
||||
* Unanalyzable expressions still need to be given a hash-cons,
|
||||
@@ -390,7 +394,9 @@ private predicate analyzableConst(Expr e) {
|
||||
* expression.
|
||||
*/
|
||||
predicate analyzableExpr(Expr e, string kind) {
|
||||
(analyzableConst(e) and kind = "Const") or
|
||||
(analyzableIntLiteral(e) and kind = "IntLiteral") or
|
||||
(analyzableFloatLiteral(e) and kind = "FloatLiteral") or
|
||||
(analyzableStringLiteral(e) and kind = "StringLiteral") or
|
||||
(analyzableDotFieldAccess(e) and kind = "DotFieldAccess") or
|
||||
(analyzablePointerFieldAccess(e) and kind = "PointerFieldAccess") or
|
||||
(analyzableImplicitThisFieldAccess(e) and kind = "ImplicitThisFieldAccess") or
|
||||
|
||||
@@ -20,11 +20,12 @@
|
||||
| test.cpp:43:7:43:24 | ... + ... | 43:c7-c24 45:c7-c24 |
|
||||
| test.cpp:43:12:43:13 | p1 | 43:c12-c13 45:c12-c13 |
|
||||
| test.cpp:43:17:43:24 | global03 | 43:c17-c24 45:c17-c24 |
|
||||
| test.cpp:44:9:44:9 | 0 | 44:c9-c9 51:c25-c25 53:c18-c21 56:c39-c42 59:c17-c20 88:c12-c12 |
|
||||
| test.cpp:44:9:44:9 | 0 | 44:c9-c9 51:c25-c25 88:c12-c12 |
|
||||
| test.cpp:53:10:53:13 | (int)... | 53:c10-c13 56:c21-c24 |
|
||||
| test.cpp:53:10:53:13 | * ... | 53:c10-c13 56:c21-c24 |
|
||||
| test.cpp:53:11:53:13 | str | 53:c11-c13 56:c22-c24 |
|
||||
| test.cpp:53:18:53:21 | 0 | 53:c18-c21 56:c39-c42 59:c17-c20 |
|
||||
| test.cpp:53:18:53:21 | (int)... | 53:c18-c21 56:c39-c42 59:c17-c20 |
|
||||
| test.cpp:55:5:55:7 | ptr | 55:c5-c7 56:c14-c16 56:c32-c34 56:c47-c49 59:c10-c12 |
|
||||
| test.cpp:56:13:56:16 | (int)... | 56:c13-c16 56:c31-c34 59:c9-c12 |
|
||||
| test.cpp:56:13:56:16 | * ... | 56:c13-c16 56:c31-c34 59:c9-c12 |
|
||||
@@ -36,7 +37,7 @@
|
||||
| test.cpp:103:10:103:11 | 1 | 103:c10-c11 104:c7-c7 107:c7-c7 108:c7-c7 10:c16-c16 |
|
||||
| test.cpp:104:3:104:3 | x | 104:c3-c3 105:c3-c3 106:c3-c3 107:c3-c3 108:c3-c3 |
|
||||
| test.cpp:105:7:105:7 | 2 | 105:c7-c7 106:c7-c7 107:c11-c11 108:c11-c11 21:c16-c16 |
|
||||
| test.cpp:107:7:107:11 | ... + ... | 107:c7-c11 108:c7-c11 35:c16-c16 |
|
||||
| test.cpp:107:7:107:11 | ... + ... | 107:c7-c11 108:c7-c11 |
|
||||
| test.cpp:110:15:110:17 | 1 | 110:c15-c17 111:c9-c11 |
|
||||
| test.cpp:110:15:110:17 | (char *)... | 110:c15-c17 111:c9-c11 |
|
||||
| test.cpp:110:15:110:17 | array to pointer conversion | 110:c15-c17 111:c9-c11 |
|
||||
|
||||
Reference in New Issue
Block a user