@@ -1444,6 +1444,31 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
14441444 )
14451445 }
14461446
1447+ pragma [ nomagic]
1448+ private predicate compatibleContainer0 ( ApHeadContent apc , DataFlowType containerType ) {
1449+ exists ( DataFlowType containerType0 , Content c |
1450+ PrevStage:: storeStepCand ( _, _, c , _, _, containerType0 ) and
1451+ not isTopType ( containerType0 ) and
1452+ compatibleTypesCached ( containerType0 , containerType ) and
1453+ apc = projectToHeadContent ( c )
1454+ )
1455+ }
1456+
1457+ pragma [ nomagic]
1458+ private predicate topTypeContent ( ApHeadContent apc ) {
1459+ exists ( DataFlowType containerType0 , Content c |
1460+ PrevStage:: storeStepCand ( _, _, c , _, _, containerType0 ) and
1461+ isTopType ( containerType0 ) and
1462+ apc = projectToHeadContent ( c )
1463+ )
1464+ }
1465+
1466+ bindingset [ apc, containerType]
1467+ pragma [ inline_late]
1468+ private predicate compatibleContainer ( ApHeadContent apc , DataFlowType containerType ) {
1469+ compatibleContainer0 ( apc , containerType )
1470+ }
1471+
14471472 /**
14481473 * Holds if `node` is reachable with access path `ap` from a source.
14491474 *
@@ -1465,7 +1490,15 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
14651490 ) {
14661491 fwdFlow0 ( node , state , cc , summaryCtx , argT , argAp , t0 , ap , apa ) and
14671492 PrevStage:: revFlow ( node , state , apa ) and
1468- filter ( node , state , t0 , ap , t )
1493+ filter ( node , state , t0 , ap , t ) and
1494+ (
1495+ if castingNodeEx ( node )
1496+ then
1497+ ap instanceof ApNil or
1498+ compatibleContainer ( getHeadContent ( ap ) , node .getDataFlowType ( ) ) or
1499+ topTypeContent ( getHeadContent ( ap ) )
1500+ else any ( )
1501+ )
14691502 }
14701503
14711504 pragma [ nomagic]
@@ -2853,20 +2886,22 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
28532886 private import LocalFlowBigStep
28542887
28552888 pragma [ nomagic]
2856- private predicate castingNodeEx ( NodeEx node ) { node .asNode ( ) instanceof CastingNode }
2889+ private predicate castingNodeEx ( NodeEx node ) {
2890+ node .asNode ( ) instanceof CastingNode or exists ( node .asParamReturnNode ( ) )
2891+ }
28572892
28582893 private module Stage3Param implements MkStage< Stage2 > :: StageParam {
28592894 private module PrevStage = Stage2;
28602895
2861- class Typ = DataFlowType ;
2896+ class Typ = Unit ;
28622897
28632898 class Ap = ApproxAccessPathFront ;
28642899
28652900 class ApNil = ApproxAccessPathFrontNil ;
28662901
28672902 PrevStage:: Ap getApprox ( Ap ap ) { result = ap .toBoolNonEmpty ( ) }
28682903
2869- Typ getTyp ( DataFlowType t ) { result = t }
2904+ Typ getTyp ( DataFlowType t ) { any ( ) }
28702905
28712906 bindingset [ c, t, tail]
28722907 Ap apCons ( Content c , Typ t , Ap tail ) { result .getAHead ( ) = c and exists ( t ) and exists ( tail ) }
@@ -2903,7 +2938,8 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
29032938 NodeEx node1 , FlowState state1 , NodeEx node2 , FlowState state2 , boolean preservesValue ,
29042939 Typ t , LocalCc lcc
29052940 ) {
2906- localFlowBigStep ( node1 , state1 , node2 , state2 , preservesValue , t , _, _) and
2941+ localFlowBigStep ( node1 , state1 , node2 , state2 , preservesValue , _, _, _) and
2942+ exists ( t ) and
29072943 exists ( lcc )
29082944 }
29092945
@@ -2926,7 +2962,6 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
29262962 // the cons candidates including types are used to construct subsequent
29272963 // access path approximations.
29282964 t0 = t and
2929- ( if castingNodeEx ( node ) then compatibleTypes ( node .getDataFlowType ( ) , t0 ) else any ( ) ) and
29302965 (
29312966 notExpectsContent ( node )
29322967 or
@@ -2935,11 +2970,7 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
29352970 }
29362971
29372972 bindingset [ typ, contentType]
2938- predicate typecheckStore ( Typ typ , DataFlowType contentType ) {
2939- // We need to typecheck stores here, since reverse flow through a getter
2940- // might have a different type here compared to inside the getter.
2941- compatibleTypes ( typ , contentType )
2942- }
2973+ predicate typecheckStore ( Typ typ , DataFlowType contentType ) { any ( ) }
29432974 }
29442975
29452976 private module Stage3 = MkStage< Stage2 > :: Stage< Stage3Param > ;
@@ -2949,7 +2980,11 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
29492980 if castingNodeEx ( node )
29502981 then
29512982 exists ( DataFlowType nt | nt = node .getDataFlowType ( ) |
2952- if typeStrongerThan ( nt , t0 ) then t = nt else ( compatibleTypes ( nt , t0 ) and t = t0 )
2983+ if typeStrongerThanFilter ( nt , t0 )
2984+ then t = nt
2985+ else (
2986+ compatibleTypesFilter ( nt , t0 ) and t = t0
2987+ )
29532988 )
29542989 else t = t0
29552990 }
@@ -3048,7 +3083,7 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
30483083 predicate typecheckStore ( Typ typ , DataFlowType contentType ) {
30493084 // We need to typecheck stores here, since reverse flow through a getter
30503085 // might have a different type here compared to inside the getter.
3051- compatibleTypes ( typ , contentType )
3086+ compatibleTypesFilter ( typ , contentType )
30523087 }
30533088 }
30543089
@@ -3304,7 +3339,7 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
33043339
33053340 bindingset [ typ, contentType]
33063341 predicate typecheckStore ( Typ typ , DataFlowType contentType ) {
3307- compatibleTypes ( typ , contentType )
3342+ compatibleTypesFilter ( typ , contentType )
33083343 }
33093344 }
33103345
@@ -4244,7 +4279,7 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
42444279 Stage5:: storeStepCand ( mid .getNodeExOutgoing ( ) , _, c , node , contentType , t ) and
42454280 state = mid .getState ( ) and
42464281 cc = mid .getCallContext ( ) and
4247- compatibleTypes ( t0 , contentType )
4282+ compatibleTypesFilter ( t0 , contentType )
42484283 )
42494284 }
42504285
@@ -5294,7 +5329,7 @@ module MakeImpl<LocationSig Location, InputSig<Location> Lang> {
52945329 storeExUnrestricted ( midNode , c , node , contentType , t2 ) and
52955330 ap2 .getHead ( ) = c and
52965331 ap2 .len ( ) = unbindInt ( ap1 .len ( ) + 1 ) and
5297- compatibleTypes ( t1 , contentType )
5332+ compatibleTypesFilter ( t1 , contentType )
52985333 )
52995334 }
53005335
0 commit comments