JS: Make more general-purpose data flow things local

This commit is contained in:
Asger F
2025-10-10 09:46:49 +02:00
parent b1418e1d70
commit c09563f775
5 changed files with 15 additions and 1 deletions

View File

@@ -1,6 +1,8 @@
/**
* Provides classes for reasoning about `extend`-like functions.
*/
overlay[local]
module;
import javascript
@@ -169,6 +171,7 @@ private class FunctionalExtendCallShallow extends ExtendCall {
*
* Since all object properties are preserved, we model this as a value-preserving step.
*/
overlay[global]
private class ExtendCallStep extends PreCallGraphStep {
override predicate step(DataFlow::Node pred, DataFlow::Node succ) {
exists(ExtendCall extend |
@@ -184,6 +187,7 @@ private import semmle.javascript.dataflow.internal.PreCallGraphStep
/**
* A step through a cloning library, such as `clone` or `fclone`.
*/
overlay[global]
private class CloneStep extends PreCallGraphStep {
override predicate step(DataFlow::Node pred, DataFlow::Node succ) {
exists(DataFlow::CallNode call |

View File

@@ -1,6 +1,8 @@
/**
* Provides predicates for associating qualified names with data flow nodes.
*/
overlay[local]
module;
import javascript
private import semmle.javascript.dataflow.InferredTypes
@@ -657,7 +659,7 @@ module AccessPath {
*/
cached
predicate hasDominatingWrite(DataFlow::PropRead read) {
Stages::TypeTracking::ref() and
Stages::DataFlowStage::ref() and
// within the same basic block.
exists(ReachableBasicBlock bb, Root root, string path, int ranking |
read.asExpr() = rankedAccessPath(bb, root, path, ranking, AccessPathRead()) and

View File

@@ -15,6 +15,7 @@ private import AngularJS
/**
* Holds if `nd` is a reference to the `angular` variable.
*/
overlay[local]
DataFlow::SourceNode angular() {
// either as a global
result = DataFlow::globalVarRef("angular")

View File

@@ -9,6 +9,7 @@ module LodashUnderscore {
/**
* A data flow node that accesses a given member of `lodash` or `underscore`.
*/
overlay[local]
abstract class Member extends DataFlow::SourceNode {
/** Gets the name of the accessed member. */
abstract string getName();
@@ -17,6 +18,7 @@ module LodashUnderscore {
/**
* An import of `lodash` or `underscore` accessing a given member of that package.
*/
overlay[local]
private class DefaultMember extends Member {
string name;
@@ -39,12 +41,14 @@ module LodashUnderscore {
* In addition to normal imports, this supports per-method imports such as `require("lodash.map")` and `require("lodash/map")`.
* In addition, the global variable `_` is assumed to refer to `lodash` or `underscore`.
*/
overlay[local]
DataFlow::SourceNode member(string name) { result.(Member).getName() = name }
/**
* Holds if `name` is the name of a member exported from the `lodash` package
* which has a corresponding `lodash.xxx` NPM package.
*/
overlay[local]
private predicate isLodashMember(string name) {
// Can be generated using Object.keys(require('lodash'))
name =

View File

@@ -4,6 +4,8 @@
* Subclass `PropertyProjection` to refine the behavior of the analysis on existing property projections.
* Subclass `CustomPropertyProjection` to introduce new kinds of property projections.
*/
overlay[local]
module;
import javascript
@@ -137,6 +139,7 @@ private class VarArgsPropertyProjection extends PropertyProjection::Range {
/**
* A taint step for a property projection.
*/
overlay[global]
private class PropertyProjectionTaintStep extends TaintTracking::SharedTaintStep {
override predicate step(DataFlow::Node pred, DataFlow::Node succ) {
// reading from a tainted object yields a tainted result