@@ -1394,16 +1394,22 @@ private module AssocFunctionResolution {
13941394
13951395 /**
13961396 * Holds if function `f` with the name `name` and the arity `arity` exists in
1397- * `i`, and the type of the `self` parameter is `selfType`.
1397+ * `i`, and the type at `selfPos` and `strippedTypePath` is `selfType`.
1398+ *
1399+ * `selfPos` is one of the positions that can be used to resolve the call, for
1400+ * example the `self` parameter of a method or a position corresponding to `Self`
1401+ * trait type parameter.
13981402 *
13991403 * `strippedTypePath` points to the type `strippedType` inside `selfType`,
14001404 * which is the (possibly complex-stripped) root type of `selfType`. For example,
14011405 * if `f` has a `&self` parameter, then `strippedTypePath` is `getRefSharedTypeParameter()`
14021406 * and `strippedType` is the type inside the reference.
1407+ *
1408+ * `selfPosAdj` is the function-call adjusted version of `selfPos`.
14031409 */
14041410 pragma [ nomagic]
14051411 private predicate assocFunctionInfo (
1406- Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition posAdj ,
1412+ Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition selfPosAdj ,
14071413 ImplOrTraitItemNode i , AssocFunctionType selfType , TypePath strippedTypePath , Type strippedType
14081414 ) {
14091415 assocFunctionInfo ( f , name , arity , i , selfPos , selfType ) and
@@ -1413,7 +1419,7 @@ private module AssocFunctionResolution {
14131419 or
14141420 selfPos .isTypeQualifier ( ) and strippedTypePath .isEmpty ( )
14151421 ) and
1416- posAdj = selfPos .getFunctionCallAdjusted ( f ) and
1422+ selfPosAdj = selfPos .getFunctionCallAdjusted ( f ) and
14171423 (
14181424 selfPos .isSelfOrTypeQualifier ( )
14191425 or
@@ -1425,10 +1431,10 @@ private module AssocFunctionResolution {
14251431
14261432 pragma [ nomagic]
14271433 private predicate assocFunctionInfoTypeParam (
1428- Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition posAdj ,
1434+ Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition selfPosAdj ,
14291435 ImplOrTraitItemNode i , AssocFunctionType selfType , TypePath strippedTypePath , TypeParam tp
14301436 ) {
1431- assocFunctionInfo ( f , name , arity , selfPos , posAdj , i , selfType , strippedTypePath ,
1437+ assocFunctionInfo ( f , name , arity , selfPos , selfPosAdj , i , selfType , strippedTypePath ,
14321438 TTypeParamTypeParameter ( tp ) )
14331439 }
14341440
@@ -1439,33 +1445,35 @@ private module AssocFunctionResolution {
14391445 */
14401446 pragma [ inline]
14411447 private predicate assocFunctionInfoNonBlanket (
1442- Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition posAdj ,
1448+ Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition selfPosAdj ,
14431449 ImplOrTraitItemNode i , AssocFunctionType selfType , TypePath strippedTypePath , Type strippedType
14441450 ) {
14451451 (
1446- assocFunctionInfo ( f , name , arity , selfPos , posAdj , i , selfType , strippedTypePath , strippedType ) or
1447- assocFunctionInfoTypeParam ( f , name , arity , selfPos , posAdj , i , selfType , strippedTypePath , _)
1452+ assocFunctionInfo ( f , name , arity , selfPos , selfPosAdj , i , selfType , strippedTypePath ,
1453+ strippedType ) or
1454+ assocFunctionInfoTypeParam ( f , name , arity , selfPos , selfPosAdj , i , selfType , strippedTypePath ,
1455+ _)
14481456 ) and
14491457 not BlanketImplementation:: isBlanketLike ( i , _, _)
14501458 }
14511459
14521460 /**
1453- * Holds if function `f` with the name `name` and the arity `arity` exists in
1454- * blanket (like) implementation `impl` of `trait`, and the type of the `self`
1455- * parameter is `selfType`.
1461+ * Holds if associated function `f` with the name `name` and the arity `arity` exists
1462+ * in blanket (like) implementation `impl` of `trait`, and the type at `selfPos` and
1463+ * `blanketPath` is `selfType`.
14561464 *
14571465 * `blanketPath` points to the type `blanketTypeParam` inside `selfType`, which
14581466 * is the type parameter used in the blanket implementation.
14591467 */
14601468 pragma [ nomagic]
14611469 private predicate assocFunctionSelfInfoBlanketLike (
1462- Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition posAdj ,
1470+ Function f , string name , int arity , FunctionPosition selfPos , FunctionPosition selfPosAdj ,
14631471 ImplItemNode impl , Trait trait , AssocFunctionType selfType , TypePath blanketPath ,
14641472 TypeParam blanketTypeParam
14651473 ) {
14661474 assocFunctionInfoBlanketLike ( f , name , arity , impl , trait , selfPos , selfType , blanketPath ,
14671475 blanketTypeParam ) and
1468- posAdj = selfPos .getFunctionCallAdjusted ( f ) and
1476+ selfPosAdj = selfPos .getFunctionCallAdjusted ( f ) and
14691477 (
14701478 selfPos .isSelfOrTypeQualifier ( )
14711479 or
@@ -1522,12 +1530,12 @@ private module AssocFunctionResolution {
15221530 bindingset [ mc, strippedTypePath, strippedType]
15231531 pragma [ inline_late]
15241532 private predicate methodCallNonBlanketCandidate (
1525- MethodCall mc , Function f , FunctionPosition selfPos , FunctionPosition pos ,
1533+ MethodCall mc , Function f , FunctionPosition selfPos , FunctionPosition selfPosAdj ,
15261534 ImplOrTraitItemNode i , AssocFunctionType self , TypePath strippedTypePath , Type strippedType
15271535 ) {
15281536 exists ( string name , int arity |
15291537 mc .hasNameAndArity ( name , arity ) and
1530- assocFunctionInfoNonBlanket ( f , name , arity , selfPos , pos , i , self , strippedTypePath ,
1538+ assocFunctionInfoNonBlanket ( f , name , arity , selfPos , selfPosAdj , i , self , strippedTypePath ,
15311539 strippedType ) and
15321540 ( if mc .hasReceiver ( ) then f instanceof Method else any ( ) ) and
15331541 // todo: comment
@@ -1565,13 +1573,13 @@ private module AssocFunctionResolution {
15651573 bindingset [ mc]
15661574 pragma [ inline_late]
15671575 private predicate methodCallBlanketLikeCandidate (
1568- MethodCall mc , Function f , FunctionPosition selfPos , FunctionPosition pos , ImplItemNode impl ,
1569- AssocFunctionType self , TypePath blanketPath , TypeParam blanketTypeParam
1576+ MethodCall mc , Function f , FunctionPosition selfPos , FunctionPosition selfPosAdj ,
1577+ ImplItemNode impl , AssocFunctionType self , TypePath blanketPath , TypeParam blanketTypeParam
15701578 ) {
15711579 exists ( string name , int arity |
15721580 mc .hasNameAndArity ( name , arity ) and
1573- assocFunctionSelfInfoBlanketLike ( f , name , arity , selfPos , pos , impl , _, self , blanketPath ,
1574- blanketTypeParam ) and
1581+ assocFunctionSelfInfoBlanketLike ( f , name , arity , selfPos , selfPosAdj , impl , _, self ,
1582+ blanketPath , blanketTypeParam ) and
15751583 if mc .hasReceiver ( ) then f instanceof Method else any ( )
15761584 |
15771585 methodCallVisibleImplTraitCandidate ( mc , impl )
@@ -2005,10 +2013,10 @@ private module AssocFunctionResolution {
20052013 */
20062014 pragma [ nomagic]
20072015 Function resolveCallTarget (
2008- ImplOrTraitItemNode i , FunctionPosition pos , DerefChain derefChain , BorrowKind borrow
2016+ ImplOrTraitItemNode i , FunctionPosition selfPos , DerefChain derefChain , BorrowKind borrow
20092017 ) {
20102018 exists ( MethodCallCand mcc |
2011- mcc = MkMethodCallCand ( this , pos , _, derefChain , borrow ) and
2019+ mcc = MkMethodCallCand ( this , selfPos , _, derefChain , borrow ) and
20122020 result = mcc .resolveCallTarget ( i )
20132021 )
20142022 }
@@ -2171,32 +2179,25 @@ private module AssocFunctionResolution {
21712179
21722180 private newtype TMethodCallCand =
21732181 MkMethodCallCand (
2174- MethodCall mc , FunctionPosition selfPos , FunctionPosition pos , DerefChain derefChain ,
2182+ MethodCall mc , FunctionPosition selfPos , FunctionPosition selfPosAdj , DerefChain derefChain ,
21752183 BorrowKind borrow
21762184 ) {
21772185 // todo: restrict to relevant positions
21782186 exists ( mc .getACandidateReceiverTypeAt ( selfPos , derefChain , borrow , _) ) and
21792187 if mc .hasReceiver ( )
2180- then
2181- pos .asPosition ( ) = 0 and selfPos .isSelf ( )
2182- or
2183- pos .asPosition ( ) = selfPos .asPosition ( ) + 1
2184- or
2185- pos .isTypeQualifier ( ) and selfPos .isTypeQualifier ( )
2186- or
2187- pos .isReturn ( ) and selfPos .isReturn ( )
2188- else pos = selfPos
2188+ then selfPosAdj = selfPos .getFunctionCallAdjusted ( )
2189+ else selfPosAdj = selfPos
21892190 }
21902191
21912192 /** A method call with a dereference chain and a potential borrow. */
21922193 private class MethodCallCand extends MkMethodCallCand {
21932194 MethodCall mc_ ;
2194- FunctionPosition pos ;
21952195 FunctionPosition selfPos ;
2196+ FunctionPosition selfPosAdj ;
21962197 DerefChain derefChain ;
21972198 BorrowKind borrow ;
21982199
2199- MethodCallCand ( ) { this = MkMethodCallCand ( mc_ , selfPos , pos , derefChain , borrow ) }
2200+ MethodCallCand ( ) { this = MkMethodCallCand ( mc_ , selfPos , selfPosAdj , derefChain , borrow ) }
22002201
22012202 MethodCall getMethodCall ( ) { result = mc_ }
22022203
@@ -2220,7 +2221,7 @@ private module AssocFunctionResolution {
22202221
22212222 pragma [ nomagic]
22222223 predicate hasSignature (
2223- MethodCall mc , FunctionPosition pos_ , TypePath strippedTypePath , Type strippedType ,
2224+ MethodCall mc , FunctionPosition pos , TypePath strippedTypePath , Type strippedType ,
22242225 string name , int arity
22252226 ) {
22262227 strippedType = this .getTypeAt ( strippedTypePath ) and
@@ -2231,7 +2232,7 @@ private module AssocFunctionResolution {
22312232 ) and
22322233 mc = mc_ and
22332234 mc .hasNameAndArity ( name , arity ) and
2234- pos = pos_
2235+ pos = selfPosAdj
22352236 }
22362237
22372238 /**
@@ -2252,10 +2253,11 @@ private module AssocFunctionResolution {
22522253 mc_ .hasTrait ( )
22532254 or
22542255 exists ( TypePath strippedTypePath , Type strippedType , string name , int arity |
2255- ( pos .isTypeQualifier ( ) or pos .asPosition ( ) = 0 ) and
2256- this .hasSignature ( _, pos , strippedTypePath , strippedType , name , arity ) and
2256+ ( selfPosAdj .isTypeQualifier ( ) or selfPosAdj .asPosition ( ) = 0 ) and
2257+ this .hasSignature ( _, selfPosAdj , strippedTypePath , strippedType , name , arity ) and
22572258 forall ( Impl i |
2258- assocFunctionInfoNonBlanket ( _, name , arity , _, pos , i , _, strippedTypePath , strippedType ) and
2259+ assocFunctionInfoNonBlanket ( _, name , arity , _, selfPosAdj , i , _, strippedTypePath ,
2260+ strippedType ) and
22592261 not i .hasTrait ( )
22602262 |
22612263 this .hasIncompatibleInherentTarget ( i )
@@ -2287,7 +2289,8 @@ private module AssocFunctionResolution {
22872289 }
22882290
22892291 string toString ( ) {
2290- result = mc_ .toString ( ) + " at " + pos + " [" + derefChain .toString ( ) + "; " + borrow + "]"
2292+ result =
2293+ mc_ .toString ( ) + " at " + selfPos + " [" + derefChain .toString ( ) + "; " + borrow + "]"
22912294 }
22922295
22932296 Location getLocation ( ) { result = mc_ .getLocation ( ) }
@@ -2368,9 +2371,9 @@ private module AssocFunctionResolution {
23682371 predicate hasBlanketCandidate (
23692372 MethodCallCand mcc , ImplItemNode impl , TypePath blanketPath , TypeParam blanketTypeParam
23702373 ) {
2371- exists ( MethodCall mc , FunctionPosition pos , BorrowKind borrow |
2372- mcc = MkMethodCallCand ( mc , _, pos , _, borrow ) and
2373- methodCallBlanketLikeCandidate ( mc , _, _, pos , impl , _, blanketPath , blanketTypeParam ) and
2374+ exists ( MethodCall mc , FunctionPosition selfPosAdj , BorrowKind borrow |
2375+ mcc = MkMethodCallCand ( mc , _, selfPosAdj , _, borrow ) and
2376+ methodCallBlanketLikeCandidate ( mc , _, _, selfPosAdj , impl , _, blanketPath , blanketTypeParam ) and
23742377 // Only apply blanket implementations when no other implementations are possible;
23752378 // this is to account for codebases that use the (unstable) specialization feature
23762379 // (https://rust-lang.github.io/rfcs/1210-impl-specialization.html), as well as
@@ -2444,9 +2447,9 @@ private module AssocFunctionResolution {
24442447 predicate potentialInstantiationOf (
24452448 MethodCallCand mcc , TypeAbstraction abs , AssocFunctionType constraint
24462449 ) {
2447- exists ( MethodCall mc , FunctionPosition pos |
2448- mcc = MkMethodCallCand ( mc , _, pos , _, _) and
2449- methodCallBlanketLikeCandidate ( mc , _, _, pos , abs , constraint , _, _) and
2450+ exists ( MethodCall mc , FunctionPosition selfPosAdj |
2451+ mcc = MkMethodCallCand ( mc , _, selfPosAdj , _, _) and
2452+ methodCallBlanketLikeCandidate ( mc , _, _, selfPosAdj , abs , constraint , _, _) and
24502453 if abs .( Impl ) .hasTrait ( )
24512454 then
24522455 // inherent methods take precedence over trait methods, so only allow
@@ -2474,8 +2477,8 @@ private module AssocFunctionResolution {
24742477 ReceiverIsInstantiationOfSelfParamInput:: potentialInstantiationOf0 ( mcc , abs , constraint ) and
24752478 abs = any ( Impl i | not i .hasTrait ( ) ) and
24762479 // todo: comment
2477- exists ( FunctionPosition pos | mcc = MkMethodCallCand ( _, _, pos , _, _) |
2478- pos .isTypeQualifier ( ) or pos .asPosition ( ) = 0
2480+ exists ( FunctionPosition selfPosAdj | mcc = MkMethodCallCand ( _, _, selfPosAdj , _, _) |
2481+ selfPosAdj .isTypeQualifier ( ) or selfPosAdj .asPosition ( ) = 0
24792482 )
24802483 }
24812484 }
@@ -2623,17 +2626,7 @@ private module MethodCallMatchingInput implements MatchingWithEnvironmentInputSi
26232626 )
26242627 |
26252628 // result = this.getInferredNonSelfType(pos, path)
2626- if this .hasReceiver ( )
2627- then apos = pos
2628- else (
2629- pos .asPosition ( ) = 0 and apos .isSelf ( )
2630- or
2631- pos .asPosition ( ) = apos .asPosition ( ) + 1
2632- or
2633- pos .isTypeQualifier ( ) and apos .isTypeQualifier ( )
2634- or
2635- pos .isReturn ( ) and apos .isReturn ( )
2636- )
2629+ if this .hasReceiver ( ) then apos = pos else pos = apos .getFunctionCallAdjusted ( )
26372630 )
26382631 }
26392632
@@ -2689,17 +2682,7 @@ private Type inferMethodCallType0(
26892682 exists ( TypePath path0 |
26902683 n = a .getNodeAt ( apos ) and
26912684 exists ( FunctionPosition pos |
2692- if a .hasReceiver ( )
2693- then apos = pos
2694- else (
2695- apos .asPosition ( ) = 0 and pos .isSelf ( )
2696- or
2697- apos .asPosition ( ) = pos .asPosition ( ) + 1
2698- or
2699- apos .isTypeQualifier ( ) and pos .isTypeQualifier ( )
2700- or
2701- apos .isReturn ( ) and pos .isReturn ( )
2702- )
2685+ if a .hasReceiver ( ) then apos = pos else apos = pos .getFunctionCallAdjusted ( )
27032686 |
27042687 exists ( string derefChainBorrow |
27052688 MethodCallMatchingInput:: decodeDerefChainBorrow ( derefChainBorrow , _, derefChain , borrow )
0 commit comments