Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 133909d

Browse files
committed
Python taint-tracking: Lengthen steps to better conform to old edge relation.
1 parent da6a669 commit 133909d

2 files changed

Lines changed: 43 additions & 22 deletions

File tree

python/ql/src/semmle/python/dataflow/Implementation.qll

Lines changed: 41 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -120,11 +120,16 @@ class TaintTrackingNode extends TTaintTrackingNode {
120120
}
121121

122122
TaintTrackingNode getASuccessor() {
123-
exists(DataFlow::Node node, TaintTrackingContext ctx, AttributePath path,
124-
TaintKind kind, TaintTracking::Configuration config |
125-
result = TTaintTrackingNode_(node, ctx, path, kind, config) and
126-
config.(TaintTrackingImplementation).flowStep(this, node, ctx, path, kind)
127-
)
123+
result.isVisible() and
124+
result = this.getAnInvisibleSuccessor*().getAShortStepSuccessor()
125+
}
126+
127+
TaintTrackingNode getAnInvisibleSuccessor() {
128+
result = this.getAShortStepSuccessor() and not result.isVisible()
129+
}
130+
131+
private TaintTrackingNode getAShortStepSuccessor() {
132+
this.getConfiguration().(TaintTrackingImplementation).flowStep(this, result)
128133
}
129134

130135
predicate isSource() {
@@ -135,6 +140,11 @@ class TaintTrackingNode extends TTaintTrackingNode {
135140
this.getConfiguration().(TaintTrackingImplementation).isPathSink(this)
136141
}
137142

143+
/** Holds if this node should be presented to the user as part of a path */
144+
predicate isVisible() {
145+
exists(this.getNode().asCfgNode())
146+
}
147+
138148
}
139149

140150
class TaintTrackingImplementation extends string {
@@ -274,8 +284,8 @@ class TaintTrackingImplementation extends string {
274284
this.fromImportStep(src, node, context, path, kind)
275285
or
276286
this.attributeLoadStep(src, node, context, path, kind)
277-
//or
278-
//this.getattrStep(src, node, context, path, kind)
287+
or
288+
this.getattrStep(src, node, context, path, kind)
279289
or
280290
this.useStep(src, node, context, path, kind)
281291
or
@@ -284,10 +294,12 @@ class TaintTrackingImplementation extends string {
284294
this.returnFlowStep(src, node, context, path, kind)
285295
or
286296
this.iterationStep(src, node, context, path, kind)
287-
//or
288-
//this.yieldStep(src, node, context, path, kind)
289-
//or
290-
//this.subscriptStep(src, node, context, path, kind)
297+
or
298+
this.yieldStep(src, node, context, path, kind)
299+
or
300+
this.subscriptStep(src, node, context, path, kind)
301+
or
302+
this.parameterStep(src, node, context, path, kind)
291303
or
292304
this.ifExpStep(src, node, context, path, kind)
293305
or
@@ -346,15 +358,20 @@ class TaintTrackingImplementation extends string {
346358

347359
pragma [noinline]
348360
predicate getattrStep(TaintTrackingNode src, DataFlow::Node node, TaintTrackingContext context, AttributePath path, TaintKind kind) {
349-
exists(DataFlow::Node srcnode, AttributePath srcpath, string attrname |
350-
src = TTaintTrackingNode_(srcnode, context, srcpath, kind, this) and
361+
exists(DataFlow::Node srcnode, AttributePath srcpath, TaintKind srckind, string attrname |
362+
src = TTaintTrackingNode_(srcnode, context, srcpath, srckind, this) and
351363
exists(CallNode call, ControlFlowNode arg |
352364
call = node.asCfgNode() and
353365
call.getFunction().pointsTo(ObjectInternal::builtin("getattr")) and
354366
arg = call.getArg(0) and
355367
attrname = call.getArg(1).getNode().(StrConst).getText() and
356-
arg = srcnode.asCfgNode() and
357-
path = srcpath.fromAttribute(attrname)
368+
arg = srcnode.asCfgNode()
369+
|
370+
path = srcpath.fromAttribute(attrname) and
371+
kind = srckind
372+
or
373+
path = srcpath and
374+
kind = srckind.getTaintOfAttribute(attrname)
358375
)
359376
)
360377
}
@@ -416,6 +433,15 @@ class TaintTrackingImplementation extends string {
416433
)
417434
}
418435

436+
pragma [noinline]
437+
predicate parameterStep(TaintTrackingNode src, DataFlow::Node node, TaintTrackingContext context, AttributePath path, TaintKind kind) {
438+
exists(CallNode call, PythonFunctionObjectInternal pyfunc, int arg |
439+
this.callWithTaintedArgument(src, call, _, pyfunc, arg, path, kind) and
440+
node.asCfgNode() = pyfunc.getParameter(arg) and
441+
context = TParamContext(kind, path, arg)
442+
)
443+
}
444+
419445
pragma [noinline]
420446
predicate yieldStep(TaintTrackingNode src, DataFlow::Node node, TaintTrackingContext context, AttributePath path, TaintKind kind) {
421447
exists(DataFlow::Node srcnode, TaintKind itemkind |
@@ -519,13 +545,6 @@ class TaintTrackingImplementation extends string {
519545

520546
pragma [noinline]
521547
predicate taintedParameterDefinition(TaintTrackingNode src, ParameterDefinition defn, TaintTrackingContext context, AttributePath path, TaintKind kind) {
522-
exists(CallNode call, PythonFunctionObjectInternal pyfunc, int arg |
523-
this.callWithTaintedArgument(src, call, _, pyfunc, arg, path, kind) and
524-
defn.getDefiningNode() = pyfunc.getParameter(arg) and
525-
context = TParamContext(kind, path, arg)
526-
)
527-
or
528-
/* Tainted parameter (usually user-defined) */
529548
exists(DataFlow::Node srcnode |
530549
src = TTaintTrackingNode_(srcnode, context, path, kind, this) and
531550
srcnode.asCfgNode() = defn.getDefiningNode()

python/ql/src/semmle/python/security/Paths.qll

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,3 +8,5 @@ query predicate edges(TaintTrackingNode fromnode, TaintTrackingNode tonode) {
88
/* Don't record flow past sinks */
99
not fromnode.isSink()
1010
}
11+
12+

0 commit comments

Comments
 (0)