Skip to content

Commit 4efc418

Browse files
authored
Merge pull request #2617 from asger-semmle/prototype-pollution-utility
Approved by esbena, mchammer01
2 parents 8128d23 + 7a1d068 commit 4efc418

File tree

14 files changed

+3254
-0
lines changed

14 files changed

+3254
-0
lines changed

change-notes/1.24/analysis-javascript.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
| Cross-site scripting through exception (`js/xss-through-exception`) | security, external/cwe/cwe-079, external/cwe/cwe-116 | Highlights potential XSS vulnerabilities where an exception is written to the DOM. Results are not shown on LGTM by default. |
2222
| Regular expression always matches (`js/regex/always-matches`) | correctness, regular-expressions | Highlights regular expression checks that trivially succeed by matching an empty substring. Results are shown on LGTM by default. |
2323
| Missing await (`js/missing-await`) | correctness | Highlights expressions that operate directly on a promise object in a nonsensical way, instead of awaiting its result. Results are shown on LGTM by default. |
24+
| Prototype pollution in utility function (`js/prototype-pollution-utility`) | security, external/cwe/cwe-400, external/cwe/cwe-471 | Highlights recursive copying operations that are susceptible to prototype pollution. Results are shown on LGTM by default. |
2425

2526
## Changes to existing queries
2627

javascript/config/suites/javascript/security

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
+ semmlecode-javascript-queries/Security/CWE-352/MissingCsrfMiddleware.ql: /Security/CWE/CWE-352
3232
+ semmlecode-javascript-queries/Security/CWE-400/RemotePropertyInjection.ql: /Security/CWE/CWE-400
3333
+ semmlecode-javascript-queries/Security/CWE-400/PrototypePollution.ql: /Security/CWE/CWE-400
34+
+ semmlecode-javascript-queries/Security/CWE-400/PrototypePollutionUtility.ql: /Security/CWE/CWE-400
3435
+ semmlecode-javascript-queries/Security/CWE-502/UnsafeDeserialization.ql: /Security/CWE/CWE-502
3536
+ semmlecode-javascript-queries/Security/CWE-506/HardcodedDataInterpretedAsCode.ql: /Security/CWE/CWE-506
3637
+ semmlecode-javascript-queries/Security/CWE-601/ClientSideUrlRedirect.ql: /Security/CWE/CWE-601
Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
<!DOCTYPE qhelp PUBLIC
2+
"-//Semmle//qhelp//EN"
3+
"qhelp.dtd">
4+
<qhelp>
5+
6+
<overview>
7+
<p>
8+
Most JavaScript objects inherit the properties of the built-in <code>Object.prototype</code> object.
9+
Prototype pollution is a type of vulnerability in which an attacker is able to modify <code>Object.prototype</code>.
10+
Since most objects inherit from the compromised <code>Object.prototype</code>, the attacker can use this
11+
to tamper with the application logic, and often escalate to remote code execution or cross-site scripting.
12+
</p>
13+
14+
<p>
15+
One way to cause prototype pollution is through use of an unsafe <em>merge</em> or <em>extend</em> function
16+
to recursively copy properties from one object to another.
17+
Such a function has the potential to modify any object reachable from the destination object, and
18+
the built-in <code>Object.prototype</code> is usually reachable through the special properties
19+
<code>__proto__</code> and <code>constructor.prototype</code>.
20+
</p>
21+
</overview>
22+
23+
<recommendation>
24+
<p>
25+
The most effective place to guard against this is in the function that performs
26+
the recursive copy.
27+
</p>
28+
29+
<p>
30+
Only merge a property recursively when it is an own property of the <em>destination</em> object.
31+
Alternatively, blacklist the property names <code>__proto__</code> and <code>constructor</code>
32+
from being merged.
33+
</p>
34+
</recommendation>
35+
36+
<example>
37+
<p>
38+
This function recursively copies properties from <code>src</code> to <code>dst</code>:
39+
</p>
40+
41+
<sample src="examples/PrototypePollutionUtility.js"/>
42+
43+
<p>
44+
However, if <code>src</code> is the object <code>{"__proto__": {"isAdmin": true}}</code>,
45+
it will inject the property <code>isAdmin: true</code> in <code>Object.prototype</code>.
46+
</p>
47+
48+
<p>
49+
The issue can be fixed by ensuring that only own properties of the destination object
50+
are merged recursively:
51+
</p>
52+
53+
<sample src="examples/PrototypePollutionUtility_fixed.js"/>
54+
55+
<p>
56+
Alternatively, blacklist the <code>__proto__</code> and <code>constructor</code> properties:
57+
</p>
58+
59+
<sample src="examples/PrototypePollutionUtility_fixed2.js"/>
60+
</example>
61+
62+
<references>
63+
<li>Prototype pollution attacks:
64+
<a href="https://hackerone.com/reports/380873">lodash</a>,
65+
<a href="https://hackerone.com/reports/454365">jQuery</a>,
66+
<a href="https://hackerone.com/reports/381185">extend</a>,
67+
<a href="https://hackerone.com/reports/430291">just-extend</a>,
68+
<a href="https://hackerone.com/reports/381194">merge.recursive</a>.
69+
</li>
70+
</references>
71+
</qhelp>

0 commit comments

Comments
 (0)