|
| 1 | +<?php |
| 2 | + |
| 3 | +namespace Drupal\Core\Security; |
| 4 | + |
| 5 | +use TYPO3\PharStreamWrapper\Assertable; |
| 6 | +use TYPO3\PharStreamWrapper\Helper; |
| 7 | +use TYPO3\PharStreamWrapper\Exception; |
| 8 | + |
| 9 | +/** |
| 10 | + * An alternate PharExtensionInterceptor to support phar-based CLI tools. |
| 11 | + * |
| 12 | + * @see \TYPO3\PharStreamWrapper\Interceptor\PharExtensionInterceptor |
| 13 | + */ |
| 14 | +class PharExtensionInterceptor implements Assertable { |
| 15 | + |
| 16 | + /** |
| 17 | + * Determines whether phar file is allowed to execute. |
| 18 | + * |
| 19 | + * The phar file is allowed to execute if: |
| 20 | + * - the base file name has a ".phar" suffix. |
| 21 | + * - it is the CLI tool that has invoked the interceptor. |
| 22 | + * |
| 23 | + * @param string $path |
| 24 | + * The path of the phar file to check. |
| 25 | + * |
| 26 | + * @param string $command |
| 27 | + * The command being carried out. |
| 28 | + * |
| 29 | + * @return bool |
| 30 | + * TRUE if the phar file is allowed to execute. |
| 31 | + * |
| 32 | + * @throws Exception |
| 33 | + * Thrown when the file is not allowed to execute. |
| 34 | + */ |
| 35 | + public function assert($path, $command) { |
| 36 | + if ($this->baseFileContainsPharExtension($path)) { |
| 37 | + return TRUE; |
| 38 | + } |
| 39 | + throw new Exception( |
| 40 | + sprintf( |
| 41 | + 'Unexpected file extension in "%s"', |
| 42 | + $path |
| 43 | + ), |
| 44 | + 1535198703 |
| 45 | + ); |
| 46 | + } |
| 47 | + |
| 48 | + /** |
| 49 | + * @param string $path |
| 50 | + * The path of the phar file to check. |
| 51 | + * |
| 52 | + * @return bool |
| 53 | + * TRUE if the file has a .phar extension or if the execution has been |
| 54 | + * invoked by the phar file. |
| 55 | + */ |
| 56 | + private function baseFileContainsPharExtension($path) { |
| 57 | + $baseFile = Helper::determineBaseFile($path); |
| 58 | + if ($baseFile === NULL) { |
| 59 | + return FALSE; |
| 60 | + } |
| 61 | + // If the stream wrapper is registered by invoking a phar file that does |
| 62 | + // not not have .phar extension then this should be allowed. For |
| 63 | + // example, some CLI tools recommend removing the extension. |
| 64 | + $backtrace = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS); |
| 65 | + $caller = array_pop($backtrace); |
| 66 | + if (isset($caller['file']) && $baseFile === $caller['file']) { |
| 67 | + return TRUE; |
| 68 | + } |
| 69 | + $fileExtension = pathinfo($baseFile, PATHINFO_EXTENSION); |
| 70 | + return strtolower($fileExtension) === 'phar'; |
| 71 | + } |
| 72 | + |
| 73 | +} |
0 commit comments