Data flow: Speedup subpaths predicate

Before
```
[2022-05-02 15:47:16] (1280s) Tuple counts for DataFlowImpl::Subpaths::subpaths#656de156#ffff/4@c5f3dclb after 3m22s:
                      8389013    ~4%     {5} r1 = JOIN DataFlowImpl::Subpaths::subpaths#656de156#ffff#shared WITH DataFlowImpl::PathNode::getASuccessor#dispred#f0820431#ff_10#join_rhs ON FIRST 1 OUTPUT Rhs.1 'arg', Lhs.1, Lhs.2, Lhs.3, Lhs.4 'out'
                      6689751    ~0%     {4} r2 = JOIN r1 WITH DataFlowImpl::Subpaths::subpaths03#656de156#ffffff_034512#join_rhs ON FIRST 4 OUTPUT Rhs.4, Lhs.4 'out', Lhs.0 'arg', Rhs.5 'ret'

                      1513839768 ~1%     {5} r3 = JOIN r2 WITH DataFlowImpl::PathNodeImpl::getNodeEx#dispred#f0820431#ff_10#join_rhs ON FIRST 1 OUTPUT Lhs.1 'out', Lhs.2 'arg', Lhs.3 'ret', Rhs.1 'par', Lhs.3 'ret'
                      1513839768 ~1%     {5} r4 = r3 AND NOT DataFlowImpl::PathNodeImpl::isHidden#dispred#f0820431#f(Lhs.4 'ret')
                      1513839768 ~5%     {4} r5 = SCAN r4 OUTPUT In.1 'arg', In.3 'par', In.0 'out', In.4 'ret'

                      1513839768 ~2%     {4} r6 = JOIN r2 WITH DataFlowImpl::PathNodeImpl::getNodeEx#dispred#f0820431#ff_10#join_rhs ON FIRST 1 OUTPUT Lhs.3 'ret', Lhs.1 'out', Lhs.2 'arg', Rhs.1 'par'
                      0          ~0%     {5} r7 = JOIN r6 WITH boundedFastTC(DataFlowImpl::Subpaths::localStepToHidden#656de156#ff_10#higher_order_body,DataFlowImpl::Subpaths::subpaths#656de156#ffff#higher_order_body) ON FIRST 1 OUTPUT Lhs.1 'out', Lhs.2 'arg', Lhs.0, Lhs.3 'par', Rhs.1 'ret'
                      0          ~0%     {5} r8 = r7 AND NOT DataFlowImpl::PathNodeImpl::isHidden#dispred#f0820431#f(Lhs.4 'ret')
                      0          ~0%     {4} r9 = SCAN r8 OUTPUT In.1 'arg', In.3 'par', In.0 'out', In.4 'ret'

                      1513839768 ~5%     {4} r10 = r5 UNION r9
                      6689751    ~0%     {4} r11 = JOIN r10 WITH DataFlowImpl::PathNode::getASuccessor#dispred#f0820431#ff ON FIRST 2 OUTPUT Lhs.0 'arg', Lhs.1 'par', Lhs.3 'ret', Lhs.2 'out'
                                         return r11
```

After
```
[2022-05-03 11:44:10] (969s) Tuple counts for DataFlowImpl::Subpaths::subpaths#656de156#ffff/4@b26b969r after 11.8s:
                      8372525 ~0%     {3} r1 = JOIN DataFlowImpl::PathNode::getASuccessor#dispred#f0820431#ff_10#join_rhs WITH DataFlowImpl::PathNodeImpl::getNodeEx#dispred#f0820431#ff ON FIRST 1 OUTPUT Lhs.1 'arg', Rhs.1, Rhs.0
                      6673799 ~6%     {9} r2 = JOIN r1 WITH DataFlowImpl::Subpaths::subpaths03#656de156#fffffffff ON FIRST 2 OUTPUT Rhs.3, Rhs.4, Rhs.5, Rhs.7, Rhs.6, Rhs.8, Lhs.2 'par', Lhs.0 'arg', Rhs.2 'ret'

                      6637884 ~0%     {5} r3 = JOIN r2 WITH project#DataFlowImpl::pathNode#656de156#ffffffff_1234560#join_rhs ON FIRST 6 OUTPUT Lhs.6 'par', Lhs.7 'arg', Lhs.8 'ret', Rhs.6 'out', Lhs.8 'ret'

                      6637884 ~0%     {4} r4 = JOIN r2 WITH project#DataFlowImpl::pathNode#656de156#ffffffff_1234560#join_rhs ON FIRST 6 OUTPUT Rhs.6 'out', Lhs.6 'par', Lhs.7 'arg', Lhs.8 'ret'

                      51867   ~0%     {5} r5 = JOIN r4 WITH DataFlowImpl::PathNodeMid::projectToSink#dispred#f0820431#ff ON FIRST 1 OUTPUT Lhs.1 'par', Lhs.2 'arg', Lhs.3 'ret', Rhs.1 'out', Lhs.3 'ret'

                      6689751 ~0%     {5} r6 = r3 UNION r5
                      6689751 ~0%     {5} r7 = r6 AND NOT DataFlowImpl::PathNodeImpl::isHidden#dispred#f0820431#f(Lhs.4 'ret')
                      6689751 ~0%     {4} r8 = SCAN r7 OUTPUT In.1 'arg', In.0 'par', In.4 'ret', In.3 'out'

                      6637884 ~0%     {4} r9 = JOIN r2 WITH project#DataFlowImpl::pathNode#656de156#ffffffff_1234560#join_rhs ON FIRST 6 OUTPUT Lhs.8 'ret', Lhs.6 'par', Lhs.7 'arg', Rhs.6 'out'

                      51867   ~0%     {4} r10 = JOIN r4 WITH DataFlowImpl::PathNodeMid::projectToSink#dispred#f0820431#ff ON FIRST 1 OUTPUT Lhs.3 'ret', Lhs.1 'par', Lhs.2 'arg', Rhs.1 'out'

                      6689751 ~0%     {4} r11 = r9 UNION r10
                      0       ~0%     {5} r12 = JOIN r11 WITH boundedFastTC(DataFlowImpl::Subpaths::localStepToHidden#656de156#ff_10#higher_order_body,DataFlowImpl::Subpaths::subpaths#656de156#ffff#higher_order_body) ON FIRST 1 OUTPUT Lhs.1 'par', Lhs.2 'arg', Lhs.0, Lhs.3 'out', Rhs.1 'ret'
                      0       ~0%     {5} r13 = r12 AND NOT DataFlowImpl::PathNodeImpl::isHidden#dispred#f0820431#f(Lhs.4 'ret')
                      0       ~0%     {4} r14 = SCAN r13 OUTPUT In.1 'arg', In.0 'par', In.4 'ret', In.3 'out'

                      6689751 ~0%     {4} r15 = r8 UNION r14
                                      return r15
```
This commit is contained in:
Tom Hvitved
2022-05-03 11:31:58 +02:00
parent 806dacb0e3
commit 2b4fde74bb

