Skip to content

Commit 594da1a

Browse files
committed
C++: Speedup 'isSuccessor'.
1 parent e58b99d commit 594da1a

File tree

1 file changed

+83
-2
lines changed

1 file changed

+83
-2
lines changed

cpp/ql/lib/experimental/semmle/code/cpp/dataflow/ProductFlow.qll

Lines changed: 83 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -343,14 +343,95 @@ module ProductFlow {
343343
)
344344
}
345345

346+
pragma[assume_small_delta]
347+
pragma[nomagic]
348+
private predicate fwdLocalPathStep1(Flow1::PathNode n) {
349+
fwdReachableInterprocEntry(n, _)
350+
or
351+
exists(Flow1::PathNode mid |
352+
fwdLocalPathStep1(mid) and
353+
localPathStep1(mid, n)
354+
)
355+
}
356+
357+
pragma[assume_small_delta]
358+
pragma[nomagic]
359+
private predicate revLocalPathStep1(Flow1::PathNode n) {
360+
fwdLocalPathStep1(n) and
361+
(
362+
isSinkPair(n, _)
363+
or
364+
interprocEdgePair(n, _, _, _)
365+
or
366+
exists(Flow1::PathNode mid |
367+
revLocalPathStep1(mid) and
368+
localPathStep1(n, mid)
369+
)
370+
)
371+
}
372+
373+
pragma[assume_small_delta]
374+
private predicate prunedLocalPathStep1(Flow1::PathNode n1, Flow1::PathNode n2) {
375+
revLocalPathStep1(n1) and
376+
revLocalPathStep1(n2) and
377+
localPathStep1(n1, n2)
378+
}
379+
380+
pragma[nomagic]
381+
private predicate fwdLocalPathStep2(Flow2::PathNode n) {
382+
fwdReachableInterprocEntry(_, n)
383+
or
384+
exists(Flow2::PathNode mid |
385+
fwdLocalPathStep2(mid) and
386+
localPathStep2(mid, n)
387+
)
388+
}
389+
390+
pragma[assume_small_delta]
391+
pragma[nomagic]
392+
private predicate revLocalPathStep2(Flow2::PathNode n) {
393+
fwdLocalPathStep2(n) and
394+
(
395+
isSinkPair(_, n)
396+
or
397+
interprocEdgePair(_, n, _, _)
398+
or
399+
exists(Flow2::PathNode mid |
400+
revLocalPathStep2(mid) and
401+
localPathStep2(n, mid)
402+
)
403+
)
404+
}
405+
406+
pragma[assume_small_delta]
407+
private predicate prunedLocalPathStep2(Flow2::PathNode n1, Flow2::PathNode n2) {
408+
revLocalPathStep2(n1) and
409+
revLocalPathStep2(n2) and
410+
localPathStep2(n1, n2)
411+
}
412+
413+
private predicate localPathStep1SuccPlus(Flow1::PathNode n1, Flow1::PathNode n2) =
414+
fastTC(prunedLocalPathStep1/2)(n1, n2)
415+
416+
private predicate localPathStep2SuccPlus(Flow2::PathNode n1, Flow2::PathNode n2) =
417+
fastTC(prunedLocalPathStep2/2)(n1, n2)
418+
419+
private predicate localPathStep1Tc(Flow1::PathNode n1, Flow1::PathNode n2) {
420+
localPathStep1SuccPlus(n1, n2) or n1 = n2
421+
}
422+
423+
private predicate localPathStep2Tc(Flow2::PathNode n1, Flow2::PathNode n2) {
424+
localPathStep2SuccPlus(n1, n2) or n1 = n2
425+
}
426+
346427
bindingset[pred1, pred2]
347428
bindingset[succ1, succ2]
348429
private predicate isSuccessor(
349430
Flow1::PathNode pred1, Flow2::PathNode pred2, Flow1::PathNode succ1, Flow2::PathNode succ2
350431
) {
351432
exists(Flow1::PathNode mid1, Flow2::PathNode mid2 |
352-
localPathStep1*(pred1, mid1) and
353-
localPathStep2*(pred2, mid2)
433+
localPathStep1Tc(pred1, mid1) and
434+
localPathStep2Tc(pred2, mid2)
354435
|
355436
isSinkPair(mid1, mid2) and
356437
succ1 = mid1 and

0 commit comments

Comments
 (0)