Resolve vulnerability: Improper neutralization of special elements used in an OS Command ('OS Command Injection')

AI GENERATED VULNERABILITY REMEDIATION

Issue Reference

Closes #33

MR created from vulnerability: Improper neutralization of special elements used in an OS Command ('OS Command Injection')

AI GENERATED FIX

The suggested code changes were generated by GitLab Duo Vulnerability Resolution, an AI feature. Use this feature with caution. Before you run a pipeline or apply the code changes, carefully review and test them, to ensure that they solve the vulnerability.

The large language model that generated the suggested code changes was provided with the entire file that contains the vulnerable lines of code. It is not aware of any functionality outside of this context.

Please see our documentation for more information about this feature and leave feedback in this issue.

Vulnerability Description

The application was found with instances where user input is unsafely passed to the subprocess.run() or related functions, which can lead to command injection vulnerabilities. It specifically looks for cases where shell commands like sh, bash, etc. are executed with user-controlled input.

Command injection is a serious security vulnerability that allows an attacker to execute arbitrary system commands on the host operating system. This can lead to data breaches, data loss, system compromise, and other devastating impacts.

To fix command injection vulnerabilities, user input should never be passed directly to subprocess functions that execute system commands. Instead, use the subprocess module's argument list feature to pass command arguments safely without invoking a shell.

import subprocess

user_input = "file.txt"
subprocess.run(["ls", user_input])

General mitigation guidelines:

  • Never pass user input directly to subprocess functions that execute commands
  • Use the argument list feature of subprocess to pass command and arguments safely
  • Validate and sanitize any user input before using it in command execution

Vulnerability Details

Summary

Vulnerability

The code contained an OS Command Injection vulnerability (CWE-78) where user input from form fields was directly incorporated into a shell command executed with subprocess.check_output() using shell=True. This allows attackers to inject malicious commands by manipulating the username or password fields.

For example, if an attacker entered a username like '; rm -rf /* #, the resulting command would be:

grep ''; rm -rf /* #:/password' /app/users.txt

This would execute the destructive command after the semicolon.

Fix

The fix replaces the vulnerable shell command execution with a safer approach:

  1. Removed the string interpolation that created the vulnerable command
  2. Used the argument list form of subprocess.check_output() instead of the string form
  3. Eliminated the shell=True parameter, which prevents shell interpretation of special characters
  4. Passed the search pattern and file path as separate arguments

The new implementation passes each component of the command as separate arguments in a list, which prevents the shell from interpreting special characters in the user input as command syntax. This is the recommended approach in the Python documentation and security best practices for executing system commands with user input.

This change maintains the same functionality while eliminating the command injection risk.

Identifiers

  • A1:2017 - Injection
  • CWE-78
  • python-lang-cmdi-subprocess-taint
  • A03:2021 - Injection
  • SAST Rules ID - python_exec_rule-subprocess-call
  • SAST Rules ID - python_exec_rule-subprocess-popen-shell-true
  • Bandit Test ID bandit.B604
  • Bandit Test ID bandit.B602
  • Bandit Test ID bandit.B603
  • SAST Rules ID - python_exec_rule-subprocess-call-array
  • SAST Rules ID - python_exec_rule-subprocess-shell-TRUE
  • SAST Rules ID - python_exec_rule-start-process-path
Edited by Falko Sieverding

Merge request reports

Loading