View File

@@ -4206,10 +4206,11 @@ private module Subpaths {
pragma[nomagic]
private predicate subpaths01(
PathNodeImpl arg, ParamNodeEx par, SummaryCtxSome sc, CallContext innercc, ReturnKindExt kind,
NodeEx out, FlowState sout, AccessPath apout
NodeEx out, FlowState sout, CallContext ccout, AccessPath apout
) {
exists(Configuration config |
pathThroughCallable(arg, out, pragma[only_bind_into](sout), _, pragma[only_bind_into](apout)) and
pathThroughCallable(arg, out, pragma[only_bind_into](sout), ccout,
pragma[only_bind_into](apout)) and
pathIntoCallable(arg, par, _, _, innercc, sc, _, config) and
paramFlowsThrough(kind, pragma[only_bind_into](sout), innercc, sc,
pragma[only_bind_into](apout), _, unbindConf(config)) and
@@ -4224,10 +4225,11 @@ private module Subpaths {
pragma[nomagic]
private predicate subpaths02(
PathNode arg, ParamNodeEx par, SummaryCtxSome sc, CallContext innercc, ReturnKindExt kind,
NodeEx out, FlowState sout, AccessPath apout
NodeEx out, FlowState sout, CallContext ccout, AccessPath apout, Configuration config
) {
subpaths01(arg, par, sc, innercc, kind, out, sout, apout) and
out.asNode() = kind.getAnOutNode(_)
subpaths01(arg, par, sc, innercc, kind, out, sout, ccout, apout) and
out.asNode() = kind.getAnOutNode(_) and
config = getPathNodeConf(arg)
}
pragma[nomagic]
@@ -4238,12 +4240,14 @@ private module Subpaths {
*/
pragma[nomagic]
private predicate subpaths03(
PathNode arg, ParamNodeEx par, PathNodeMid ret, NodeEx out, FlowState sout, AccessPath apout
PathNodeMid arg, ParamNodeEx par, PathNodeMid ret, NodeEx out, FlowState sout,
CallContext ccout, AccessPath apout, SummaryCtx scout, Configuration config
) {
exists(SummaryCtxSome sc, CallContext innercc, ReturnKindExt kind, RetNodeEx retnode |
subpaths02(arg, par, sc, innercc, kind, out, sout, apout) and
pathNode(ret, retnode, sout, innercc, sc, apout, unbindConf(getPathNodeConf(arg)), _) and
kind = retnode.getKind()
subpaths02(arg, par, sc, innercc, kind, out, sout, ccout, apout, config) and
pathNode(ret, retnode, sout, innercc, sc, apout, config, _) and
kind = retnode.getKind() and
scout = arg.getSummaryCtx()
)
}
@@ -4263,16 +4267,17 @@ private module Subpaths {
* `ret -> out` is summarized as the edge `arg -> out`.
*/
predicate subpaths(PathNode arg, PathNodeImpl par, PathNodeImpl ret, PathNode out) {
exists(ParamNodeEx p, NodeEx o, FlowState sout, AccessPath apout, PathNodeMid out0 |
exists(
ParamNodeEx p, NodeEx o, FlowState sout, AccessPath apout, CallContext ccout,
SummaryCtx scout, PathNodeMid out0, Configuration config
|
pragma[only_bind_into](arg).getASuccessor() = par and
pragma[only_bind_into](arg).getASuccessor() = out0 and
subpaths03(arg, p, localStepToHidden*(ret), o, sout, apout) and
subpaths03(arg, p, localStepToHidden*(ret), o, sout, ccout, apout, scout, config) and
pathNode(out0, o, sout, ccout, scout, apout, config, _) and
not ret.isHidden() and
par.getNodeEx() = p and
out0.getNodeEx() = o and
out0.getState() = sout and
out0.getAp() = apout and
(out = out0 or out = out0.projectToSink())
par.getNodeEx() = p
|
out = out0 or out = out0.projectToSink()
)
}