Skip to content

Commit 41ef65e

Browse files
committed
DataFlow:Run overlay-informed if not diff-informed
To ensure good performance, always run data flow overlay-informed unless the configuration has opted in to being diff-informed. This change affects only databases with an overlay and therefore has no immediate production consequences.
1 parent 0c827a5 commit 41ef65e

File tree

3 files changed

+49
-3
lines changed

3 files changed

+49
-3
lines changed

java/ql/lib/semmle/code/java/dataflow/internal/DataFlowImplSpecific.qll

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ module;
66

77
private import semmle.code.Location
88
private import codeql.dataflow.DataFlow
9+
private import semmle.code.java.Overlay
910

1011
module Private {
1112
import DataFlowPrivate
@@ -29,4 +30,6 @@ module JavaDataFlow implements InputSig<Location> {
2930
predicate mayBenefitFromCallContext = Private::mayBenefitFromCallContext/1;
3031

3132
predicate viableImplInCallContext = Private::viableImplInCallContext/2;
33+
34+
predicate isEvaluatingInOverlay = isOverlay/0;
3235
}

shared/dataflow/codeql/dataflow/DataFlow.qll

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -349,6 +349,18 @@ signature module InputSig<LocationSig Location> {
349349

350350
/** Holds if `fieldFlowBranchLimit` should be ignored for flow going into/out of `c`. */
351351
default predicate ignoreFieldFlowBranchLimit(DataFlowCallable c) { none() }
352+
353+
/**
354+
* Holds if the evaluator is currently evaluating with an overlay. The
355+
* implementation of this predicate needs to be `overlay[local]`. For a
356+
* language with no overlay support, `none()` is a valid implementation.
357+
*
358+
* When called from a local predicate, this predicate holds if we are in the
359+
* overlay-only local evaluation. When called from a global predicate, this
360+
* predicate holds if we are evaluating globally with overlay and base both
361+
* visible.
362+
*/
363+
default predicate isEvaluatingInOverlay() { none() }
352364
}
353365

354366
module Configs<LocationSig Location, InputSig<Location> Lang> {

shared/dataflow/codeql/dataflow/internal/DataFlowImplStage1.qll

Lines changed: 34 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
* Provides an implementation of a fast initial pruning of global
55
* (interprocedural) data flow reachability (Stage 1).
66
*/
7-
overlay[local?]
7+
overlay[local?] // when this is removed, put `overlay[local?]` on `isOverlayNode`.
88
module;
99

1010
private import codeql.util.Unit
@@ -129,14 +129,38 @@ module MakeImplStage1<LocationSig Location, InputSig<Location> Lang> {
129129

130130
private module AlertFiltering = AlertFilteringImpl<Location>;
131131

132+
/**
133+
* Holds if the given node is visible in overlay-only local evaluation.
134+
*
135+
* This predicate needs to be `overlay[local?]`, either directly or
136+
* through annotations from an outer scope. If `Node` is global for the
137+
* language under analysis, then every node is considered an overlay
138+
* node, which means there will effectively be no overlay-based
139+
* filtering of sources and sinks.
140+
*/
141+
private predicate isOverlayNode(Node node) {
142+
isEvaluatingInOverlay() and
143+
// Any local node is an overlay node if we are evaluating in overlay mode
144+
exists(node)
145+
}
146+
147+
overlay[global]
132148
pragma[nomagic]
133149
private predicate isFilteredSource(Node source) {
134150
Config::isSource(source, _) and
135151
if Config::observeDiffInformedIncrementalMode()
136152
then AlertFiltering::filterByLocation(Config::getASelectedSourceLocation(source))
137-
else any()
153+
else (
154+
// If we are in base-only global evaluation, do not filter out any sources.
155+
not isEvaluatingInOverlay()
156+
or
157+
// If we are in global evaluation with an overlay present, restrict
158+
// sources to those visible in the overlay.
159+
isOverlayNode(source)
160+
)
138161
}
139162

163+
overlay[global]
140164
pragma[nomagic]
141165
private predicate isFilteredSink(Node sink) {
142166
(
@@ -145,7 +169,14 @@ module MakeImplStage1<LocationSig Location, InputSig<Location> Lang> {
145169
) and
146170
if Config::observeDiffInformedIncrementalMode()
147171
then AlertFiltering::filterByLocation(Config::getASelectedSinkLocation(sink))
148-
else any()
172+
else (
173+
// If we are in base-only global evaluation, do not filter out any sinks.
174+
not isEvaluatingInOverlay()
175+
or
176+
// If we are in global evaluation with an overlay present, restrict
177+
// sinks to those visible in the overlay.
178+
isOverlayNode(sink)
179+
)
149180
}
150181

151182
private predicate hasFilteredSource() { isFilteredSource(_) }

0 commit comments

Comments
 (0)