Skip to content

Commit 18eede5

Browse files
committed
fix some inconsistencies related to primitive types
1 parent 9127fa5 commit 18eede5

File tree

5 files changed

+45
-13
lines changed

5 files changed

+45
-13
lines changed

ql/src/codeql_ql/ast/Ast.qll

Lines changed: 21 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1551,7 +1551,7 @@ class ExprAggregate extends TExprAggregate, Aggregate {
15511551

15521552
override Type getType() {
15531553
exists(PrimitiveType prim | prim = result |
1554-
kind.regexpMatch("(strict)?count|sum|min|max|rank") and
1554+
kind.regexpMatch("(strict)?count") and
15551555
result.getName() = "int"
15561556
or
15571557
kind.regexpMatch("(strict)?concat") and
@@ -1615,16 +1615,16 @@ class FullAggregate extends TFullAggregate, Aggregate {
16151615

16161616
override Type getType() {
16171617
exists(PrimitiveType prim | prim = result |
1618-
kind.regexpMatch("(strict)?(count|sum|min|max|rank)") and
1618+
kind = ["count", "strictcount"] and
16191619
result.getName() = "int"
16201620
or
16211621
kind.regexpMatch("(strict)?concat") and
16221622
result.getName() = "string"
16231623
)
16241624
or
1625-
kind = ["any", "min", "max", "unique"] and
1625+
kind = ["any", "min", "max", "unique", "rank", "sum", "strictsum"] and
16261626
not exists(this.getExpr(_)) and
1627-
result = this.getArgument(0).getTypeExpr().getResolvedType()
1627+
result = this.getArgument(0).getType()
16281628
or
16291629
not kind = ["count", "strictcount"] and
16301630
result = this.getExpr(0).getType()
@@ -1910,11 +1910,18 @@ private Expr exprOfPrimitiveAddType(PrimitiveType t) {
19101910
result.getType() = getASubTypeOfAddPrimitive(t)
19111911
}
19121912

1913+
/**
1914+
* Gets a subtype of the given primitive type `prim`.
1915+
* This predicate does not consider float to be a supertype of int.
1916+
*/
19131917
private Type getASubTypeOfAddPrimitive(PrimitiveType prim) {
19141918
result = prim and
19151919
result.getName() = ["int", "string", "float"]
19161920
or
1917-
result.getASuperType() = getASubTypeOfAddPrimitive(prim)
1921+
exists(Type superType | superType = getASubTypeOfAddPrimitive(prim) |
1922+
result.getASuperType() = superType and
1923+
not (result.getName() = "int" and superType.getName() = "float")
1924+
)
19181925
}
19191926

19201927
/**
@@ -1957,15 +1964,18 @@ class MulDivModExpr extends TMulDivModExpr, BinOpExpr {
19571964
this.getLeftOperand().getType() = result and
19581965
this.getRightOperand().getType() = result
19591966
or
1960-
// Both operands are subtypes of `int`
1961-
result.getName() = "int" and
1962-
result = this.getLeftOperand().getType().getASuperType*() and
1963-
result = this.getRightOperand().getType().getASuperType*()
1967+
// Both operands are subtypes of `int`/`float`
1968+
result.getName() = ["int", "float"] and
1969+
exprOfPrimitiveAddType(result) = this.getLeftOperand() and
1970+
exprOfPrimitiveAddType(result) = this.getRightOperand()
19641971
or
19651972
// Coercion from `int` to `float`
19661973
exists(PrimitiveType i | result.getName() = "float" and i.getName() = "int" |
1967-
this.getAnOperand().getType() = result and
1968-
this.getAnOperand().getType().getASuperType*() = i
1974+
this.getLeftOperand() = exprOfPrimitiveAddType(result) and
1975+
this.getRightOperand() = exprOfPrimitiveAddType(i)
1976+
or
1977+
this.getRightOperand() = exprOfPrimitiveAddType(result) and
1978+
this.getLeftOperand() = exprOfPrimitiveAddType(i)
19691979
)
19701980
}
19711981

ql/src/codeql_ql/ast/internal/Type.qll

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -340,6 +340,12 @@ module TyConsistency {
340340
resolveTypeExpr(te, t)
341341
}
342342

343+
query predicate multiplePrimitives(TypeExpr te, int c, PrimitiveType t) {
344+
c = strictcount(PrimitiveType t0 | resolveTypeExpr(te, t0)) and
345+
c > 1 and
346+
resolveTypeExpr(te, t)
347+
}
348+
343349
query predicate varDefNoType(VarDef def) {
344350
not exists(def.getType()) and
345351
not def.getLocation()
@@ -360,4 +366,10 @@ module TyConsistency {
360366
.getAbsolutePath()
361367
.regexpMatch(".*/(test|examples|ql-training|recorded-call-graph-metrics)/.*")
362368
}
369+
370+
query predicate multiplePrimitivesExpr(Expr e, int c, PrimitiveType t) {
371+
c = strictcount(PrimitiveType t0 | t0 = e.getType()) and
372+
c > 1 and
373+
t = e.getType()
374+
}
363375
}

ql/src/queries/diagnostics/EmptyConsistencies.ql

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,12 +21,15 @@ where
2121
or
2222
PredConsistency::noResolvePredicateExpr(node) and msg = "PredConsistency::noResolvePredicateExpr"
2323
or
24-
TypeConsistency::noResolve(node) and msg = "TypeConsistency::noResolve"
25-
or
2624
TypeConsistency::exprNoType(node) and msg = "TypeConsistency::exprNoType"
2725
or
2826
TypeConsistency::varDefNoType(node) and msg = "TypeConsistency::varDefNoType"
2927
or
28+
TypeConsistency::multiplePrimitives(node, _, _) and msg = "TypeConsistency::multiplePrimitives"
29+
or
30+
TypeConsistency::multiplePrimitivesExpr(node, _, _) and
31+
msg = "TypeConsistency::multiplePrimitivesExpr"
32+
or
3033
//or // has 1 result, but the CodeQL compiler also can't figure out that one. I suppoed the file is never imported.
3134
//TypeConsistency::noResolve(node) and msg = "TypeConsistency::noResolve"
3235
//or // has 1 result, but the CodeQL compiler also can't figure out that one. Same file as above.

ql/test/type/Test.qll

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,3 +25,6 @@ class Sub extends Base {
2525

2626
int bar2() { result = super.foo() }
2727
}
28+
29+
bindingset[result, a, b]
30+
int integerMul(int a, int b) { result = a * b }

ql/test/type/type.expected

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,3 +52,7 @@
5252
| Test.qll:26:16:26:21 | result | file://:0:0:0:0 | int |
5353
| Test.qll:26:25:26:29 | Super | Test.qll:15:1:19:1 | Base |
5454
| Test.qll:26:25:26:35 | MemberCall | file://:0:0:0:0 | int |
55+
| Test.qll:30:32:30:37 | result | file://:0:0:0:0 | int |
56+
| Test.qll:30:41:30:41 | a | file://:0:0:0:0 | int |
57+
| Test.qll:30:41:30:45 | MulExpr | file://:0:0:0:0 | int |
58+
| Test.qll:30:45:30:45 | b | file://:0:0:0:0 | int |

0 commit comments

Comments
 (0)