Skip to content

Commit 18b05bc

Browse files
committed
Fix tests and add global option
1 parent 54012eb commit 18b05bc

File tree

5 files changed

+35
-4
lines changed

5 files changed

+35
-4
lines changed

python/ql/src/experimental/semmle/python/frameworks/LDAP.qll

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,11 @@ private module LDAP {
8888
result.(DataFlow::AttrRead).getAttributeName() instanceof LDAP2BindMethods
8989
}
9090

91+
/**List of SSL-demanding options */
92+
private class LDAPSSLOptions extends DataFlow::Node {
93+
LDAPSSLOptions() { this = ldap().getMember("OPT_X_TLS_" + ["DEMAND", "HARD"]).getAUse() }
94+
}
95+
9196
/**
9297
* A class to find `ldap` methods binding a connection.
9398
*
@@ -111,6 +116,8 @@ private module LDAP {
111116
override predicate useSSL() {
112117
// use initialize to correlate `this` and so avoid FP in several instances
113118
exists(DataFlow::CallCfgNode initialize |
119+
ldap().getMember("set_option").getACall().getArg(_) instanceof LDAPSSLOptions
120+
or
114121
this.getFunction().(DataFlow::AttrRead).getObject().getALocalSource() = initialize and
115122
initialize = ldapInitialize().getACall() and
116123
(
@@ -126,7 +133,7 @@ private module LDAP {
126133
setOption.getFunction().(DataFlow::AttrRead).getObject().getALocalSource() =
127134
initialize and
128135
setOption.getFunction().(DataFlow::AttrRead).getAttributeName() = "set_option" and
129-
setOption.getArg(0) = ldap().getMember("OPT_X_TLS_" + ["DEMAND", "HARD"]).getAUse() and
136+
setOption.getArg(0) instanceof LDAPSSLOptions and
130137
not DataFlow::exprNode(any(False falseExpr))
131138
.(DataFlow::LocalSourceNode)
132139
.flowsTo(setOption.getArg(1))
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import ldap
2+
from flask import request, Flask
3+
4+
app = Flask(__name__)
5+
6+
# GOOD
7+
8+
# SSL through ldap global variable option
9+
10+
ldap.set_option(ldap.OPT_X_TLS_DEMAND)
11+
12+
13+
@app.route("/one")
14+
def one():
15+
ldap_connection_5 = ldap.initialize("ldap://somethingon.theinternet.com")
16+
ldap_connection_5.simple_bind_s('', '')
17+
user = ldap_connection_5.search_s(
18+
"dn", ldap.SCOPE_SUBTREE, "search_filter")
19+
20+
return user
21+
22+
23+
# if __name__ == "__main__":
24+
# app.run(debug=True)

python/ql/test/experimental/query-tests/Security/CWE-522/ldap2_private.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ def one_bad():
5454
@app.route("/one_bad_2")
5555
def one_bad_2():
5656
ldap_connection_4 = ldap.initialize(schema + remote_host)
57-
ldap_connection_4.set_option(ldap.OPT_X_TLS_NEVER)
57+
ldap_connection_4.set_option(ldap.OPT_X_TLS_NEVER, True)
5858
ldap_connection_4.simple_bind_s('', '')
5959
user = ldap_connection_4.search_s(
6060
"dn", ldap.SCOPE_SUBTREE, "search_filter")

python/ql/test/experimental/query-tests/Security/CWE-522/ldap2_remote.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ def one_bad():
5454
@app.route("/one_bad_2")
5555
def one_bad_2():
5656
ldap_connection_8 = ldap.initialize(schema + remote_host)
57-
ldap_connection_8.set_option(ldap.OPT_X_TLS_NEVER)
57+
ldap_connection_8.set_option(ldap.OPT_X_TLS_NEVER, True)
5858
ldap_connection_8.simple_bind_s('', '')
5959
user = ldap_connection_8.search_s(
6060
"dn", ldap.SCOPE_SUBTREE, "search_filter")

python/ql/test/experimental/query-tests/Security/CWE-522/ldap3_remote.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313

1414
@app.route("/one")
1515
def one():
16-
srv = Server("ldap://somethingon.theinternet.com", port=1337, True)
16+
srv = Server("ldap://somethingon.theinternet.com", 1337, True)
1717
conn = Connection(srv, "dn", "password")
1818
conn.search("dn", "search_filter")
1919
return conn.response

0 commit comments

Comments
 (0)