Skip to content

Commit eabd943

Browse files
Merge pull request #7 from GitHubSecurityLab/part3
Add challenges to part 3
2 parents a77bce7 + 2a936c0 commit eabd943

24 files changed

+213
-0
lines changed

2/challenge-1/sql-injection.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,4 +15,8 @@ def show_user(request, username):
1515
# BAD -- Manually quoting placeholder (%s)
1616
cursor.execute("SELECT * FROM users WHERE username = '%s'" % username)
1717
user = cursor.fetchone()
18+
19+
# GOOD - string literal
20+
cursor.execute("SELECT * FROM users WHERE username = 'johndoe'")
21+
user = cursor.fetchone()
1822
urlpatterns = [url(r'^users/(?P<username>[^/]+)$', show_user)]

3/1/instructions.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
You will need to set up CodeQL using one of the methods presented in [challenge 2](https://github.com/GitHubSecurityLab/codeql-zero-to-hero/blob/main/2/challenge-2/instructions.md) from CodeQL zero to hero part 2 to run the queries. Remember also to download and [select a CodeQL database](https://github.com/GitHubSecurityLab/codeql-zero-to-hero/blob/main/2/challenge-2/instructions.md#select-codeql-database) - it can be the GitHubSecurityLab/codeql-zero-to-hero database, but you may also choose another project.
2+
3+
Run the query in this challenge to find all method calls that are called ‘execute’ and come from the `django.db` library.
4+
5+
If the path is not displaying properly, you may need to change the view to ‘alerts’.
6+
7+
<img src=../../images/alert-view.png>

3/1/query.ql

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
/**
2+
* @id codeql-zero-to-hero/3-1
3+
* @severity error
4+
* @kind problem
5+
*/
6+
7+
import python
8+
import semmle.python.ApiGraphs
9+
10+
from API::CallNode node
11+
where node =
12+
API::moduleImport("django").getMember("db").getMember("connection").getMember("cursor").getReturn().getMember("execute").getACall()
13+
and
14+
node.getLocation().getFile().getRelativePath().regexpMatch("2/challenge-1/.*")
15+
select node, "Call to django.db execute"

3/10/instructions.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
Run the CWE-20 Untrusted APIs query on a repo of your choice. For Python in the VS Code CodeQL Starter Workspace, it is located in `vscode-codeql-starter/ql/python/ql/src/Security/CWE-020-ExternalAPIs/UntrustedDataToExternalAPI.ql`.
2+
Try to choose a new project, download its database from GitHub (see [setup](https://github.com/GitHubSecurityLab/codeql-zero-to-hero/blob/main/2/challenge-2/instructions.md#option-b-local-installation)) and run this query on it.

3/11/instructions.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
Set up MRVA using instructions [here](https://codeql.github.com/docs/codeql-for-visual-studio-code/running-codeql-queries-at-scale-with-mrva/#controller-repository). Select top 10 repositories in the CodeQL extension tab. Choose one of the prewritten queries in your favorite language, right-click in the query file, and select CodeQL: Run Variant Analysis to start variant analysis. If you don’t find anything using that query, it’s likely because the project is already secured against that vulnerability. If you prefer, run one of the bigger lists with 100 or 1000 repositories.
2+
Caution: if you do find true positive vulnerabilities, make sure to verify them first and then report them using the coordinated disclosure process. See our [guide](https://github.blog/2022-02-09-coordinated-vulnerability-disclosure-cvd-open-source-projects/) for reporting vulnerabilities to open source.

3/2/instructions.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
Now you know how to query for calls to functions from specific libraries.
2+
3+
If `os.system` executes input coming from a user, it could lead to a command injection. Write a query to find calls to `os.system` and run it on the database you selected in the previous challenge.
4+
5+
See solution in this folder.

3/2/query.ql

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
/**
2+
* @id codeql-zero-to-hero/3-2
3+
* @severity error
4+
* @kind problem
5+
*/
6+
7+
import python
8+
import semmle.python.ApiGraphs
9+
10+
from API::CallNode node
11+
where node = API::moduleImport("os").getMember("system").getACall()
12+
and node.getLocation().getFile().getRelativePath().regexpMatch("2/challenge-1/.*")
13+
select node, "Call to os.system"

3/3/instructions.md

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
Flask is a popular Python web framework. Frameworks very often introduce potential sources for untrusted data, [Flask request](https://flask.palletsprojects.com/en/3.0.x/api/#incoming-request-data) being one of them. For example, a source of untrusted data could be:
2+
3+
```
4+
username = request.args.get("username")
5+
```
6+
7+
Write a query to find `request.args`
8+
9+
See solution in this folder.

3/3/query.ql

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
/**
2+
* @id codeql-zero-to-hero/3-3
3+
* @severity error
4+
* @kind problem
5+
*/
6+
7+
import python
8+
import semmle.python.ApiGraphs
9+
10+
select API::moduleImport("flask").getMember("request").getMember("args").asSource(), "Flask request.args source"
11+
12+
// Note that you can also use a wildcard to query for any method of the request object, for example:
13+
14+
// select API::moduleImport("flask").getMember("request").getMember(_).asSource()

3/4/instructions.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
Run a query with `getAQlClass` predicate.
2+
3+
See example in this folder.

0 commit comments

Comments
 (0)