Package: release.debian.org Severity: normal User: [email protected] Usertags: unblock X-Debbugs-Cc: [email protected],[email protected]
Hi Release team, Please unblock package composer The update fixes CVE-2021-29472 (which was as well fixed in DSA 4907-1 for buster) and contains the security fix only (plus a change in the Vcs-Git field). unblock composer/composer Regards, Salvatore
diff -Nru composer-2.0.9/debian/changelog composer-2.0.9/debian/changelog --- composer-2.0.9/debian/changelog 2021-01-29 01:05:13.000000000 +0100 +++ composer-2.0.9/debian/changelog 2021-04-28 00:20:52.000000000 +0200 @@ -1,3 +1,13 @@ +composer (2.0.9-2) unstable; urgency=medium + + * Use debian/bullseye branch + * Security: Fixed command injection vulnerability. + Fix external process calls to avoid user input being able to pass extra + parameters in HgDriver/HgDownloader and hardened other VCS drivers and + downloaders (GHSA-h5h8-pc6h-jvvx) [CVE-2021-29472] + + -- David Prévot <[email protected]> Tue, 27 Apr 2021 18:20:52 -0400 + composer (2.0.9-1) unstable; urgency=medium [ Jordi Boggiano ] diff -Nru composer-2.0.9/debian/control composer-2.0.9/debian/control --- composer-2.0.9/debian/control 2021-01-29 01:04:50.000000000 +0100 +++ composer-2.0.9/debian/control 2021-04-28 00:18:57.000000000 +0200 @@ -28,7 +28,7 @@ Standards-Version: 4.5.1 Homepage: https://getcomposer.org/ Vcs-Browser: https://salsa.debian.org/php-team/pear/composer -Vcs-Git: https://salsa.debian.org/php-team/pear/composer.git -b debian/latest +Vcs-Git: https://salsa.debian.org/php-team/pear/composer.git -b debian/bullseye Rules-Requires-Root: no Package: composer diff -Nru composer-2.0.9/debian/gbp.conf composer-2.0.9/debian/gbp.conf --- composer-2.0.9/debian/gbp.conf 2021-01-28 23:53:16.000000000 +0100 +++ composer-2.0.9/debian/gbp.conf 2021-04-28 00:18:57.000000000 +0200 @@ -1,5 +1,5 @@ [DEFAULT] -debian-branch = debian/latest +debian-branch = debian/bullseye pristine-tar = True filter = [ '.gitattributes' ] upstream-vcs-tag = %(version%~%-)s diff -Nru composer-2.0.9/debian/patches/0009-Merge-pull-request-from-GHSA-h5h8-pc6h-jvvx.patch composer-2.0.9/debian/patches/0009-Merge-pull-request-from-GHSA-h5h8-pc6h-jvvx.patch --- composer-2.0.9/debian/patches/0009-Merge-pull-request-from-GHSA-h5h8-pc6h-jvvx.patch 1970-01-01 01:00:00.000000000 +0100 +++ composer-2.0.9/debian/patches/0009-Merge-pull-request-from-GHSA-h5h8-pc6h-jvvx.patch 2021-04-28 00:18:57.000000000 +0200 @@ -0,0 +1,491 @@ +From: Jordi Boggiano <[email protected]> +Date: Tue, 27 Apr 2021 13:00:40 +0200 +Subject: Merge pull request from GHSA-h5h8-pc6h-jvvx + +* Fix external process calls to avoid user input being able to pass extra parameters + +* Tweak some fixes + +Origin: upstream, https://github.com/composer/composer/commit/332c46af8bebdead80a2601350dff7af0ac1f490 +Bug-Debian-Security: https://security-tracker.debian.org/tracker/CVE-2021-29472 +--- + src/Composer/Downloader/FossilDownloader.php | 6 ++-- + src/Composer/Downloader/GitDownloader.php | 12 ++++---- + src/Composer/Downloader/GzipDownloader.php | 2 +- + src/Composer/Downloader/HgDownloader.php | 6 ++-- + src/Composer/Downloader/RarDownloader.php | 2 +- + src/Composer/Downloader/SvnDownloader.php | 2 +- + src/Composer/Repository/Vcs/FossilDriver.php | 6 ++-- + src/Composer/Repository/Vcs/GitDriver.php | 2 +- + src/Composer/Repository/Vcs/HgDriver.php | 4 +-- + src/Composer/Repository/Vcs/SvnDriver.php | 2 +- + src/Composer/Util/Git.php | 4 +-- + src/Composer/Util/Svn.php | 2 +- + .../Test/Downloader/FossilDownloaderTest.php | 6 ++-- + .../Composer/Test/Downloader/GitDownloaderTest.php | 36 +++++++++++----------- + .../Composer/Test/Downloader/HgDownloaderTest.php | 6 ++-- + tests/Composer/Test/Util/SvnTest.php | 2 +- + 16 files changed, 50 insertions(+), 50 deletions(-) + +diff --git a/src/Composer/Downloader/FossilDownloader.php b/src/Composer/Downloader/FossilDownloader.php +index a597d51..74364dd 100644 +--- a/src/Composer/Downloader/FossilDownloader.php ++++ b/src/Composer/Downloader/FossilDownloader.php +@@ -39,15 +39,15 @@ class FossilDownloader extends VcsDownloader + $ref = ProcessExecutor::escape($package->getSourceReference()); + $repoFile = $path . '.fossil'; + $this->io->writeError("Cloning ".$package->getSourceReference()); +- $command = sprintf('fossil clone %s %s', $url, ProcessExecutor::escape($repoFile)); ++ $command = sprintf('fossil clone -- %s %s', $url, ProcessExecutor::escape($repoFile)); + if (0 !== $this->process->execute($command, $ignoredOutput)) { + throw new \RuntimeException('Failed to execute ' . $command . "\n\n" . $this->process->getErrorOutput()); + } +- $command = sprintf('fossil open %s --nested', ProcessExecutor::escape($repoFile)); ++ $command = sprintf('fossil open --nested -- %s', ProcessExecutor::escape($repoFile)); + if (0 !== $this->process->execute($command, $ignoredOutput, realpath($path))) { + throw new \RuntimeException('Failed to execute ' . $command . "\n\n" . $this->process->getErrorOutput()); + } +- $command = sprintf('fossil update %s', $ref); ++ $command = sprintf('fossil update -- %s', $ref); + if (0 !== $this->process->execute($command, $ignoredOutput, realpath($path))) { + throw new \RuntimeException('Failed to execute ' . $command . "\n\n" . $this->process->getErrorOutput()); + } +diff --git a/src/Composer/Downloader/GitDownloader.php b/src/Composer/Downloader/GitDownloader.php +index dd8a7d8..ef23a51 100644 +--- a/src/Composer/Downloader/GitDownloader.php ++++ b/src/Composer/Downloader/GitDownloader.php +@@ -90,10 +90,10 @@ class GitDownloader extends VcsDownloader implements DvcsDownloaderInterface + $command = + 'git clone --no-checkout %cachePath% %path% --dissociate --reference %cachePath% ' + . '&& cd '.$flag.'%path% ' +- . '&& git remote set-url origin %sanitizedUrl% && git remote add composer %sanitizedUrl%'; ++ . '&& git remote set-url origin -- %sanitizedUrl% && git remote add composer -- %sanitizedUrl%'; + } else { + $msg = "Cloning ".$this->getShortHash($ref); +- $command = 'git clone --no-checkout %url% %path% && cd '.$flag.'%path% && git remote add composer %url% && git fetch composer && git remote set-url origin %sanitizedUrl% && git remote set-url composer %sanitizedUrl%'; ++ $command = 'git clone --no-checkout -- %url% %path% && cd '.$flag.'%path% && git remote add composer -- %url% && git fetch composer && git remote set-url origin -- %sanitizedUrl% && git remote set-url composer -- %sanitizedUrl%'; + if (getenv('COMPOSER_DISABLE_NETWORK')) { + throw new \RuntimeException('The required git reference for '.$package->getName().' is not in cache and network is disabled, aborting'); + } +@@ -145,10 +145,10 @@ class GitDownloader extends VcsDownloader implements DvcsDownloaderInterface + + if (!empty($this->cachedPackages[$target->getId()][$ref])) { + $msg = "Checking out ".$this->getShortHash($ref).' from cache'; +- $command = '(git rev-parse --quiet --verify %ref% || (git remote set-url composer %cachePath% && git fetch composer && git fetch --tags composer)) && git remote set-url composer %sanitizedUrl%'; ++ $command = '(git rev-parse --quiet --verify %ref% || (git remote set-url composer -- %cachePath% && git fetch composer && git fetch --tags composer)) && git remote set-url composer -- %sanitizedUrl%'; + } else { + $msg = "Checking out ".$this->getShortHash($ref); +- $command = '(git remote set-url composer %url% && git rev-parse --quiet --verify %ref% || (git fetch composer && git fetch --tags composer)) && git remote set-url composer %sanitizedUrl%'; ++ $command = '(git remote set-url composer -- %url% && git rev-parse --quiet --verify %ref% || (git fetch composer && git fetch --tags composer)) && git remote set-url composer -- %sanitizedUrl%'; + if (getenv('COMPOSER_DISABLE_NETWORK')) { + throw new \RuntimeException('The required git reference for '.$target->getName().' is not in cache and network is disabled, aborting'); + } +@@ -476,7 +476,7 @@ class GitDownloader extends VcsDownloader implements DvcsDownloaderInterface + + protected function updateOriginUrl($path, $url) + { +- $this->process->execute(sprintf('git remote set-url origin %s', ProcessExecutor::escape($url)), $output, $path); ++ $this->process->execute(sprintf('git remote set-url origin -- %s', ProcessExecutor::escape($url)), $output, $path); + $this->setPushUrl($path, $url); + } + +@@ -489,7 +489,7 @@ class GitDownloader extends VcsDownloader implements DvcsDownloaderInterface + if (!in_array('ssh', $protocols, true)) { + $pushUrl = 'https://' . $match[1] . '/'.$match[2].'/'.$match[3].'.git'; + } +- $cmd = sprintf('git remote set-url --push origin %s', ProcessExecutor::escape($pushUrl)); ++ $cmd = sprintf('git remote set-url --push origin -- %s', ProcessExecutor::escape($pushUrl)); + $this->process->execute($cmd, $ignoredOutput, $path); + } + } +diff --git a/src/Composer/Downloader/GzipDownloader.php b/src/Composer/Downloader/GzipDownloader.php +index 04dd5e7..e12e091 100644 +--- a/src/Composer/Downloader/GzipDownloader.php ++++ b/src/Composer/Downloader/GzipDownloader.php +@@ -30,7 +30,7 @@ class GzipDownloader extends ArchiveDownloader + + // Try to use gunzip on *nix + if (!Platform::isWindows()) { +- $command = 'gzip -cd ' . ProcessExecutor::escape($file) . ' > ' . ProcessExecutor::escape($targetFilepath); ++ $command = 'gzip -cd -- ' . ProcessExecutor::escape($file) . ' > ' . ProcessExecutor::escape($targetFilepath); + + if (0 === $this->process->execute($command, $ignoredOutput)) { + return; +diff --git a/src/Composer/Downloader/HgDownloader.php b/src/Composer/Downloader/HgDownloader.php +index 59ced01..1997b31 100644 +--- a/src/Composer/Downloader/HgDownloader.php ++++ b/src/Composer/Downloader/HgDownloader.php +@@ -36,13 +36,13 @@ class HgDownloader extends VcsDownloader + $hgUtils = new HgUtils($this->io, $this->config, $this->process); + + $cloneCommand = function ($url) use ($path) { +- return sprintf('hg clone %s %s', ProcessExecutor::escape($url), ProcessExecutor::escape($path)); ++ return sprintf('hg clone -- %s %s', ProcessExecutor::escape($url), ProcessExecutor::escape($path)); + }; + + $hgUtils->runCommand($cloneCommand, $url, $path); + + $ref = ProcessExecutor::escape($package->getSourceReference()); +- $command = sprintf('hg up %s', $ref); ++ $command = sprintf('hg up -- %s', $ref); + if (0 !== $this->process->execute($command, $ignoredOutput, realpath($path))) { + throw new \RuntimeException('Failed to execute ' . $command . "\n\n" . $this->process->getErrorOutput()); + } +@@ -63,7 +63,7 @@ class HgDownloader extends VcsDownloader + } + + $command = function ($url) use ($ref) { +- return sprintf('hg pull %s && hg up %s', ProcessExecutor::escape($url), ProcessExecutor::escape($ref)); ++ return sprintf('hg pull -- %s && hg up -- %s', ProcessExecutor::escape($url), ProcessExecutor::escape($ref)); + }; + + $hgUtils->runCommand($command, $url, $path); +diff --git a/src/Composer/Downloader/RarDownloader.php b/src/Composer/Downloader/RarDownloader.php +index 8951d96..7f58922 100644 +--- a/src/Composer/Downloader/RarDownloader.php ++++ b/src/Composer/Downloader/RarDownloader.php +@@ -33,7 +33,7 @@ class RarDownloader extends ArchiveDownloader + + // Try to use unrar on *nix + if (!Platform::isWindows()) { +- $command = 'unrar x ' . ProcessExecutor::escape($file) . ' ' . ProcessExecutor::escape($path) . ' >/dev/null && chmod -R u+w ' . ProcessExecutor::escape($path); ++ $command = 'unrar x -- ' . ProcessExecutor::escape($file) . ' ' . ProcessExecutor::escape($path) . ' >/dev/null && chmod -R u+w ' . ProcessExecutor::escape($path); + + if (0 === $this->process->execute($command, $ignoredOutput)) { + return; +diff --git a/src/Composer/Downloader/SvnDownloader.php b/src/Composer/Downloader/SvnDownloader.php +index 2f253b4..d2e2adc 100644 +--- a/src/Composer/Downloader/SvnDownloader.php ++++ b/src/Composer/Downloader/SvnDownloader.php +@@ -179,7 +179,7 @@ class SvnDownloader extends VcsDownloader + { + if (preg_match('{@(\d+)$}', $fromReference) && preg_match('{@(\d+)$}', $toReference)) { + // retrieve the svn base url from the checkout folder +- $command = sprintf('svn info --non-interactive --xml %s', ProcessExecutor::escape($path)); ++ $command = sprintf('svn info --non-interactive --xml -- %s', ProcessExecutor::escape($path)); + if (0 !== $this->process->execute($command, $output, $path)) { + throw new \RuntimeException( + 'Failed to execute ' . $command . "\n\n" . $this->process->getErrorOutput() +diff --git a/src/Composer/Repository/Vcs/FossilDriver.php b/src/Composer/Repository/Vcs/FossilDriver.php +index 12218b2..8f73ffb 100644 +--- a/src/Composer/Repository/Vcs/FossilDriver.php ++++ b/src/Composer/Repository/Vcs/FossilDriver.php +@@ -94,13 +94,13 @@ class FossilDriver extends VcsDriver + + $fs->ensureDirectoryExists($this->checkoutDir); + +- if (0 !== $this->process->execute(sprintf('fossil clone %s %s', ProcessExecutor::escape($this->url), ProcessExecutor::escape($this->repoFile)), $output)) { ++ if (0 !== $this->process->execute(sprintf('fossil clone -- %s %s', ProcessExecutor::escape($this->url), ProcessExecutor::escape($this->repoFile)), $output)) { + $output = $this->process->getErrorOutput(); + + throw new \RuntimeException('Failed to clone '.$this->url.' to repository ' . $this->repoFile . "\n\n" .$output); + } + +- if (0 !== $this->process->execute(sprintf('fossil open %s --nested', ProcessExecutor::escape($this->repoFile)), $output, $this->checkoutDir)) { ++ if (0 !== $this->process->execute(sprintf('fossil open --nested -- %s', ProcessExecutor::escape($this->repoFile)), $output, $this->checkoutDir)) { + $output = $this->process->getErrorOutput(); + + throw new \RuntimeException('Failed to open repository '.$this->repoFile.' in ' . $this->checkoutDir . "\n\n" .$output); +@@ -149,7 +149,7 @@ class FossilDriver extends VcsDriver + */ + public function getFileContent($file, $identifier) + { +- $command = sprintf('fossil cat -r %s %s', ProcessExecutor::escape($identifier), ProcessExecutor::escape($file)); ++ $command = sprintf('fossil cat -r %s -- %s', ProcessExecutor::escape($identifier), ProcessExecutor::escape($file)); + $this->process->execute($command, $content, $this->checkoutDir); + + if (!trim($content)) { +diff --git a/src/Composer/Repository/Vcs/GitDriver.php b/src/Composer/Repository/Vcs/GitDriver.php +index 3c3817c..70400e8 100644 +--- a/src/Composer/Repository/Vcs/GitDriver.php ++++ b/src/Composer/Repository/Vcs/GitDriver.php +@@ -227,7 +227,7 @@ class GitDriver extends VcsDriver + + try { + $gitUtil->runCommand(function ($url) { +- return 'git ls-remote --heads ' . ProcessExecutor::escape($url); ++ return 'git ls-remote --heads -- ' . ProcessExecutor::escape($url); + }, $url, sys_get_temp_dir()); + } catch (\RuntimeException $e) { + return false; +diff --git a/src/Composer/Repository/Vcs/HgDriver.php b/src/Composer/Repository/Vcs/HgDriver.php +index 4fa7371..f3b0e6c 100644 +--- a/src/Composer/Repository/Vcs/HgDriver.php ++++ b/src/Composer/Repository/Vcs/HgDriver.php +@@ -67,7 +67,7 @@ class HgDriver extends VcsDriver + + $repoDir = $this->repoDir; + $command = function ($url) use ($repoDir) { +- return sprintf('hg clone --noupdate %s %s', ProcessExecutor::escape($url), ProcessExecutor::escape($repoDir)); ++ return sprintf('hg clone --noupdate -- %s %s', ProcessExecutor::escape($url), ProcessExecutor::escape($repoDir)); + }; + + $hgUtils->runCommand($command, $this->url, null); +@@ -228,7 +228,7 @@ class HgDriver extends VcsDriver + } + + $process = new ProcessExecutor($io); +- $exit = $process->execute(sprintf('hg identify %s', ProcessExecutor::escape($url)), $ignored); ++ $exit = $process->execute(sprintf('hg identify -- %s', ProcessExecutor::escape($url)), $ignored); + + return $exit === 0; + } +diff --git a/src/Composer/Repository/Vcs/SvnDriver.php b/src/Composer/Repository/Vcs/SvnDriver.php +index 8e2c5e7..ab3f95f 100644 +--- a/src/Composer/Repository/Vcs/SvnDriver.php ++++ b/src/Composer/Repository/Vcs/SvnDriver.php +@@ -306,7 +306,7 @@ class SvnDriver extends VcsDriver + + $process = new ProcessExecutor($io); + $exit = $process->execute( +- "svn info --non-interactive ".ProcessExecutor::escape($url), ++ "svn info --non-interactive -- ".ProcessExecutor::escape($url), + $ignoredOutput + ); + +diff --git a/src/Composer/Util/Git.php b/src/Composer/Util/Git.php +index 6539693..312b5b0 100644 +--- a/src/Composer/Util/Git.php ++++ b/src/Composer/Util/Git.php +@@ -261,7 +261,7 @@ class Git + $commandCallable = function ($url) { + $sanitizedUrl = preg_replace('{://([^@]+?):(.+?)@}', '://', $url); + +- return sprintf('git remote set-url origin %s && git remote update --prune origin && git remote set-url origin %s && git gc --auto', ProcessExecutor::escape($url), ProcessExecutor::escape($sanitizedUrl)); ++ return sprintf('git remote set-url origin -- %s && git remote update --prune origin && git remote set-url origin -- %s && git gc --auto', ProcessExecutor::escape($url), ProcessExecutor::escape($sanitizedUrl)); + }; + $this->runCommand($commandCallable, $url, $dir); + } catch (\Exception $e) { +@@ -277,7 +277,7 @@ class Git + $this->filesystem->removeDirectory($dir); + + $commandCallable = function ($url) use ($dir) { +- return sprintf('git clone --mirror %s %s', ProcessExecutor::escape($url), ProcessExecutor::escape($dir)); ++ return sprintf('git clone --mirror -- %s %s', ProcessExecutor::escape($url), ProcessExecutor::escape($dir)); + }; + + $this->runCommand($commandCallable, $url, $dir, true); +diff --git a/src/Composer/Util/Svn.php b/src/Composer/Util/Svn.php +index 6088d0c..da934c1 100644 +--- a/src/Composer/Util/Svn.php ++++ b/src/Composer/Util/Svn.php +@@ -224,7 +224,7 @@ class Svn + protected function getCommand($cmd, $url, $path = null) + { + $cmd = sprintf( +- '%s %s%s %s', ++ '%s %s%s -- %s', + $cmd, + '--non-interactive ', + $this->getCredentialString(), +diff --git a/tests/Composer/Test/Downloader/FossilDownloaderTest.php b/tests/Composer/Test/Downloader/FossilDownloaderTest.php +index dbd07cd..adf26c7 100644 +--- a/tests/Composer/Test/Downloader/FossilDownloaderTest.php ++++ b/tests/Composer/Test/Downloader/FossilDownloaderTest.php +@@ -69,19 +69,19 @@ class FossilDownloaderTest extends TestCase + ->will($this->returnValue(array('http://fossil.kd2.org/kd2fw/'))); + $processExecutor = $this->getMockBuilder('Composer\Util\ProcessExecutor')->getMock(); + +- $expectedFossilCommand = $this->getCmd('fossil clone \'http://fossil.kd2.org/kd2fw/\' \'repo.fossil\''); ++ $expectedFossilCommand = $this->getCmd('fossil clone -- \'http://fossil.kd2.org/kd2fw/\' \'repo.fossil\''); + $processExecutor->expects($this->at(0)) + ->method('execute') + ->with($this->equalTo($expectedFossilCommand)) + ->will($this->returnValue(0)); + +- $expectedFossilCommand = $this->getCmd('fossil open \'repo.fossil\' --nested'); ++ $expectedFossilCommand = $this->getCmd('fossil open --nested -- \'repo.fossil\''); + $processExecutor->expects($this->at(1)) + ->method('execute') + ->with($this->equalTo($expectedFossilCommand)) + ->will($this->returnValue(0)); + +- $expectedFossilCommand = $this->getCmd('fossil update \'trunk\''); ++ $expectedFossilCommand = $this->getCmd('fossil update -- \'trunk\''); + $processExecutor->expects($this->at(2)) + ->method('execute') + ->with($this->equalTo($expectedFossilCommand)) +diff --git a/tests/Composer/Test/Downloader/GitDownloaderTest.php b/tests/Composer/Test/Downloader/GitDownloaderTest.php +index e09b6d4..1a321c8 100644 +--- a/tests/Composer/Test/Downloader/GitDownloaderTest.php ++++ b/tests/Composer/Test/Downloader/GitDownloaderTest.php +@@ -109,7 +109,7 @@ class GitDownloaderTest extends TestCase + ->will($this->returnValue('dev-master')); + $processExecutor = $this->getMockBuilder('Composer\Util\ProcessExecutor')->getMock(); + +- $expectedGitCommand = $this->winCompat("git clone --no-checkout 'https://example.com/composer/composer' 'composerPath' && cd 'composerPath' && git remote add composer 'https://example.com/composer/composer' && git fetch composer && git remote set-url origin 'https://example.com/composer/composer' && git remote set-url composer 'https://example.com/composer/composer'"); ++ $expectedGitCommand = $this->winCompat("git clone --no-checkout -- 'https://example.com/composer/composer' 'composerPath' && cd 'composerPath' && git remote add composer -- 'https://example.com/composer/composer' && git fetch composer && git remote set-url origin -- 'https://example.com/composer/composer' && git remote set-url composer -- 'https://example.com/composer/composer'"); + $processExecutor->expects($this->at(0)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) +@@ -158,7 +158,7 @@ class GitDownloaderTest extends TestCase + $filesystem = new \Composer\Util\Filesystem; + $filesystem->removeDirectory($cachePath); + +- $expectedGitCommand = $this->winCompat(sprintf("git clone --mirror 'https://example.com/composer/composer' '%s'", $cachePath)); ++ $expectedGitCommand = $this->winCompat(sprintf("git clone --mirror -- 'https://example.com/composer/composer' '%s'", $cachePath)); + $processExecutor->expects($this->at(0)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) +@@ -180,7 +180,7 @@ class GitDownloaderTest extends TestCase + ->with($this->equalTo($this->winCompat('git rev-parse --quiet --verify \'1234567890123456789012345678901234567890^{commit}\'')), $this->equalTo(null), $this->equalTo($this->winCompat($cachePath))) + ->will($this->returnValue(0)); + +- $expectedGitCommand = $this->winCompat(sprintf("git clone --no-checkout '%1\$s' 'composerPath' --dissociate --reference '%1\$s' && cd 'composerPath' && git remote set-url origin 'https://example.com/composer/composer' && git remote add composer 'https://example.com/composer/composer'", $cachePath)); ++ $expectedGitCommand = $this->winCompat(sprintf("git clone --no-checkout '%1\$s' 'composerPath' --dissociate --reference '%1\$s' && cd 'composerPath' && git remote set-url origin -- 'https://example.com/composer/composer' && git remote add composer -- 'https://example.com/composer/composer'", $cachePath)); + $processExecutor->expects($this->at(3)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) +@@ -221,7 +221,7 @@ class GitDownloaderTest extends TestCase + ->will($this->returnValue('1.0.0')); + $processExecutor = $this->getMockBuilder('Composer\Util\ProcessExecutor')->getMock(); + +- $expectedGitCommand = $this->winCompat("git clone --no-checkout 'https://github.com/mirrors/composer' 'composerPath' && cd 'composerPath' && git remote add composer 'https://github.com/mirrors/composer' && git fetch composer && git remote set-url origin 'https://github.com/mirrors/composer' && git remote set-url composer 'https://github.com/mirrors/composer'"); ++ $expectedGitCommand = $this->winCompat("git clone --no-checkout -- 'https://github.com/mirrors/composer' 'composerPath' && cd 'composerPath' && git remote add composer -- 'https://github.com/mirrors/composer' && git fetch composer && git remote set-url origin -- 'https://github.com/mirrors/composer' && git remote set-url composer -- 'https://github.com/mirrors/composer'"); + $processExecutor->expects($this->at(0)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) +@@ -232,19 +232,19 @@ class GitDownloaderTest extends TestCase + ->with() + ->will($this->returnValue('Error1')); + +- $expectedGitCommand = $this->winCompat("git clone --no-checkout '[email protected]:mirrors/composer' 'composerPath' && cd 'composerPath' && git remote add composer '[email protected]:mirrors/composer' && git fetch composer && git remote set-url origin '[email protected]:mirrors/composer' && git remote set-url composer '[email protected]:mirrors/composer'"); ++ $expectedGitCommand = $this->winCompat("git clone --no-checkout -- '[email protected]:mirrors/composer' 'composerPath' && cd 'composerPath' && git remote add composer -- '[email protected]:mirrors/composer' && git fetch composer && git remote set-url origin -- '[email protected]:mirrors/composer' && git remote set-url composer -- '[email protected]:mirrors/composer'"); + $processExecutor->expects($this->at(2)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) + ->will($this->returnValue(0)); + +- $expectedGitCommand = $this->winCompat("git remote set-url origin 'https://github.com/composer/composer'"); ++ $expectedGitCommand = $this->winCompat("git remote set-url origin -- 'https://github.com/composer/composer'"); + $processExecutor->expects($this->at(3)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand), $this->equalTo(null), $this->equalTo($this->winCompat('composerPath'))) + ->will($this->returnValue(0)); + +- $expectedGitCommand = $this->winCompat("git remote set-url --push origin '[email protected]:composer/composer.git'"); ++ $expectedGitCommand = $this->winCompat("git remote set-url --push origin -- '[email protected]:composer/composer.git'"); + $processExecutor->expects($this->at(4)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand), $this->equalTo(null), $this->equalTo($this->winCompat('composerPath'))) +@@ -299,13 +299,13 @@ class GitDownloaderTest extends TestCase + ->will($this->returnValue('1.0.0')); + $processExecutor = $this->getMockBuilder('Composer\Util\ProcessExecutor')->getMock(); + +- $expectedGitCommand = $this->winCompat("git clone --no-checkout '{$url}' 'composerPath' && cd 'composerPath' && git remote add composer '{$url}' && git fetch composer && git remote set-url origin '{$url}' && git remote set-url composer '{$url}'"); ++ $expectedGitCommand = $this->winCompat("git clone --no-checkout -- '{$url}' 'composerPath' && cd 'composerPath' && git remote add composer -- '{$url}' && git fetch composer && git remote set-url origin -- '{$url}' && git remote set-url composer -- '{$url}'"); + $processExecutor->expects($this->at(0)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) + ->will($this->returnValue(0)); + +- $expectedGitCommand = $this->winCompat("git remote set-url --push origin '{$pushUrl}'"); ++ $expectedGitCommand = $this->winCompat("git remote set-url --push origin -- '{$pushUrl}'"); + $processExecutor->expects($this->at(1)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand), $this->equalTo(null), $this->equalTo($this->winCompat('composerPath'))) +@@ -327,7 +327,7 @@ class GitDownloaderTest extends TestCase + + public function testDownloadThrowsRuntimeExceptionIfGitCommandFails() + { +- $expectedGitCommand = $this->winCompat("git clone --no-checkout 'https://example.com/composer/composer' 'composerPath' && cd 'composerPath' && git remote add composer 'https://example.com/composer/composer' && git fetch composer && git remote set-url origin 'https://example.com/composer/composer' && git remote set-url composer 'https://example.com/composer/composer'"); ++ $expectedGitCommand = $this->winCompat("git clone --no-checkout -- 'https://example.com/composer/composer' 'composerPath' && cd 'composerPath' && git remote add composer -- 'https://example.com/composer/composer' && git fetch composer && git remote set-url origin -- 'https://example.com/composer/composer' && git remote set-url composer -- 'https://example.com/composer/composer'"); + $packageMock = $this->getMockBuilder('Composer\Package\PackageInterface')->getMock(); + $packageMock->expects($this->any()) + ->method('getSourceReference') +@@ -376,7 +376,7 @@ class GitDownloaderTest extends TestCase + + public function testUpdate() + { +- $expectedGitUpdateCommand = $this->winCompat("(git remote set-url composer 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer 'https://github.com/composer/composer'"); ++ $expectedGitUpdateCommand = $this->winCompat("(git remote set-url composer -- 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer -- 'https://github.com/composer/composer'"); + + $packageMock = $this->getMockBuilder('Composer\Package\PackageInterface')->getMock(); + $packageMock->expects($this->any()) +@@ -407,7 +407,7 @@ class GitDownloaderTest extends TestCase + + public function testUpdateWithNewRepoUrl() + { +- $expectedGitUpdateCommand = $this->winCompat("(git remote set-url composer 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer 'https://github.com/composer/composer'"); ++ $expectedGitUpdateCommand = $this->winCompat("(git remote set-url composer -- 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer -- 'https://github.com/composer/composer'"); + + $packageMock = $this->getMockBuilder('Composer\Package\PackageInterface')->getMock(); + $packageMock->expects($this->any()) +@@ -462,11 +462,11 @@ composer https://github.com/old/url (push) + })); + $processExecutor->expects($this->at(7)) + ->method('execute') +- ->with($this->equalTo($this->winCompat("git remote set-url origin 'https://github.com/composer/composer'")), $this->equalTo(null), $this->equalTo($this->winCompat($this->workingDir))) ++ ->with($this->equalTo($this->winCompat("git remote set-url origin -- 'https://github.com/composer/composer'")), $this->equalTo(null), $this->equalTo($this->winCompat($this->workingDir))) + ->will($this->returnValue(0)); + $processExecutor->expects($this->at(8)) + ->method('execute') +- ->with($this->equalTo($this->winCompat("git remote set-url --push origin '[email protected]:composer/composer.git'")), $this->equalTo(null), $this->equalTo($this->winCompat($this->workingDir))) ++ ->with($this->equalTo($this->winCompat("git remote set-url --push origin -- '[email protected]:composer/composer.git'")), $this->equalTo(null), $this->equalTo($this->winCompat($this->workingDir))) + ->will($this->returnValue(0)); + + $this->fs->ensureDirectoryExists($this->workingDir.'/.git'); +@@ -482,8 +482,8 @@ composer https://github.com/old/url (push) + */ + public function testUpdateThrowsRuntimeExceptionIfGitCommandFails() + { +- $expectedGitUpdateCommand = $this->winCompat("(git remote set-url composer 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer 'https://github.com/composer/composer'"); +- $expectedGitUpdateCommand2 = $this->winCompat("(git remote set-url composer '[email protected]:composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer '[email protected]:composer/composer'"); ++ $expectedGitUpdateCommand = $this->winCompat("(git remote set-url composer -- 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer -- 'https://github.com/composer/composer'"); ++ $expectedGitUpdateCommand2 = $this->winCompat("(git remote set-url composer -- '[email protected]:composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer -- '[email protected]:composer/composer'"); + + $packageMock = $this->getMockBuilder('Composer\Package\PackageInterface')->getMock(); + $packageMock->expects($this->any()) +@@ -526,8 +526,8 @@ composer https://github.com/old/url (push) + + public function testUpdateDoesntThrowsRuntimeExceptionIfGitCommandFailsAtFirstButIsAbleToRecover() + { +- $expectedFirstGitUpdateCommand = $this->winCompat("(git remote set-url composer '".(Platform::isWindows() ? 'C:\\\\' : '/')."' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer '".(Platform::isWindows() ? 'C:\\\\' : '/')."'"); +- $expectedSecondGitUpdateCommand = $this->winCompat("(git remote set-url composer 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer 'https://github.com/composer/composer'"); ++ $expectedFirstGitUpdateCommand = $this->winCompat("(git remote set-url composer -- '".(Platform::isWindows() ? 'C:\\\\' : '/')."' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer -- '".(Platform::isWindows() ? 'C:\\\\' : '/')."'"); ++ $expectedSecondGitUpdateCommand = $this->winCompat("(git remote set-url composer -- 'https://github.com/composer/composer' && git rev-parse --quiet --verify 'ref^{commit}' || (git fetch composer && git fetch --tags composer)) && git remote set-url composer -- 'https://github.com/composer/composer'"); + + $packageMock = $this->getMockBuilder('Composer\Package\PackageInterface')->getMock(); + $packageMock->expects($this->any()) +diff --git a/tests/Composer/Test/Downloader/HgDownloaderTest.php b/tests/Composer/Test/Downloader/HgDownloaderTest.php +index 64f72d1..14afdcf 100644 +--- a/tests/Composer/Test/Downloader/HgDownloaderTest.php ++++ b/tests/Composer/Test/Downloader/HgDownloaderTest.php +@@ -69,13 +69,13 @@ class HgDownloaderTest extends TestCase + ->will($this->returnValue(array('https://mercurial.dev/l3l0/composer'))); + $processExecutor = $this->getMockBuilder('Composer\Util\ProcessExecutor')->getMock(); + +- $expectedGitCommand = $this->getCmd('hg clone \'https://mercurial.dev/l3l0/composer\' \'composerPath\''); ++ $expectedGitCommand = $this->getCmd('hg clone -- \'https://mercurial.dev/l3l0/composer\' \'composerPath\''); + $processExecutor->expects($this->at(0)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) + ->will($this->returnValue(0)); + +- $expectedGitCommand = $this->getCmd('hg up \'ref\''); ++ $expectedGitCommand = $this->getCmd('hg up -- \'ref\''); + $processExecutor->expects($this->at(1)) + ->method('execute') + ->with($this->equalTo($expectedGitCommand)) +@@ -122,7 +122,7 @@ class HgDownloaderTest extends TestCase + ->method('execute') + ->with($this->equalTo($expectedHgCommand)) + ->will($this->returnValue(0)); +- $expectedHgCommand = $this->getCmd("hg pull 'https://github.com/l3l0/composer' && hg up 'ref'"); ++ $expectedHgCommand = $this->getCmd("hg pull -- 'https://github.com/l3l0/composer' && hg up -- 'ref'"); + $processExecutor->expects($this->at(1)) + ->method('execute') + ->with($this->equalTo($expectedHgCommand)) +diff --git a/tests/Composer/Test/Util/SvnTest.php b/tests/Composer/Test/Util/SvnTest.php +index 03a1835..ada3818 100644 +--- a/tests/Composer/Test/Util/SvnTest.php ++++ b/tests/Composer/Test/Util/SvnTest.php +@@ -60,7 +60,7 @@ class SvnTest extends TestCase + $reflMethod->setAccessible(true); + + $this->assertEquals( +- $this->getCmd("svn ls --non-interactive 'http://svn.example.org'"), ++ $this->getCmd("svn ls --non-interactive -- 'http://svn.example.org'"), + $reflMethod->invokeArgs($svn, array('svn ls', $url)) + ); + } diff -Nru composer-2.0.9/debian/patches/series composer-2.0.9/debian/patches/series --- composer-2.0.9/debian/patches/series 2021-01-28 23:53:35.000000000 +0100 +++ composer-2.0.9/debian/patches/series 2021-04-28 00:18:57.000000000 +0200 @@ -6,3 +6,4 @@ 0007-Tag-test-relying-on-git-repository.patch 0007-Use-expectException-instead-of-setExpectedException.patch 0008-Compatibility-with-recent-PHPUnit-8.patch +0009-Merge-pull-request-from-GHSA-h5h8-pc6h-jvvx.patch

