Skip to content

Commit

Permalink
feat(python/django): add crlf_injection rule
Browse files Browse the repository at this point in the history
  • Loading branch information
elsapet committed Jun 6, 2024
1 parent 06febd5 commit e0c6f60
Show file tree
Hide file tree
Showing 3 changed files with 88 additions and 0 deletions.
51 changes: 51 additions & 0 deletions rules/python/django/crlf_injection.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
imports:
- python_shared_common_user_input
patterns:
- pattern: |
$<FILE>.write($<USER_INPUT>$<...>)
filters:
- variable: FILE
detection: python_django_crlf_injection_file
scope: cursor
- variable: USER_INPUT
detection: python_shared_common_user_input
scope: result
- not:
variable: USER_INPUT
detection: python_django_crlf_injection_sanitized_dynamic_input
scope: result
auxiliary:
- id: python_django_crlf_injection_file
patterns:
- open($<...>)
- id: python_django_crlf_injection_sanitized_dynamic_input
patterns:
- $<_>.strip()
- pattern: $<_>.strip($<SOURCE>)
filters:
- variable: SOURCE
string_regex: \A(\\r\\n|\\n\\r)n\z
languages:
- python
severity: medium
metadata:
description: Possible CLRF injection detected
remediation_message: |-
## Description
CRLF (Carriage Return Line Feed) injection vulnerability occurs when an attacker is able to insert a sequence of line termination characters into a log message or a file. This can lead to forged log entries, compromising the integrity of log files, or worse, a denial-of-service (DoS) if an attacker abuses the vulnerability by using up all available disk space.
## Remediations
- **Do** strip any carriage return and line feed characters from user input data before logging it or writing to a file. This prevents attackers from injecting malicious CRLF sequences.
```pyhton
response.write(user_input.replaceAll("[\r\n]+", ""));
```
## References
- [OWASP CRLF Injection](https://owasp.org/www-community/vulnerabilities/CRLF_Injection)
cwe_id:
- 93
id: python_django_crlf_injection
documentation_url: https://docs.bearer.com/reference/rules/python_django_crlf_injection
20 changes: 20 additions & 0 deletions tests/python/django/crlf_injection/test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
const {
createNewInvoker,
getEnvironment,
} = require("../../../helper.js")
const { ruleId, ruleFile, testBase } = getEnvironment(__dirname)

describe(ruleId, () => {
const invoke = createNewInvoker(ruleId, ruleFile, testBase)

test("crlf_injection", () => {
const testCase = "main.py"

const results = invoke(testCase)

expect(results).toEqual({
Missing: [],
Extra: []
})
})
})
17 changes: 17 additions & 0 deletions tests/python/django/crlf_injection/testdata/main.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
def bad(request):
log_code = request.POST.get('log_code')
log_filename = os.path.join(dirname, "my-log-code.py")
f = open(log_filename,"w")
# bearer:expected python_django_crlf_injection
f.write(log_code)
f.close()

def ok(request):
log_code = request.POST.get('log_code')
log_filename = os.path.join(dirname, "my-log-code.py")
f = open(log_filename,"w")
# ok
f.write(log_code.strip())
# ok
f.write(log_code.strip("\r\n"))
f.close()

0 comments on commit e0c6f60

Please sign in to comment.