Skip to content

Commit 362047f

Browse files
committed
wip11
1 parent fd3023c commit 362047f

2 files changed

Lines changed: 49 additions & 53 deletions

File tree

rust/ql/lib/codeql/rust/internal/typeinference/TypeInference.qll

Lines changed: 39 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -457,19 +457,6 @@ private module Input3 implements InputSig3 {
457457
)
458458
}
459459

460-
Type inferCallReturnType(AstNode n, TypePath path) {
461-
exists(Call call, TypePath path0 |
462-
result = M3::inferCallReturnType(call, _, path0) and
463-
n = call and
464-
if
465-
// index expression `x[i]` desugars to `*x.index(i)`, so we must account for
466-
// the implicit deref
467-
call instanceof IndexExpr
468-
then path0.isCons(getRefTypeParameter(_), path)
469-
else path = path0
470-
)
471-
}
472-
473460
Type inferCallArgumentType(AstNode n, TypePath path) {
474461
exists(FunctionCallMatchingInput::Access call, FunctionPosition pos |
475462
result = inferCallArgumentType(call, pos.asPosition(), n, _, _, path) and
@@ -752,7 +739,7 @@ private class FunctionDeclaration extends Function {
752739
TypeParameter getTypeParameter(ImplOrTraitItemNodeOption i, TypeParameterPosition ppos) {
753740
result = ppos.asTypeParameter() and
754741
(
755-
ppos.asTypeParam() = this.getTypeParam(i)
742+
result = TTypeParamTypeParameter(this.getTypeParam(i))
756743
or
757744
// For every `TypeParam` of this function, any associated types accessed on
758745
// the type parameter are also type parameters.
@@ -2604,13 +2591,29 @@ private module FunctionCallMatchingInput implements MatchingWithEnvironmentInput
26042591
import FunctionPositionMatchingInput
26052592

26062593
private newtype TDeclaration =
2607-
TFunctionDeclaration(ImplOrTraitItemNodeOption i, FunctionDeclaration f) { f.isFor(i) }
2594+
TFunctionDeclaration(ImplOrTraitItemNodeOption i, FunctionDeclaration f, boolean forIndexExpr) {
2595+
f.isFor(i) and
2596+
(
2597+
forIndexExpr = false
2598+
or
2599+
forIndexExpr = true and
2600+
exists(Function traitFunction |
2601+
traitFunction =
2602+
[any(IndexTrait t).getIndexFunction(), any(IndexMutTrait t).getIndexMutFunction()]
2603+
|
2604+
f = traitFunction
2605+
or
2606+
f.implements(traitFunction)
2607+
)
2608+
)
2609+
}
26082610

26092611
final class Declaration extends TFunctionDeclaration {
26102612
ImplOrTraitItemNodeOption i;
26112613
FunctionDeclaration f;
2614+
boolean forIndexExpr;
26122615

2613-
Declaration() { this = TFunctionDeclaration(i, f) }
2616+
Declaration() { this = TFunctionDeclaration(i, f, forIndexExpr) }
26142617

26152618
FunctionDeclaration getFunction() { result = f }
26162619

@@ -2619,9 +2622,10 @@ private module FunctionCallMatchingInput implements MatchingWithEnvironmentInput
26192622
f_ = f
26202623
}
26212624

2622-
predicate isAssocFunction(ImplOrTraitItemNode i_, Function f_) {
2625+
predicate isAssocFunction(ImplOrTraitItemNode i_, Function f_, boolean forIndexExpr_) {
26232626
i_ = i.asSome() and
2624-
f_ = f
2627+
f_ = f and
2628+
forIndexExpr_ = forIndexExpr
26252629
}
26262630

26272631
TypeParameter getTypeParameter(TypeParameterPosition ppos) {
@@ -2631,8 +2635,16 @@ private module FunctionCallMatchingInput implements MatchingWithEnvironmentInput
26312635
Type getDeclaredType(FunctionPosition pos, TypePath path) {
26322636
result = f.getParameterType(i, pos, path)
26332637
or
2638+
// index expression `x[i]` desugars to `*x.index(i)`, so we must account for
2639+
// the implicit deref
26342640
pos.isReturn() and
2635-
result = f.getReturnType(i, path)
2641+
exists(TypePath path0 | result = f.getReturnType(i, path0) |
2642+
forIndexExpr = true and
2643+
path0.isCons(getRefTypeParameter(_), path)
2644+
or
2645+
forIndexExpr = false and
2646+
path = path0
2647+
)
26362648
}
26372649

26382650
string toString() {
@@ -2738,23 +2750,8 @@ private module FunctionCallMatchingInput implements MatchingWithEnvironmentInput
27382750

27392751
pragma[nomagic]
27402752
private Type getInferredNonSelfType(FunctionPosition pos, TypePath path) {
2741-
if
2742-
// index expression `x[i]` desugars to `*x.index(i)`, so we must account for
2743-
// the implicit deref
2744-
pos.isReturn() and
2745-
this instanceof IndexExpr
2746-
then
2747-
path.isEmpty() and
2748-
result instanceof RefType
2749-
or
2750-
exists(TypePath suffix |
2751-
result = super.getTypeAt(pos, suffix) and
2752-
path = TypePath::cons(getRefTypeParameter(_), suffix)
2753-
)
2754-
else (
2755-
not super.hasReceiverAtPos(pos) and
2756-
result = super.getTypeAt(pos, path)
2757-
)
2753+
not super.hasReceiverAtPos(pos) and
2754+
result = super.getTypeAt(pos, path)
27582755
}
27592756

27602757
bindingset[derefChainBorrow]
@@ -2772,7 +2769,10 @@ private module FunctionCallMatchingInput implements MatchingWithEnvironmentInput
27722769
}
27732770

27742771
override Declaration getTarget(string derefChainBorrow) {
2775-
exists(ImplOrTraitItemNode i | result.isAssocFunction(i, this.getTarget(i, derefChainBorrow)))
2772+
exists(ImplOrTraitItemNode i, boolean forIndexExpr |
2773+
result.isAssocFunction(i, this.getTarget(i, derefChainBorrow), forIndexExpr) and
2774+
if this instanceof IndexExpr then forIndexExpr = true else forIndexExpr = false
2775+
)
27762776
}
27772777

27782778
pragma[nomagic]
@@ -2825,7 +2825,7 @@ private module FunctionCallMatchingInput implements MatchingWithEnvironmentInput
28252825
private Declaration getTarget() {
28262826
result =
28272827
TFunctionDeclaration(ImplOrTraitItemNodeOption::none_(),
2828-
super.resolveCallTargetViaPathResolution())
2828+
super.resolveCallTargetViaPathResolution(), false)
28292829
}
28302830

28312831
override Declaration getTarget(string derefChainBorrow) {
@@ -3151,7 +3151,7 @@ private module OperationMatchingInput implements MatchingInputSig {
31513151

31523152
Declaration getTarget() {
31533153
exists(ImplOrTraitItemNode i |
3154-
result.isAssocFunction(i, this.resolveCallTarget(i, _, _, _)) // mutual recursion
3154+
result.isAssocFunction(i, this.resolveCallTarget(i, _, _, _), false) // mutual recursion
31553155
)
31563156
}
31573157
}

shared/typeinference/codeql/typeinference/internal/TypeInference.qll

Lines changed: 10 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2194,7 +2194,12 @@ module Make1<LocationSig Location, InputSig1<Location> Input1> {
21942194

21952195
/** A callable. */
21962196
class Callable {
2197-
/** Gets the type parameter at position `ppos` of this callable, if any. */
2197+
/**
2198+
* Gets the type parameter at position `ppos` of this callable, if any.
2199+
*
2200+
* This should include type parameters declared on the callable itself,
2201+
* as well as type parameters declared on the enclosing declaration(s).
2202+
*/
21982203
TypeParameter getTypeParameter(TypeParameterPosition ppos);
21992204

22002205
/**
@@ -2213,7 +2218,7 @@ module Make1<LocationSig Location, InputSig1<Location> Input1> {
22132218
/**
22142219
* Gets the declared type of the `i`th parameter of this callable at `path`.
22152220
*
2216-
* This should also include (possibly implicit) `this`/`self` parameters, perhaps
2221+
* This should also include (possibly implicit) `this`/`self` parameters,
22172222
* using index `-1`.
22182223
*/
22192224
Type getParameterType(int i, TypePath path);
@@ -2236,8 +2241,7 @@ module Make1<LocationSig Location, InputSig1<Location> Input1> {
22362241
/**
22372242
* Gets the AST node corresponding to the `i`th argument of this call.
22382243
*
2239-
* This should include the receiver argument for method calls, perhaps
2240-
* using index `-1`.
2244+
* This should include the receiver argument for method calls, using index `-1`.
22412245
*/
22422246
AstNode getArgument(int i);
22432247

@@ -2262,14 +2266,6 @@ module Make1<LocationSig Location, InputSig1<Location> Input1> {
22622266
exists(ctx)
22632267
}
22642268

2265-
/**
2266-
* Gets the inferred return type of `call` at `path`.
2267-
*
2268-
* When no post-processing is needed, simply implement this predicate as
2269-
* `result = inferCallReturnType(n, _, path)`.
2270-
*/
2271-
Type inferCallReturnType(AstNode n, TypePath path);
2272-
22732269
/**
22742270
* Gets the top-down inferred type of `call` at `path` and argument position
22752271
* `pos`.
@@ -2520,7 +2516,7 @@ module Make1<LocationSig Location, InputSig1<Location> Input1> {
25202516
or
25212517
result = inferTypeFromStep(n, path)
25222518
or
2523-
result = inferCallReturnType(n, path)
2519+
result = inferCallReturnType(n, _, path)
25242520
or
25252521
// top-down inference
25262522
exists(TypePath prefix |
@@ -2625,7 +2621,7 @@ module Make1<LocationSig Location, InputSig1<Location> Input1> {
26252621

26262622
private module CallMatching = MatchingWithEnvironment<CallMatchingInput>;
26272623

2628-
Type inferCallReturnType(Call call, CallResolutionContext ctx, TypePath path) {
2624+
private Type inferCallReturnType(Call call, CallResolutionContext ctx, TypePath path) {
26292625
result = CallMatching::inferAccessType(call, ctx, -2, path)
26302626
}
26312627

0 commit comments

Comments
 (0)