track taint through string coercions for js/prototype-polluting-assignment

This commit is contained in:
Erik Krogh Kristensen
2021-05-16 23:10:08 +02:00
parent 2d65aa17db
commit 2a808b2cd6
3 changed files with 41 additions and 1 deletions

View File

@@ -31,7 +31,13 @@ class Configuration extends TaintTracking::Configuration {
node instanceof Sanitizer
or
// Concatenating with a string will in practice prevent the string `__proto__` from arising.
node instanceof StringOps::ConcatenationRoot
exists(StringOps::ConcatenationRoot root | node = root |
// Exclude the string coercion `"" + node` from this filter.
not (
strictcount(root.getALeaf()) = 2 and
root.getALeaf().getStringValue() = ""
)
)
}
override predicate isAdditionalFlowStep(

View File

@@ -56,6 +56,17 @@ nodes
| tst.js:45:9:45:11 | obj |
| tst.js:48:9:48:11 | obj |
| tst.js:48:9:48:11 | obj |
| tst.js:77:9:77:38 | taint |
| tst.js:77:17:77:38 | String( ... y.data) |
| tst.js:77:24:77:37 | req.query.data |
| tst.js:77:24:77:37 | req.query.data |
| tst.js:80:5:80:17 | object[taint] |
| tst.js:80:5:80:17 | object[taint] |
| tst.js:80:12:80:16 | taint |
| tst.js:82:5:82:22 | object["" + taint] |
| tst.js:82:5:82:22 | object["" + taint] |
| tst.js:82:12:82:21 | "" + taint |
| tst.js:82:17:82:21 | taint |
edges
| lib.js:1:38:1:40 | obj | lib.js:6:7:6:9 | obj |
| lib.js:1:38:1:40 | obj | lib.js:6:7:6:9 | obj |
@@ -113,6 +124,16 @@ edges
| tst.js:33:23:33:25 | obj | tst.js:45:9:45:11 | obj |
| tst.js:33:23:33:25 | obj | tst.js:48:9:48:11 | obj |
| tst.js:33:23:33:25 | obj | tst.js:48:9:48:11 | obj |
| tst.js:77:9:77:38 | taint | tst.js:80:12:80:16 | taint |
| tst.js:77:9:77:38 | taint | tst.js:82:17:82:21 | taint |
| tst.js:77:17:77:38 | String( ... y.data) | tst.js:77:9:77:38 | taint |
| tst.js:77:24:77:37 | req.query.data | tst.js:77:17:77:38 | String( ... y.data) |
| tst.js:77:24:77:37 | req.query.data | tst.js:77:17:77:38 | String( ... y.data) |
| tst.js:80:12:80:16 | taint | tst.js:80:5:80:17 | object[taint] |
| tst.js:80:12:80:16 | taint | tst.js:80:5:80:17 | object[taint] |
| tst.js:82:12:82:21 | "" + taint | tst.js:82:5:82:22 | object["" + taint] |
| tst.js:82:12:82:21 | "" + taint | tst.js:82:5:82:22 | object["" + taint] |
| tst.js:82:17:82:21 | taint | tst.js:82:12:82:21 | "" + taint |
#select
| lib.js:6:7:6:9 | obj | lib.js:1:43:1:46 | path | lib.js:6:7:6:9 | obj | This assignment may alter Object.prototype if a malicious '__proto__' string is injected from $@. | lib.js:1:43:1:46 | path | here |
| lib.js:15:3:15:14 | obj[path[0]] | lib.js:14:38:14:41 | path | lib.js:15:3:15:14 | obj[path[0]] | This assignment may alter Object.prototype if a malicious '__proto__' string is injected from $@. | lib.js:14:38:14:41 | path | here |
@@ -124,3 +145,5 @@ edges
| tst.js:39:9:39:11 | obj | tst.js:5:24:5:37 | req.query.data | tst.js:39:9:39:11 | obj | This assignment may alter Object.prototype if a malicious '__proto__' string is injected from $@. | tst.js:5:24:5:37 | req.query.data | here |
| tst.js:45:9:45:11 | obj | tst.js:5:24:5:37 | req.query.data | tst.js:45:9:45:11 | obj | This assignment may alter Object.prototype if a malicious '__proto__' string is injected from $@. | tst.js:5:24:5:37 | req.query.data | here |
| tst.js:48:9:48:11 | obj | tst.js:5:24:5:37 | req.query.data | tst.js:48:9:48:11 | obj | This assignment may alter Object.prototype if a malicious '__proto__' string is injected from $@. | tst.js:5:24:5:37 | req.query.data | here |
| tst.js:80:5:80:17 | object[taint] | tst.js:77:24:77:37 | req.query.data | tst.js:80:5:80:17 | object[taint] | This assignment may alter Object.prototype if a malicious '__proto__' string is injected from $@. | tst.js:77:24:77:37 | req.query.data | here |
| tst.js:82:5:82:22 | object["" + taint] | tst.js:77:24:77:37 | req.query.data | tst.js:82:5:82:22 | object["" + taint] | This assignment may alter Object.prototype if a malicious '__proto__' string is injected from $@. | tst.js:77:24:77:37 | req.query.data | here |

View File

@@ -71,3 +71,14 @@ class Box {
this.foo = 'bar'; // OK - 'this' won't refer to Object.prototype
}
}
app.get('/', (req, res) => {
let taint = String(req.query.data);
let object = {};
object[taint][taint] = taint; // NOT OK
object["" + taint]["" + taint] = taint; // NOT OK
});