Skip to content

Commit

Permalink
Rust: Add .qhelp and examples.
Browse files Browse the repository at this point in the history
  • Loading branch information
geoffw0 committed Nov 19, 2024
1 parent 2df565c commit 6a7fb06
Show file tree
Hide file tree
Showing 3 changed files with 51 additions and 0 deletions.
39 changes: 39 additions & 0 deletions rust/ql/src/queries/security/CWE-089/SqlInjection.qhelp
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
<!DOCTYPE qhelp PUBLIC
"-//Semmle//qhelp//EN"
"qhelp.dtd">
<qhelp>
<overview>

<p>
If a database query (such as a SQL query) is built from user-provided data without sufficient sanitization, a user may be able to run malicious database queries. An attacker can craft the part of the query they control to change the overall meaning of the query.
</p>

</overview>
<recommendation>

<p>
Most database connector libraries offer a way to safely embed untrusted data into a query using query parameters or prepared statements. You should use these features to build queries, rather than string concatenation or similar methods. You can also escape (sanitize) user-controlled strings so that they can be included directly in an SQL command. A library function should be used for escaping, because this approach is only safe if the escaping function is robust against all possible inputs.
</p>

</recommendation>
<example>

<p>
In the following examples, an SQL query is prepared using string formatting to directly include a user-controlled value <code>remote_controlled_string</code>. An attacker could craft <code>remote_controlled_string</code> to change the overall meaning of the SQL query.
</p>

<sample src="SqlInjectionBad.rs" />

<p>A better way to do this is with a prepared statement, binding <code>remote_controlled_string</code> to a parameter of that statement. An attacker who controls <code>remote_controlled_string</code> now cannot change the overall meaning of the query.
</p>

<sample src="SqlInjectionGood.rs" />

</example>
<references>

<li>Wikipedia: <a href="https://en.wikipedia.org/wiki/SQL_injection">SQL injection</a>.</li>
<li>OWASP: <a href="https://cheatsheetseries.owasp.org/cheatsheets/SQL_Injection_Prevention_Cheat_Sheet.html">SQL Injection Prevention Cheat Sheet</a>.</li>

</references>
</qhelp>
7 changes: 7 additions & 0 deletions rust/ql/src/queries/security/CWE-089/SqlInjectionBad.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
// with SQLx

let unsafe_query = format!("SELECT * FROM people WHERE firstname='{remote_controlled_string}'");

let _ = conn.execute(unsafe_query.as_str()).await?; // BAD (arbitrary SQL injection is possible)

let _ = sqlx::query(unsafe_query.as_str()).fetch_all(&mut conn).await?; // $ BAD (arbitrary SQL injection is possible)
5 changes: 5 additions & 0 deletions rust/ql/src/queries/security/CWE-089/SqlInjectionGood.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
// with SQLx

let prepared_query = "SELECT * FROM people WHERE firstname=?";

let _ = sqlx::query(prepared_query_1).bind(&remote_controlled_string).fetch_all(&mut conn).await?; // GOOD (prepared statement with bound parameter)

0 comments on commit 6a7fb06

Please sign in to comment.