Merge "shell: Add NO_LOCALSETTINGS restriction"
authorjenkins-bot <jenkins-bot@gerrit.wikimedia.org>
Fri, 22 Dec 2017 01:44:22 +0000 (01:44 +0000)
committerGerrit Code Review <gerrit@wikimedia.org>
Fri, 22 Dec 2017 01:44:22 +0000 (01:44 +0000)
1  2 
includes/shell/FirejailCommand.php
tests/phpunit/includes/shell/FirejailCommandTest.php

@@@ -59,15 -59,10 +59,15 @@@ class FirejailCommand extends Command 
        /**
         * @inheritDoc
         */
 -      protected function buildFinalCommand() {
 +      protected function buildFinalCommand( $command ) {
                // If there are no restrictions, don't use firejail
                if ( $this->restrictions === 0 ) {
 -                      return parent::buildFinalCommand();
 +                      $splitCommand = explode( ' ', $command, 2 );
 +                      $this->logger->debug(
 +                              "firejail: Command {$splitCommand[0]} {params} has no restrictions",
 +                              [ 'params' => isset( $splitCommand[1] ) ? $splitCommand[1] : '' ]
 +                      );
 +                      return parent::buildFinalCommand( $command );
                }
  
                if ( $this->firejail === false ) {
                        }
                }
  
+               if ( $this->hasRestriction( Shell::NO_LOCALSETTINGS ) ) {
+                       $cmd[] = '--blacklist=' . realpath( MW_CONFIG_FILE );
+               }
                if ( $this->hasRestriction( Shell::NO_ROOT ) ) {
                        $cmd[] = '--noroot';
                }
  
                if ( $this->hasRestriction( Shell::NO_EXECVE ) ) {
                        $seccomp[] = 'execve';
 +                      // Normally firejail will run commands in a bash shell,
 +                      // but that won't work if we ban the execve syscall, so
 +                      // run the command without a shell.
 +                      $cmd[] = '--shell=none';
                }
  
                if ( $seccomp ) {
                        $cmd[] = '--net=none';
                }
  
 -              list( $fullCommand, $useLogPipe ) = parent::buildFinalCommand();
 -
                $builtCmd = implode( ' ', $cmd );
  
 -              return [ "$builtCmd -- $fullCommand", $useLogPipe ];
 +              // Prefix the firejail command in front of the wanted command
 +              return parent::buildFinalCommand( "$builtCmd -- {$command}" );
        }
  
  }
@@@ -29,38 -29,39 +29,39 @@@ class FirejailCommandTest extends PHPUn
                // @codingStandardsIgnoreStart
                $env = "'MW_INCLUDE_STDERR=;MW_CPU_LIMIT=180; MW_CGROUP='\'''\''; MW_MEM_LIMIT=307200; MW_FILE_SIZE_LIMIT=102400; MW_WALL_CLOCK_LIMIT=180; MW_USE_LOG_PIPE=yes'";
                // @codingStandardsIgnoreEnd
 -              $limit = "$IP/includes/shell/limit.sh";
 +              $limit = "/bin/bash '$IP/includes/shell/limit.sh'";
                $profile = "--profile=$IP/includes/shell/firejail.profile";
-               $default = '--noroot --seccomp=@default --private-dev';
+               $blacklist = '--blacklist=' . realpath( MW_CONFIG_FILE );
+               $default = "$blacklist --noroot --seccomp=@default --private-dev";
                return [
                        [
                                'No restrictions',
 -                              'ls', 0, "/bin/bash '$limit' ''\''ls'\''' $env"
 +                              'ls', 0, "$limit ''\''ls'\''' $env"
                        ],
                        [
                                'default restriction',
                                'ls', Shell::RESTRICT_DEFAULT,
 -                              "firejail --quiet $profile $default -- /bin/bash '$limit' ''\''ls'\''' $env"
 +                              "$limit 'firejail --quiet $profile $default -- '\''ls'\''' $env"
                        ],
                        [
                                'no network',
                                'ls', Shell::NO_NETWORK,
 -                              "firejail --quiet $profile --net=none -- /bin/bash '$limit' ''\''ls'\''' $env"
 +                              "$limit 'firejail --quiet $profile --net=none -- '\''ls'\''' $env"
                        ],
                        [
                                'default restriction & no network',
                                'ls', Shell::RESTRICT_DEFAULT | Shell::NO_NETWORK,
 -                              "firejail --quiet $profile $default --net=none -- /bin/bash '$limit' ''\''ls'\''' $env"
 +                              "$limit 'firejail --quiet $profile $default --net=none -- '\''ls'\''' $env"
                        ],
                        [
                                'seccomp',
                                'ls', Shell::SECCOMP,
 -                              "firejail --quiet $profile --seccomp=@default -- /bin/bash '$limit' ''\''ls'\''' $env"
 +                              "$limit 'firejail --quiet $profile --seccomp=@default -- '\''ls'\''' $env"
                        ],
                        [
                                'seccomp & no execve',
                                'ls', Shell::SECCOMP | Shell::NO_EXECVE,
 -                              "firejail --quiet $profile --seccomp=@default,execve -- /bin/bash '$limit' ''\''ls'\''' $env"
 +                              "$limit 'firejail --quiet $profile --shell=none --seccomp=@default,execve -- '\''ls'\''' $env"
                        ],
                ];
        }
@@@ -75,7 -76,7 +76,7 @@@
                        ->params( $params )
                        ->restrict( $flags );
                $wrapper = TestingAccessWrapper::newFromObject( $command );
 -              $output = $wrapper->buildFinalCommand();
 +              $output = $wrapper->buildFinalCommand( $wrapper->command );
                $this->assertEquals( $expected, $output[0], $desc );
        }