From 18d0b2802455a025129685b7628886d0d5d38be6 Mon Sep 17 00:00:00 2001
From: amammad <77095239+amammad@users.noreply.github.com>
Date: Sun, 10 Dec 2023 20:27:21 +0100
Subject: [PATCH 1/9] v1
---
.../Security/CWE-099/EnvInjection.qhelp | 36 +++++++++++
.../Security/CWE-099/EnvInjection.ql | 31 +++++++++
.../CWE-099/EnvInjectionWithKeyControl.ql | 64 +++++++++++++++++++
.../Security/CWE-099/examples/Bad.js | 8 +++
.../Security/CWE-099/EnvInjection.expected | 22 +++++++
.../Security/CWE-099/EnvInjection.qlref | 1 +
.../experimental/Security/CWE-099/test.js | 9 +++
7 files changed, 171 insertions(+)
create mode 100644 javascript/ql/src/experimental/Security/CWE-099/EnvInjection.qhelp
create mode 100644 javascript/ql/src/experimental/Security/CWE-099/EnvInjection.ql
create mode 100644 javascript/ql/src/experimental/Security/CWE-099/EnvInjectionWithKeyControl.ql
create mode 100644 javascript/ql/src/experimental/Security/CWE-099/examples/Bad.js
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/test.js
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.qhelp b/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.qhelp
new file mode 100644
index 000000000000..65c324b16d78
--- /dev/null
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.qhelp
@@ -0,0 +1,36 @@
+
+
+
+
+
+
+ Assigning Value to environment variables from user-controllable data is not safe.
+
+
+
+
+
+
+
+ Restrict this operation only to privileged users or only for some not important environment variables.
+
+
+
+
+
+
+
+ The following example allows unauthorized users to assign a value to a critical environment variable.
+
+
+
+
+
+
+
+ Admin account TakeOver in mintplex-labs/anything-llm
+
+
+
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.ql b/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.ql
new file mode 100644
index 000000000000..a5bb557a2f20
--- /dev/null
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.ql
@@ -0,0 +1,31 @@
+/**
+ * @name User controlled environment injection
+ * @description full control on creating environment variables from user controlled data is not secure
+ * @kind path-problem
+ * @id js/envinjection
+ * @problem.severity error
+ * @security-severity 7.5
+ * @precision medium
+ * @tags security
+ * external/cwe/cwe-089
+ */
+
+import javascript
+import DataFlow::PathGraph
+
+/** A taint tracking configuration for unsafe environment injection. */
+class Configuration extends TaintTracking::Configuration {
+ Configuration() { this = "envInjection" }
+
+ override predicate isSource(DataFlow::Node source) { source instanceof RemoteFlowSource }
+
+ override predicate isSink(DataFlow::Node sink) {
+ sink = API::moduleImport("process").getMember("env").getAMember().asSink()
+ }
+}
+
+
+from Configuration cfg, DataFlow::PathNode source, DataFlow::PathNode sink
+where cfg.hasFlowPath(source, sink)
+select sink.getNode(), source, sink, "this environment variable assignment is $@.",
+ source.getNode(), "user controllable"
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvInjectionWithKeyControl.ql b/javascript/ql/src/experimental/Security/CWE-099/EnvInjectionWithKeyControl.ql
new file mode 100644
index 000000000000..02105cf51819
--- /dev/null
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvInjectionWithKeyControl.ql
@@ -0,0 +1,64 @@
+/**
+ * @name User controlled environment injection
+ * @description full control on creating environment variables from user controlled data is not secure
+ * @kind path-problem
+ * @id js/envinjection
+ * @problem.severity error
+ * @security-severity 7.5
+ * @precision medium
+ * @tags security
+ * external/cwe/cwe-089
+ */
+
+import javascript
+import DataFlow::PathGraph
+
+/** A taint tracking configuration for unsafe environment injection. */
+class Configuration extends TaintTracking::Configuration {
+ Configuration() { this = "envInjection" }
+
+ override predicate isSource(DataFlow::Node source) { source instanceof RemoteFlowSource }
+
+ override predicate isSink(DataFlow::Node sink) {
+ NodeJSLib::process()
+ .getAPropertyRead("env")
+ .asExpr()
+ .getParent()
+ .(IndexExpr)
+ .getAChildExpr()
+ .(VarRef) = sink.asExpr()
+ or
+ sink = API::moduleImport("process").getMember("env").getAMember().asSink()
+ }
+
+ override predicate isAdditionalTaintStep(DataFlow::Node pred, DataFlow::Node succ) {
+ exists(DataFlow::InvokeNode ikn |
+ ikn = DataFlow::globalVarRef("Object").getAMemberInvocation("keys")
+ |
+ pred = ikn.getArgument(0) and
+ (
+ succ = ikn.getAChainedMethodCall(["filter", "map"]) or
+ succ = ikn or
+ succ = ikn.getAChainedMethodCall("forEach").getABoundCallbackParameter(0, 0)
+ )
+ )
+ }
+}
+
+from
+ Configuration cfg, Configuration cfg2, DataFlow::PathNode source, DataFlow::PathNode sink,
+ DataFlow::PathNode sink2
+where
+ cfg.hasFlowPath(source, sink) and
+ sink.getNode() = API::moduleImport("process").getMember("env").getAMember().asSink() and
+ cfg2.hasFlowPath(source, sink2) and
+ sink.getNode().asExpr() =
+ NodeJSLib::process()
+ .getAPropertyRead("env")
+ .asExpr()
+ .getParent()
+ .(IndexExpr)
+ .getAChildExpr()
+ .(VarRef)
+select sink.getNode(), source, sink, "this environment variable assignment is $@.",
+ source.getNode(), "user controllable"
diff --git a/javascript/ql/src/experimental/Security/CWE-099/examples/Bad.js b/javascript/ql/src/experimental/Security/CWE-099/examples/Bad.js
new file mode 100644
index 000000000000..6f0cc7fc4290
--- /dev/null
+++ b/javascript/ql/src/experimental/Security/CWE-099/examples/Bad.js
@@ -0,0 +1,8 @@
+const http = require('node:http');
+
+http.createServer((req, res) => {
+ const { EnvValue } = req.body;
+ process.env["A_Critical_Env"] = EnvValue; // NOT OK
+
+ res.end('env has been injected!');
+});
\ No newline at end of file
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected
new file mode 100644
index 000000000000..39b8fe76100f
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected
@@ -0,0 +1,22 @@
+nodes
+| test.js:4:9:4:20 | { EnvValue } |
+| test.js:4:9:4:31 | EnvValue |
+| test.js:4:11:4:18 | EnvValue |
+| test.js:4:24:4:31 | req.body |
+| test.js:4:24:4:31 | req.body |
+| test.js:5:35:5:42 | EnvValue |
+| test.js:5:35:5:42 | EnvValue |
+| test.js:6:23:6:30 | EnvValue |
+| test.js:6:23:6:30 | EnvValue |
+edges
+| test.js:4:9:4:20 | { EnvValue } | test.js:4:11:4:18 | EnvValue |
+| test.js:4:9:4:31 | EnvValue | test.js:5:35:5:42 | EnvValue |
+| test.js:4:9:4:31 | EnvValue | test.js:5:35:5:42 | EnvValue |
+| test.js:4:9:4:31 | EnvValue | test.js:6:23:6:30 | EnvValue |
+| test.js:4:9:4:31 | EnvValue | test.js:6:23:6:30 | EnvValue |
+| test.js:4:11:4:18 | EnvValue | test.js:4:9:4:31 | EnvValue |
+| test.js:4:24:4:31 | req.body | test.js:4:9:4:20 | { EnvValue } |
+| test.js:4:24:4:31 | req.body | test.js:4:9:4:20 | { EnvValue } |
+#select
+| test.js:5:35:5:42 | EnvValue | test.js:4:24:4:31 | req.body | test.js:5:35:5:42 | EnvValue | this environment variable assignment is $@. | test.js:4:24:4:31 | req.body | user controllable |
+| test.js:6:23:6:30 | EnvValue | test.js:4:24:4:31 | req.body | test.js:6:23:6:30 | EnvValue | this environment variable assignment is $@. | test.js:4:24:4:31 | req.body | user controllable |
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref b/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref
new file mode 100644
index 000000000000..db98debeccdd
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref
@@ -0,0 +1 @@
+experimental/Security/CWE-099/EnvInjection.ql
\ No newline at end of file
diff --git a/javascript/ql/test/experimental/Security/CWE-099/test.js b/javascript/ql/test/experimental/Security/CWE-099/test.js
new file mode 100644
index 000000000000..6e592e31ff25
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/test.js
@@ -0,0 +1,9 @@
+const http = require('node:http');
+
+http.createServer((req, res) => {
+ const { EnvValue } = req.body;
+ process.env["A_Critical_Env"] = EnvValue; // NOT OK
+ process.env[AKey] = EnvValue; // NOT OK
+
+ res.end('env has been injected!');
+});
\ No newline at end of file
From 102f09aa2348a6a2aef97ab3a7c94f5213153069 Mon Sep 17 00:00:00 2001
From: amammad <77095239+amammad@users.noreply.github.com>
Date: Sun, 10 Dec 2023 20:33:00 +0100
Subject: [PATCH 2/9] extend tests
---
.../test/experimental/Security/CWE-099/EnvInjection.expected | 5 +++++
javascript/ql/test/experimental/Security/CWE-099/test.js | 1 +
2 files changed, 6 insertions(+)
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected
index 39b8fe76100f..7461f72ee7eb 100644
--- a/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected
@@ -8,15 +8,20 @@ nodes
| test.js:5:35:5:42 | EnvValue |
| test.js:6:23:6:30 | EnvValue |
| test.js:6:23:6:30 | EnvValue |
+| test.js:7:22:7:29 | EnvValue |
+| test.js:7:22:7:29 | EnvValue |
edges
| test.js:4:9:4:20 | { EnvValue } | test.js:4:11:4:18 | EnvValue |
| test.js:4:9:4:31 | EnvValue | test.js:5:35:5:42 | EnvValue |
| test.js:4:9:4:31 | EnvValue | test.js:5:35:5:42 | EnvValue |
| test.js:4:9:4:31 | EnvValue | test.js:6:23:6:30 | EnvValue |
| test.js:4:9:4:31 | EnvValue | test.js:6:23:6:30 | EnvValue |
+| test.js:4:9:4:31 | EnvValue | test.js:7:22:7:29 | EnvValue |
+| test.js:4:9:4:31 | EnvValue | test.js:7:22:7:29 | EnvValue |
| test.js:4:11:4:18 | EnvValue | test.js:4:9:4:31 | EnvValue |
| test.js:4:24:4:31 | req.body | test.js:4:9:4:20 | { EnvValue } |
| test.js:4:24:4:31 | req.body | test.js:4:9:4:20 | { EnvValue } |
#select
| test.js:5:35:5:42 | EnvValue | test.js:4:24:4:31 | req.body | test.js:5:35:5:42 | EnvValue | this environment variable assignment is $@. | test.js:4:24:4:31 | req.body | user controllable |
| test.js:6:23:6:30 | EnvValue | test.js:4:24:4:31 | req.body | test.js:6:23:6:30 | EnvValue | this environment variable assignment is $@. | test.js:4:24:4:31 | req.body | user controllable |
+| test.js:7:22:7:29 | EnvValue | test.js:4:24:4:31 | req.body | test.js:7:22:7:29 | EnvValue | this environment variable assignment is $@. | test.js:4:24:4:31 | req.body | user controllable |
diff --git a/javascript/ql/test/experimental/Security/CWE-099/test.js b/javascript/ql/test/experimental/Security/CWE-099/test.js
index 6e592e31ff25..9d034cfed904 100644
--- a/javascript/ql/test/experimental/Security/CWE-099/test.js
+++ b/javascript/ql/test/experimental/Security/CWE-099/test.js
@@ -4,6 +4,7 @@ http.createServer((req, res) => {
const { EnvValue } = req.body;
process.env["A_Critical_Env"] = EnvValue; // NOT OK
process.env[AKey] = EnvValue; // NOT OK
+ process.env.AKey = EnvValue; // NOT OK
res.end('env has been injected!');
});
\ No newline at end of file
From 1fc481ce81e46f234bef8dbfca86b60a29452fc9 Mon Sep 17 00:00:00 2001
From: am0o0 <77095239+am0o0@users.noreply.github.com>
Date: Sat, 25 May 2024 20:43:36 +0200
Subject: [PATCH 3/9] v2: it is basically the first stable version :))
---
.../CWE-099/EnvValueAndKeyInjection.qhelp | 36 +++++++++++++++++
...yControl.ql => EnvValueAndKeyInjection.ql} | 18 ++++-----
...njection.qhelp => EnvValueInjection.qhelp} | 2 +-
.../{EnvInjection.ql => EnvValueInjection.ql} | 7 ++--
.../examples/Bad_Value_And_Key_Assignment.js | 8 ++++
.../{Bad.js => Bad_Value_Assignment.js} | 0
.../Security/CWE-099/EnvInjection.qlref | 1 -
.../EnvInjection.expected | 39 +++++++++++++++++++
.../EnvValueAndKeyInjection.expected | 39 +++++++++++++++++++
.../EnvValueAndKeyInjection.qlref | 1 +
.../CWE-099/EnvValueAndKeyInjection/test.js | 11 ++++++
.../EnvValueInjection.expected} | 0
.../EnvValueInjection/EnvValueInjection.qlref | 1 +
.../CWE-099/{ => EnvValueInjection}/test.js | 2 +-
14 files changed, 149 insertions(+), 16 deletions(-)
create mode 100644 javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
rename javascript/ql/src/experimental/Security/CWE-099/{EnvInjectionWithKeyControl.ql => EnvValueAndKeyInjection.ql} (74%)
rename javascript/ql/src/experimental/Security/CWE-099/{EnvInjection.qhelp => EnvValueInjection.qhelp} (92%)
rename javascript/ql/src/experimental/Security/CWE-099/{EnvInjection.ql => EnvValueInjection.ql} (81%)
create mode 100644 javascript/ql/src/experimental/Security/CWE-099/examples/Bad_Value_And_Key_Assignment.js
rename javascript/ql/src/experimental/Security/CWE-099/examples/{Bad.js => Bad_Value_Assignment.js} (100%)
delete mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.qlref
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
rename javascript/ql/test/experimental/Security/CWE-099/{EnvInjection.expected => EnvValueInjection/EnvValueInjection.expected} (100%)
create mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/EnvValueInjection.qlref
rename javascript/ql/test/experimental/Security/CWE-099/{ => EnvValueInjection}/test.js (98%)
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
new file mode 100644
index 000000000000..fbf9bf81e733
--- /dev/null
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
@@ -0,0 +1,36 @@
+
+
+
+
+
+
+ Controlling the value of arbitrary environment variables from user-controllable data is not safe.
+
+
+
+
+
+
+
+ Restrict this operation only to privileged users or only for some not important environment variables.
+
+
+
+
+
+
+
+ The following example allows unauthorized users to assign a value to any environment variable.
+
+
+
+
+
+
+
+ Admin account TakeOver in mintplex-labs/anything-llm
+
+
+
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvInjectionWithKeyControl.ql b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.ql
similarity index 74%
rename from javascript/ql/src/experimental/Security/CWE-099/EnvInjectionWithKeyControl.ql
rename to javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.ql
index 02105cf51819..152552279cd6 100644
--- a/javascript/ql/src/experimental/Security/CWE-099/EnvInjectionWithKeyControl.ql
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.ql
@@ -1,8 +1,8 @@
/**
- * @name User controlled environment injection
- * @description full control on creating environment variables from user controlled data is not secure
+ * @name User controlled arbitrary environment variable injection
+ * @description creating arbitrary environment variables from user controlled data is not secure
* @kind path-problem
- * @id js/envinjection
+ * @id js/env-key-and-value-injection
* @problem.severity error
* @security-severity 7.5
* @precision medium
@@ -46,13 +46,13 @@ class Configuration extends TaintTracking::Configuration {
}
from
- Configuration cfg, Configuration cfg2, DataFlow::PathNode source, DataFlow::PathNode sink,
+ Configuration cfg, Configuration cfg2, DataFlow::PathNode source, DataFlow::PathNode sink1,
DataFlow::PathNode sink2
where
- cfg.hasFlowPath(source, sink) and
- sink.getNode() = API::moduleImport("process").getMember("env").getAMember().asSink() and
+ cfg.hasFlowPath(source, sink1) and
+ sink1.getNode() = API::moduleImport("process").getMember("env").getAMember().asSink() and
cfg2.hasFlowPath(source, sink2) and
- sink.getNode().asExpr() =
+ sink2.getNode().asExpr() =
NodeJSLib::process()
.getAPropertyRead("env")
.asExpr()
@@ -60,5 +60,5 @@ where
.(IndexExpr)
.getAChildExpr()
.(VarRef)
-select sink.getNode(), source, sink, "this environment variable assignment is $@.",
- source.getNode(), "user controllable"
+select sink1.getNode(), source, sink1, "arbitrary environment variable assignment from this $@.",
+ source.getNode(), "user controllable source"
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.qhelp b/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.qhelp
similarity index 92%
rename from javascript/ql/src/experimental/Security/CWE-099/EnvInjection.qhelp
rename to javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.qhelp
index 65c324b16d78..cbc6a04297d4 100644
--- a/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.qhelp
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.qhelp
@@ -25,7 +25,7 @@
The following example allows unauthorized users to assign a value to a critical environment variable.
-
+
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.ql b/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.ql
similarity index 81%
rename from javascript/ql/src/experimental/Security/CWE-099/EnvInjection.ql
rename to javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.ql
index a5bb557a2f20..3eb9f2305644 100644
--- a/javascript/ql/src/experimental/Security/CWE-099/EnvInjection.ql
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.ql
@@ -1,8 +1,8 @@
/**
- * @name User controlled environment injection
- * @description full control on creating environment variables from user controlled data is not secure
+ * @name User controlled environment variable value injection
+ * @description assigning important environment variables from user controlled data is not secure
* @kind path-problem
- * @id js/envinjection
+ * @id js/env-value-injection
* @problem.severity error
* @security-severity 7.5
* @precision medium
@@ -24,7 +24,6 @@ class Configuration extends TaintTracking::Configuration {
}
}
-
from Configuration cfg, DataFlow::PathNode source, DataFlow::PathNode sink
where cfg.hasFlowPath(source, sink)
select sink.getNode(), source, sink, "this environment variable assignment is $@.",
diff --git a/javascript/ql/src/experimental/Security/CWE-099/examples/Bad_Value_And_Key_Assignment.js b/javascript/ql/src/experimental/Security/CWE-099/examples/Bad_Value_And_Key_Assignment.js
new file mode 100644
index 000000000000..a6553f9c0ff3
--- /dev/null
+++ b/javascript/ql/src/experimental/Security/CWE-099/examples/Bad_Value_And_Key_Assignment.js
@@ -0,0 +1,8 @@
+const http = require('node:http');
+
+http.createServer((req, res) => {
+ const { EnvValue, EnvKey } = req.body;
+ process.env[EnvKey] = EnvValue; // NOT OK
+
+ res.end('env has been injected!');
+});
\ No newline at end of file
diff --git a/javascript/ql/src/experimental/Security/CWE-099/examples/Bad.js b/javascript/ql/src/experimental/Security/CWE-099/examples/Bad_Value_Assignment.js
similarity index 100%
rename from javascript/ql/src/experimental/Security/CWE-099/examples/Bad.js
rename to javascript/ql/src/experimental/Security/CWE-099/examples/Bad_Value_Assignment.js
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref b/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref
deleted file mode 100644
index db98debeccdd..000000000000
--- a/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.qlref
+++ /dev/null
@@ -1 +0,0 @@
-experimental/Security/CWE-099/EnvInjection.ql
\ No newline at end of file
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected
new file mode 100644
index 000000000000..9659366f6f00
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected
@@ -0,0 +1,39 @@
+nodes
+| test.js:5:9:5:28 | { EnvValue, EnvKey } |
+| test.js:5:9:5:39 | EnvKey |
+| test.js:5:9:5:39 | EnvValue |
+| test.js:5:11:5:18 | EnvValue |
+| test.js:5:21:5:26 | EnvKey |
+| test.js:5:32:5:39 | req.body |
+| test.js:5:32:5:39 | req.body |
+| test.js:6:15:6:20 | EnvKey |
+| test.js:6:15:6:20 | EnvKey |
+| test.js:6:25:6:32 | EnvValue |
+| test.js:6:25:6:32 | EnvValue |
+| test.js:7:15:7:20 | EnvKey |
+| test.js:7:15:7:20 | EnvKey |
+| test.js:7:25:7:32 | EnvValue |
+| test.js:7:25:7:32 | EnvValue |
+| test.js:8:24:8:31 | EnvValue |
+| test.js:8:24:8:31 | EnvValue |
+edges
+| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:11:5:18 | EnvValue |
+| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:21:5:26 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:6:15:6:20 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:6:15:6:20 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:7:15:7:20 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:7:15:7:20 | EnvKey |
+| test.js:5:9:5:39 | EnvValue | test.js:6:25:6:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:6:25:6:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
+| test.js:5:11:5:18 | EnvValue | test.js:5:9:5:39 | EnvValue |
+| test.js:5:21:5:26 | EnvKey | test.js:5:9:5:39 | EnvKey |
+| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
+| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
+#select
+| test.js:6:25:6:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:6:25:6:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
+| test.js:7:25:7:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:7:25:7:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
+| test.js:8:24:8:31 | EnvValue | test.js:5:32:5:39 | req.body | test.js:8:24:8:31 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
new file mode 100644
index 000000000000..9659366f6f00
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
@@ -0,0 +1,39 @@
+nodes
+| test.js:5:9:5:28 | { EnvValue, EnvKey } |
+| test.js:5:9:5:39 | EnvKey |
+| test.js:5:9:5:39 | EnvValue |
+| test.js:5:11:5:18 | EnvValue |
+| test.js:5:21:5:26 | EnvKey |
+| test.js:5:32:5:39 | req.body |
+| test.js:5:32:5:39 | req.body |
+| test.js:6:15:6:20 | EnvKey |
+| test.js:6:15:6:20 | EnvKey |
+| test.js:6:25:6:32 | EnvValue |
+| test.js:6:25:6:32 | EnvValue |
+| test.js:7:15:7:20 | EnvKey |
+| test.js:7:15:7:20 | EnvKey |
+| test.js:7:25:7:32 | EnvValue |
+| test.js:7:25:7:32 | EnvValue |
+| test.js:8:24:8:31 | EnvValue |
+| test.js:8:24:8:31 | EnvValue |
+edges
+| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:11:5:18 | EnvValue |
+| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:21:5:26 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:6:15:6:20 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:6:15:6:20 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:7:15:7:20 | EnvKey |
+| test.js:5:9:5:39 | EnvKey | test.js:7:15:7:20 | EnvKey |
+| test.js:5:9:5:39 | EnvValue | test.js:6:25:6:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:6:25:6:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
+| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
+| test.js:5:11:5:18 | EnvValue | test.js:5:9:5:39 | EnvValue |
+| test.js:5:21:5:26 | EnvKey | test.js:5:9:5:39 | EnvKey |
+| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
+| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
+#select
+| test.js:6:25:6:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:6:25:6:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
+| test.js:7:25:7:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:7:25:7:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
+| test.js:8:24:8:31 | EnvValue | test.js:5:32:5:39 | req.body | test.js:8:24:8:31 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.qlref b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.qlref
new file mode 100644
index 000000000000..fde9a286e5a8
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.qlref
@@ -0,0 +1 @@
+experimental/Security/CWE-099/EnvValueAndKeyInjection.ql
\ No newline at end of file
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
new file mode 100644
index 000000000000..c8a9b6ffabaa
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
@@ -0,0 +1,11 @@
+const http = require('node:http');
+
+
+http.createServer((req, res) => {
+ const { EnvValue, EnvKey } = req.body;
+ process.env[EnvKey] = EnvValue; // NOT OK
+ process.env[EnvKey] = EnvValue; // NOT OK
+ process.env.EnvKey = EnvValue; // NOT OK
+
+ res.end('env has been injected!');
+});
\ No newline at end of file
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/EnvValueInjection.expected
similarity index 100%
rename from javascript/ql/test/experimental/Security/CWE-099/EnvInjection.expected
rename to javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/EnvValueInjection.expected
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/EnvValueInjection.qlref b/javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/EnvValueInjection.qlref
new file mode 100644
index 000000000000..e03328beda4f
--- /dev/null
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/EnvValueInjection.qlref
@@ -0,0 +1 @@
+experimental/Security/CWE-099/EnvValueInjection.ql
\ No newline at end of file
diff --git a/javascript/ql/test/experimental/Security/CWE-099/test.js b/javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/test.js
similarity index 98%
rename from javascript/ql/test/experimental/Security/CWE-099/test.js
rename to javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/test.js
index 9d034cfed904..cb28f01b88b0 100644
--- a/javascript/ql/test/experimental/Security/CWE-099/test.js
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueInjection/test.js
@@ -7,4 +7,4 @@ http.createServer((req, res) => {
process.env.AKey = EnvValue; // NOT OK
res.end('env has been injected!');
-});
\ No newline at end of file
+});
From 2b929c4d2d1d406c47afb1d7de078df02f78027b Mon Sep 17 00:00:00 2001
From: am0o0 <77095239+am0o0@users.noreply.github.com>
Date: Sat, 25 May 2024 20:45:34 +0200
Subject: [PATCH 4/9] remove old expected test file
---
.../EnvInjection.expected | 39 -------------------
1 file changed, 39 deletions(-)
delete mode 100644 javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected
deleted file mode 100644
index 9659366f6f00..000000000000
--- a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvInjection.expected
+++ /dev/null
@@ -1,39 +0,0 @@
-nodes
-| test.js:5:9:5:28 | { EnvValue, EnvKey } |
-| test.js:5:9:5:39 | EnvKey |
-| test.js:5:9:5:39 | EnvValue |
-| test.js:5:11:5:18 | EnvValue |
-| test.js:5:21:5:26 | EnvKey |
-| test.js:5:32:5:39 | req.body |
-| test.js:5:32:5:39 | req.body |
-| test.js:6:15:6:20 | EnvKey |
-| test.js:6:15:6:20 | EnvKey |
-| test.js:6:25:6:32 | EnvValue |
-| test.js:6:25:6:32 | EnvValue |
-| test.js:7:15:7:20 | EnvKey |
-| test.js:7:15:7:20 | EnvKey |
-| test.js:7:25:7:32 | EnvValue |
-| test.js:7:25:7:32 | EnvValue |
-| test.js:8:24:8:31 | EnvValue |
-| test.js:8:24:8:31 | EnvValue |
-edges
-| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:11:5:18 | EnvValue |
-| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:21:5:26 | EnvKey |
-| test.js:5:9:5:39 | EnvKey | test.js:6:15:6:20 | EnvKey |
-| test.js:5:9:5:39 | EnvKey | test.js:6:15:6:20 | EnvKey |
-| test.js:5:9:5:39 | EnvKey | test.js:7:15:7:20 | EnvKey |
-| test.js:5:9:5:39 | EnvKey | test.js:7:15:7:20 | EnvKey |
-| test.js:5:9:5:39 | EnvValue | test.js:6:25:6:32 | EnvValue |
-| test.js:5:9:5:39 | EnvValue | test.js:6:25:6:32 | EnvValue |
-| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
-| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
-| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
-| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
-| test.js:5:11:5:18 | EnvValue | test.js:5:9:5:39 | EnvValue |
-| test.js:5:21:5:26 | EnvKey | test.js:5:9:5:39 | EnvKey |
-| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
-| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
-#select
-| test.js:6:25:6:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:6:25:6:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
-| test.js:7:25:7:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:7:25:7:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
-| test.js:8:24:8:31 | EnvValue | test.js:5:32:5:39 | req.body | test.js:8:24:8:31 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
From 5e0a78c4c7c4ab61180be88816838faa029bc138 Mon Sep 17 00:00:00 2001
From: am0o0 <77095239+am0o0@users.noreply.github.com>
Date: Fri, 7 Jun 2024 21:15:03 +0200
Subject: [PATCH 5/9] make predicate for env key and value nodes, use
propertyRead/Write instead of API nodes to find env key and value
assignments, fix a bug thanks to @erik-krogh
---
.../CWE-099/EnvValueAndKeyInjection.ql | 51 ++++++++++---------
.../CWE-099/EnvValueAndKeyInjection/test.js | 9 ++++
2 files changed, 37 insertions(+), 23 deletions(-)
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.ql b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.ql
index 152552279cd6..38c7e5912110 100644
--- a/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.ql
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.ql
@@ -20,15 +20,8 @@ class Configuration extends TaintTracking::Configuration {
override predicate isSource(DataFlow::Node source) { source instanceof RemoteFlowSource }
override predicate isSink(DataFlow::Node sink) {
- NodeJSLib::process()
- .getAPropertyRead("env")
- .asExpr()
- .getParent()
- .(IndexExpr)
- .getAChildExpr()
- .(VarRef) = sink.asExpr()
- or
- sink = API::moduleImport("process").getMember("env").getAMember().asSink()
+ sink = keyOfEnv() or
+ sink = valueOfEnv()
}
override predicate isAdditionalTaintStep(DataFlow::Node pred, DataFlow::Node succ) {
@@ -45,20 +38,32 @@ class Configuration extends TaintTracking::Configuration {
}
}
+DataFlow::Node keyOfEnv() {
+ result =
+ NodeJSLib::process().getAPropertyRead("env").getAPropertyWrite().getPropertyNameExpr().flow()
+}
+
+DataFlow::Node valueOfEnv() {
+ result = API::moduleImport("process").getMember("env").getAMember().asSink()
+}
+
+private predicate readToProcessEnv(DataFlow::Node envKey, DataFlow::Node envValue) {
+ exists(DataFlow::PropWrite env |
+ env = NodeJSLib::process().getAPropertyRead("env").getAPropertyWrite()
+ |
+ envKey = env.getPropertyNameExpr().flow() and
+ envValue = env.getRhs()
+ )
+}
+
from
- Configuration cfg, Configuration cfg2, DataFlow::PathNode source, DataFlow::PathNode sink1,
- DataFlow::PathNode sink2
+ Configuration cfgForValue, Configuration cfgForKey, DataFlow::PathNode source,
+ DataFlow::PathNode envKey, DataFlow::PathNode envValue
where
- cfg.hasFlowPath(source, sink1) and
- sink1.getNode() = API::moduleImport("process").getMember("env").getAMember().asSink() and
- cfg2.hasFlowPath(source, sink2) and
- sink2.getNode().asExpr() =
- NodeJSLib::process()
- .getAPropertyRead("env")
- .asExpr()
- .getParent()
- .(IndexExpr)
- .getAChildExpr()
- .(VarRef)
-select sink1.getNode(), source, sink1, "arbitrary environment variable assignment from this $@.",
+ cfgForValue.hasFlowPath(source, envKey) and
+ envKey.getNode() = keyOfEnv() and
+ cfgForKey.hasFlowPath(source, envValue) and
+ envValue.getNode() = valueOfEnv() and
+ readToProcessEnv(envKey.getNode(), envValue.getNode())
+select envKey.getNode(), source, envKey, "arbitrary environment variable assignment from this $@.",
source.getNode(), "user controllable source"
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
index c8a9b6ffabaa..7938f90e180f 100644
--- a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
@@ -7,5 +7,14 @@ http.createServer((req, res) => {
process.env[EnvKey] = EnvValue; // NOT OK
process.env.EnvKey = EnvValue; // NOT OK
+ res.end('env has been injected!');
+});
+
+http.createServer((req, res) => {
+ const { EnvValue, EnvKey } = req.body;
+
+ process.env[EnvKey] = "constant" // OK
+ process.env.constant = EnvValue // OK
+
res.end('env has been injected!');
});
\ No newline at end of file
From 2c9340331dab13ba2e1c06dff35623a3b6e56e07 Mon Sep 17 00:00:00 2001
From: am0o0 <77095239+am0o0@users.noreply.github.com>
Date: Fri, 7 Jun 2024 21:16:27 +0200
Subject: [PATCH 6/9] update test cases expected results
---
.../EnvValueAndKeyInjection.expected | 26 ++++++++++++++++---
1 file changed, 23 insertions(+), 3 deletions(-)
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
index 9659366f6f00..c78c367fe1bb 100644
--- a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
@@ -16,6 +16,17 @@ nodes
| test.js:7:25:7:32 | EnvValue |
| test.js:8:24:8:31 | EnvValue |
| test.js:8:24:8:31 | EnvValue |
+| test.js:14:9:14:28 | { EnvValue, EnvKey } |
+| test.js:14:9:14:39 | EnvKey |
+| test.js:14:9:14:39 | EnvValue |
+| test.js:14:11:14:18 | EnvValue |
+| test.js:14:21:14:26 | EnvKey |
+| test.js:14:32:14:39 | req.body |
+| test.js:14:32:14:39 | req.body |
+| test.js:16:15:16:20 | EnvKey |
+| test.js:16:15:16:20 | EnvKey |
+| test.js:17:26:17:33 | EnvValue |
+| test.js:17:26:17:33 | EnvValue |
edges
| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:11:5:18 | EnvValue |
| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:21:5:26 | EnvKey |
@@ -33,7 +44,16 @@ edges
| test.js:5:21:5:26 | EnvKey | test.js:5:9:5:39 | EnvKey |
| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
+| test.js:14:9:14:28 | { EnvValue, EnvKey } | test.js:14:11:14:18 | EnvValue |
+| test.js:14:9:14:28 | { EnvValue, EnvKey } | test.js:14:21:14:26 | EnvKey |
+| test.js:14:9:14:39 | EnvKey | test.js:16:15:16:20 | EnvKey |
+| test.js:14:9:14:39 | EnvKey | test.js:16:15:16:20 | EnvKey |
+| test.js:14:9:14:39 | EnvValue | test.js:17:26:17:33 | EnvValue |
+| test.js:14:9:14:39 | EnvValue | test.js:17:26:17:33 | EnvValue |
+| test.js:14:11:14:18 | EnvValue | test.js:14:9:14:39 | EnvValue |
+| test.js:14:21:14:26 | EnvKey | test.js:14:9:14:39 | EnvKey |
+| test.js:14:32:14:39 | req.body | test.js:14:9:14:28 | { EnvValue, EnvKey } |
+| test.js:14:32:14:39 | req.body | test.js:14:9:14:28 | { EnvValue, EnvKey } |
#select
-| test.js:6:25:6:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:6:25:6:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
-| test.js:7:25:7:32 | EnvValue | test.js:5:32:5:39 | req.body | test.js:7:25:7:32 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
-| test.js:8:24:8:31 | EnvValue | test.js:5:32:5:39 | req.body | test.js:8:24:8:31 | EnvValue | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
+| test.js:6:15:6:20 | EnvKey | test.js:5:32:5:39 | req.body | test.js:6:15:6:20 | EnvKey | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
+| test.js:7:15:7:20 | EnvKey | test.js:5:32:5:39 | req.body | test.js:7:15:7:20 | EnvKey | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
From 84b9d4d1ace3be11241be7ffe6c1be333531e481 Mon Sep 17 00:00:00 2001
From: am0o0 <77095239+am0o0@users.noreply.github.com>
Date: Thu, 13 Jun 2024 14:32:41 +0200
Subject: [PATCH 7/9] fix qlhelp errors
---
.../experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp | 2 +-
.../src/experimental/Security/CWE-099/EnvValueInjection.qhelp | 2 +-
2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
index fbf9bf81e733..4fba14b7bcb1 100644
--- a/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
@@ -30,7 +30,7 @@
- Admin account TakeOver in mintplex-labs/anything-llm
+ Admin account TakeOver in mintplex-labs/anything-llm
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.qhelp b/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.qhelp
index cbc6a04297d4..34720b0ac438 100644
--- a/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.qhelp
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueInjection.qhelp
@@ -30,7 +30,7 @@
- Admin account TakeOver in mintplex-labs/anything-llm
+ Admin account TakeOver in mintplex-labs/anything-llm
From f0a467e80b0638065f2ff81890f41b262242dbed Mon Sep 17 00:00:00 2001
From: am0o0 <77095239+am0o0@users.noreply.github.com>
Date: Thu, 13 Jun 2024 14:52:22 +0200
Subject: [PATCH 8/9] update tests
---
.../EnvValueAndKeyInjection.expected | 46 +++++++++----------
.../CWE-099/EnvValueAndKeyInjection/test.js | 1 -
2 files changed, 21 insertions(+), 26 deletions(-)
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
index c78c367fe1bb..f36626a73848 100644
--- a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/EnvValueAndKeyInjection.expected
@@ -14,19 +14,17 @@ nodes
| test.js:7:15:7:20 | EnvKey |
| test.js:7:25:7:32 | EnvValue |
| test.js:7:25:7:32 | EnvValue |
-| test.js:8:24:8:31 | EnvValue |
-| test.js:8:24:8:31 | EnvValue |
-| test.js:14:9:14:28 | { EnvValue, EnvKey } |
-| test.js:14:9:14:39 | EnvKey |
-| test.js:14:9:14:39 | EnvValue |
-| test.js:14:11:14:18 | EnvValue |
-| test.js:14:21:14:26 | EnvKey |
-| test.js:14:32:14:39 | req.body |
-| test.js:14:32:14:39 | req.body |
-| test.js:16:15:16:20 | EnvKey |
-| test.js:16:15:16:20 | EnvKey |
-| test.js:17:26:17:33 | EnvValue |
-| test.js:17:26:17:33 | EnvValue |
+| test.js:13:9:13:28 | { EnvValue, EnvKey } |
+| test.js:13:9:13:39 | EnvKey |
+| test.js:13:9:13:39 | EnvValue |
+| test.js:13:11:13:18 | EnvValue |
+| test.js:13:21:13:26 | EnvKey |
+| test.js:13:32:13:39 | req.body |
+| test.js:13:32:13:39 | req.body |
+| test.js:15:15:15:20 | EnvKey |
+| test.js:15:15:15:20 | EnvKey |
+| test.js:16:26:16:33 | EnvValue |
+| test.js:16:26:16:33 | EnvValue |
edges
| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:11:5:18 | EnvValue |
| test.js:5:9:5:28 | { EnvValue, EnvKey } | test.js:5:21:5:26 | EnvKey |
@@ -38,22 +36,20 @@ edges
| test.js:5:9:5:39 | EnvValue | test.js:6:25:6:32 | EnvValue |
| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
| test.js:5:9:5:39 | EnvValue | test.js:7:25:7:32 | EnvValue |
-| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
-| test.js:5:9:5:39 | EnvValue | test.js:8:24:8:31 | EnvValue |
| test.js:5:11:5:18 | EnvValue | test.js:5:9:5:39 | EnvValue |
| test.js:5:21:5:26 | EnvKey | test.js:5:9:5:39 | EnvKey |
| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
| test.js:5:32:5:39 | req.body | test.js:5:9:5:28 | { EnvValue, EnvKey } |
-| test.js:14:9:14:28 | { EnvValue, EnvKey } | test.js:14:11:14:18 | EnvValue |
-| test.js:14:9:14:28 | { EnvValue, EnvKey } | test.js:14:21:14:26 | EnvKey |
-| test.js:14:9:14:39 | EnvKey | test.js:16:15:16:20 | EnvKey |
-| test.js:14:9:14:39 | EnvKey | test.js:16:15:16:20 | EnvKey |
-| test.js:14:9:14:39 | EnvValue | test.js:17:26:17:33 | EnvValue |
-| test.js:14:9:14:39 | EnvValue | test.js:17:26:17:33 | EnvValue |
-| test.js:14:11:14:18 | EnvValue | test.js:14:9:14:39 | EnvValue |
-| test.js:14:21:14:26 | EnvKey | test.js:14:9:14:39 | EnvKey |
-| test.js:14:32:14:39 | req.body | test.js:14:9:14:28 | { EnvValue, EnvKey } |
-| test.js:14:32:14:39 | req.body | test.js:14:9:14:28 | { EnvValue, EnvKey } |
+| test.js:13:9:13:28 | { EnvValue, EnvKey } | test.js:13:11:13:18 | EnvValue |
+| test.js:13:9:13:28 | { EnvValue, EnvKey } | test.js:13:21:13:26 | EnvKey |
+| test.js:13:9:13:39 | EnvKey | test.js:15:15:15:20 | EnvKey |
+| test.js:13:9:13:39 | EnvKey | test.js:15:15:15:20 | EnvKey |
+| test.js:13:9:13:39 | EnvValue | test.js:16:26:16:33 | EnvValue |
+| test.js:13:9:13:39 | EnvValue | test.js:16:26:16:33 | EnvValue |
+| test.js:13:11:13:18 | EnvValue | test.js:13:9:13:39 | EnvValue |
+| test.js:13:21:13:26 | EnvKey | test.js:13:9:13:39 | EnvKey |
+| test.js:13:32:13:39 | req.body | test.js:13:9:13:28 | { EnvValue, EnvKey } |
+| test.js:13:32:13:39 | req.body | test.js:13:9:13:28 | { EnvValue, EnvKey } |
#select
| test.js:6:15:6:20 | EnvKey | test.js:5:32:5:39 | req.body | test.js:6:15:6:20 | EnvKey | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
| test.js:7:15:7:20 | EnvKey | test.js:5:32:5:39 | req.body | test.js:7:15:7:20 | EnvKey | arbitrary environment variable assignment from this $@. | test.js:5:32:5:39 | req.body | user controllable source |
diff --git a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
index 7938f90e180f..a12377c9cec9 100644
--- a/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
+++ b/javascript/ql/test/experimental/Security/CWE-099/EnvValueAndKeyInjection/test.js
@@ -5,7 +5,6 @@ http.createServer((req, res) => {
const { EnvValue, EnvKey } = req.body;
process.env[EnvKey] = EnvValue; // NOT OK
process.env[EnvKey] = EnvValue; // NOT OK
- process.env.EnvKey = EnvValue; // NOT OK
res.end('env has been injected!');
});
From 4e1f7a930d5cf770bc4ea12bbfd8365263971f0b Mon Sep 17 00:00:00 2001
From: am0o0 <77095239+am0o0@users.noreply.github.com>
Date: Fri, 14 Jun 2024 13:47:01 +0200
Subject: [PATCH 9/9] fix invalid js file sample in qlhelp
---
.../experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
index 4fba14b7bcb1..1f8ab1cc7440 100644
--- a/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
+++ b/javascript/ql/src/experimental/Security/CWE-099/EnvValueAndKeyInjection.qhelp
@@ -25,7 +25,7 @@
The following example allows unauthorized users to assign a value to any environment variable.
-
+