GitPython: Remote.pull() arbitrary command execution via refspec injection
The GitPython library fails to validate the refspec positional argument in Remote.pull(), allowing attackers to inject shell commands via --upload-pack options when using SSH or local transports.
Triage facts
Revision 1- Applicability
- GitPython (>= 3.1.30, < 3.2.0)
- Evidence
- Unknown
- Severity
- High
- Action
- Elevated
- Sources
- 1 public source
- Freshness
- Revision 1Oct 29, 23:25 UTC
- Source quality
- A1Likely
GitPython's Remote.pull() method contains a vulnerability in its security guard intended to prevent command injection. While the library attempts to block dangerous options like --upload-pack, the guard only inspects keyword arguments and fails to validate the positional refspec argument. An attacker can supply a refspec starting with --upload-pack=, which is forwarded to the underlying git pull process. Because git pull does not properly terminate positional arguments before passing them to internal git fetch operations, the injected command is executed as the upload-pack program. Exploitation is possible when using local filesystem or SSH transports. No fix is currently available.
Attack Chain
- Exposure: An application calls
Remote.pull(refspec=<value>)where<value>is derived from attacker-influenced input. - Control: The attacker provides a string such as
--upload-pack=<command>; git-upload-pack. - Path: The input passes through
Git._unpack_argsandGit.check_unsafe_protocolswithout being flagged as malicious. - Guard: The unsafe-option guard incorrectly assumes positionals are safe, failing to check the
refspecagainstunsafe_git_pull_options. - Primitive: The
refspecis passed togit pull -v -- <remote> <refspec>. - Execution: The
git pullcommand forwards the positional to an internalgit fetchwithout a--separator, causing the system to execute the injected command as theupload-packprogram. - Result: Arbitrary command execution occurs on the system with the privileges of the calling process.
Impact
Successful exploitation allows arbitrary command execution as the user running the GitPython process. This requires the use of SSH or local filesystem transports; HTTPS transports are not affected as the server ignores the client-supplied upload-pack program.
Recommendation
- Validate that all
refspecstrings passed toRemote.pull()do not start with a hyphen (-). - Prefer HTTPS remotes over local-path or SSH transports where possible.
- Avoid passing untrusted user input directly into GitPython method arguments.
- Monitor for GitPython processes spawning child processes that are not standard git utilities or that originate from unexpected command-line arguments.
Immediate actions
Inventory applications using GitPython to pull from SSH or local filesystem origins.
Threat Hunt
Search process logs for 'git pull' or 'git fetch' commands containing '--upload-pack=' in the command-line arguments.
Data: Process creation logs (CommandLine)
Mitigations
Implement strict allow-listing for refspec parameters in web or CI services interacting with GitPython.
GitPython (>= 3.1.30, < 3.2.0)