Merge pull request #1555 from mtmail/setup-escape-shell-args

setup: escape arguments when executing shell commands (psql, createdb)
This commit is contained in:
Sarah Hoffmann 2019-11-06 22:47:00 +01:00 committed by GitHub
commit f42e40712e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 41 additions and 30 deletions

View File

@ -284,7 +284,7 @@ class DB
{ {
// https://secure.php.net/manual/en/ref.pdo-pgsql.connection.php // https://secure.php.net/manual/en/ref.pdo-pgsql.connection.php
$aInfo = array(); $aInfo = array();
if (preg_match('/^pgsql:(.+)/', $sDSN, $aMatches)) { if (preg_match('/^pgsql:(.+)$/', $sDSN, $aMatches)) {
foreach (explode(';', $aMatches[1]) as $sKeyVal) { foreach (explode(';', $aMatches[1]) as $sKeyVal) {
list($sKey, $sVal) = explode('=', $sKeyVal, 2); list($sKey, $sVal) = explode('=', $sKeyVal, 2);
if ($sKey == 'host') $sKey = 'hostspec'; if ($sKey == 'host') $sKey = 'hostspec';

View File

@ -148,12 +148,14 @@ function runSQLScript($sScript, $bfatal = true, $bVerbose = false, $bIgnoreError
// Convert database DSN to psql parameters // Convert database DSN to psql parameters
$aDSNInfo = \Nominatim\DB::parseDSN(CONST_Database_DSN); $aDSNInfo = \Nominatim\DB::parseDSN(CONST_Database_DSN);
if (!isset($aDSNInfo['port']) || !$aDSNInfo['port']) $aDSNInfo['port'] = 5432; if (!isset($aDSNInfo['port']) || !$aDSNInfo['port']) $aDSNInfo['port'] = 5432;
$sCMD = 'psql -p '.$aDSNInfo['port'].' -d '.$aDSNInfo['database']; $sCMD = 'psql'
.' -p '.escapeshellarg($aDSNInfo['port'])
.' -d '.escapeshellarg($aDSNInfo['database']);
if (isset($aDSNInfo['hostspec']) && $aDSNInfo['hostspec']) { if (isset($aDSNInfo['hostspec']) && $aDSNInfo['hostspec']) {
$sCMD .= ' -h ' . $aDSNInfo['hostspec']; $sCMD .= ' -h ' . escapeshellarg($aDSNInfo['hostspec']);
} }
if (isset($aDSNInfo['username']) && $aDSNInfo['username']) { if (isset($aDSNInfo['username']) && $aDSNInfo['username']) {
$sCMD .= ' -U ' . $aDSNInfo['username']; $sCMD .= ' -U ' . escapeshellarg($aDSNInfo['username']);
} }
$aProcEnv = null; $aProcEnv = null;
if (isset($aDSNInfo['password']) && $aDSNInfo['password']) { if (isset($aDSNInfo['password']) && $aDSNInfo['password']) {

View File

@ -80,13 +80,15 @@ class SetupFunctions
fail('database already exists ('.CONST_Database_DSN.')'); fail('database already exists ('.CONST_Database_DSN.')');
} }
$sCreateDBCmd = 'createdb -E UTF-8 -p '.$this->aDSNInfo['port'].' '.$this->aDSNInfo['database']; $sCreateDBCmd = 'createdb -E UTF-8'
.' -p '.escapeshellarg($this->aDSNInfo['port'])
.' '.escapeshellarg($this->aDSNInfo['database']);
if (isset($this->aDSNInfo['username'])) { if (isset($this->aDSNInfo['username'])) {
$sCreateDBCmd .= ' -U '.$this->aDSNInfo['username']; $sCreateDBCmd .= ' -U '.escapeshellarg($this->aDSNInfo['username']);
} }
if (isset($this->aDSNInfo['hostspec'])) { if (isset($this->aDSNInfo['hostspec'])) {
$sCreateDBCmd .= ' -h '.$this->aDSNInfo['hostspec']; $sCreateDBCmd .= ' -h '.escapeshellarg($this->aDSNInfo['hostspec']);
} }
$result = $this->runWithPgEnv($sCreateDBCmd); $result = $this->runWithPgEnv($sCreateDBCmd);
@ -178,30 +180,30 @@ class SetupFunctions
fail("osm2pgsql not found in '$osm2pgsql'"); fail("osm2pgsql not found in '$osm2pgsql'");
} }
$osm2pgsql .= ' -S '.CONST_Import_Style; $osm2pgsql .= ' -S '.escapeshellarg(CONST_Import_Style);
if (!is_null(CONST_Osm2pgsql_Flatnode_File) && CONST_Osm2pgsql_Flatnode_File) { if (!is_null(CONST_Osm2pgsql_Flatnode_File) && CONST_Osm2pgsql_Flatnode_File) {
$osm2pgsql .= ' --flat-nodes '.CONST_Osm2pgsql_Flatnode_File; $osm2pgsql .= ' --flat-nodes '.escapeshellarg(CONST_Osm2pgsql_Flatnode_File);
} }
if (CONST_Tablespace_Osm2pgsql_Data) if (CONST_Tablespace_Osm2pgsql_Data)
$osm2pgsql .= ' --tablespace-slim-data '.CONST_Tablespace_Osm2pgsql_Data; $osm2pgsql .= ' --tablespace-slim-data '.escapeshellarg(CONST_Tablespace_Osm2pgsql_Data);
if (CONST_Tablespace_Osm2pgsql_Index) if (CONST_Tablespace_Osm2pgsql_Index)
$osm2pgsql .= ' --tablespace-slim-index '.CONST_Tablespace_Osm2pgsql_Index; $osm2pgsql .= ' --tablespace-slim-index '.escapeshellarg(CONST_Tablespace_Osm2pgsql_Index);
if (CONST_Tablespace_Place_Data) if (CONST_Tablespace_Place_Data)
$osm2pgsql .= ' --tablespace-main-data '.CONST_Tablespace_Place_Data; $osm2pgsql .= ' --tablespace-main-data '.escapeshellarg(CONST_Tablespace_Place_Data);
if (CONST_Tablespace_Place_Index) if (CONST_Tablespace_Place_Index)
$osm2pgsql .= ' --tablespace-main-index '.CONST_Tablespace_Place_Index; $osm2pgsql .= ' --tablespace-main-index '.escapeshellarg(CONST_Tablespace_Place_Index);
$osm2pgsql .= ' -lsc -O gazetteer --hstore --number-processes 1'; $osm2pgsql .= ' -lsc -O gazetteer --hstore --number-processes 1';
$osm2pgsql .= ' -C '.$this->iCacheMemory; $osm2pgsql .= ' -C '.escapeshellarg($this->iCacheMemory);
$osm2pgsql .= ' -P '.$this->aDSNInfo['port']; $osm2pgsql .= ' -P '.escapeshellarg($this->aDSNInfo['port']);
if (isset($this->aDSNInfo['username'])) { if (isset($this->aDSNInfo['username'])) {
$osm2pgsql .= ' -U '.$this->aDSNInfo['username']; $osm2pgsql .= ' -U '.escapeshellarg($this->aDSNInfo['username']);
} }
if (isset($this->aDSNInfo['hostspec'])) { if (isset($this->aDSNInfo['hostspec'])) {
$osm2pgsql .= ' -H '.$this->aDSNInfo['hostspec']; $osm2pgsql .= ' -H '.escapeshellarg($this->aDSNInfo['hostspec']);
} }
$osm2pgsql .= ' -d '.$this->aDSNInfo['database'].' '.$sOSMFile; $osm2pgsql .= ' -d '.escapeshellarg($this->aDSNInfo['database']).' '.escapeshellarg($sOSMFile);
$this->runWithPgEnv($osm2pgsql); $this->runWithPgEnv($osm2pgsql);
@ -599,13 +601,15 @@ class SetupFunctions
public function index($bIndexNoanalyse) public function index($bIndexNoanalyse)
{ {
$sOutputFile = ''; $sOutputFile = '';
$sBaseCmd = CONST_InstallPath.'/nominatim/nominatim -i -d '.$this->aDSNInfo['database'].' -P ' $sBaseCmd = CONST_InstallPath.'/nominatim/nominatim -i'
.$this->aDSNInfo['port'].' -t '.$this->iInstances.$sOutputFile; .' -d '.escapeshellarg($this->aDSNInfo['database'])
.' -P '.escapeshellarg($this->aDSNInfo['port'])
.' -t '.escapeshellarg($this->iInstances.$sOutputFile);
if (isset($this->aDSNInfo['hostspec'])) { if (isset($this->aDSNInfo['hostspec'])) {
$sBaseCmd .= ' -H '.$this->aDSNInfo['hostspec']; $sBaseCmd .= ' -H '.escapeshellarg($this->aDSNInfo['hostspec']);
} }
if (isset($this->aDSNInfo['username'])) { if (isset($this->aDSNInfo['username'])) {
$sBaseCmd .= ' -U '.$this->aDSNInfo['username']; $sBaseCmd .= ' -U '.escapeshellarg($this->aDSNInfo['username']);
} }
info('Index ranks 0 - 4'); info('Index ranks 0 - 4');
@ -742,15 +746,18 @@ class SetupFunctions
private function pgsqlRunDropAndRestore($sDumpFile) private function pgsqlRunDropAndRestore($sDumpFile)
{ {
$sCMD = 'pg_restore -p '.$this->aDSNInfo['port'].' -d '.$this->aDSNInfo['database'].' --no-owner -Fc --clean '.$sDumpFile; $sCMD = 'pg_restore'
.' -p '.escapeshellarg($this->aDSNInfo['port'])
.' -d '.escapeshellarg($this->aDSNInfo['database'])
.' --no-owner -Fc --clean '.escapeshellarg($sDumpFile);
if ($this->oDB->getPostgresVersion() >= 9.04) { if ($this->oDB->getPostgresVersion() >= 9.04) {
$sCMD .= ' --if-exists'; $sCMD .= ' --if-exists';
} }
if (isset($this->aDSNInfo['hostspec'])) { if (isset($this->aDSNInfo['hostspec'])) {
$sCMD .= ' -h '.$this->aDSNInfo['hostspec']; $sCMD .= ' -h '.escapeshellarg($this->aDSNInfo['hostspec']);
} }
if (isset($this->aDSNInfo['username'])) { if (isset($this->aDSNInfo['username'])) {
$sCMD .= ' -U '.$this->aDSNInfo['username']; $sCMD .= ' -U '.escapeshellarg($this->aDSNInfo['username']);
} }
$this->runWithPgEnv($sCMD); $this->runWithPgEnv($sCMD);
@ -814,15 +821,17 @@ class SetupFunctions
{ {
if (!file_exists($sFilename)) fail('unable to find '.$sFilename); if (!file_exists($sFilename)) fail('unable to find '.$sFilename);
$sCMD = 'psql -p '.$this->aDSNInfo['port'].' -d '.$this->aDSNInfo['database']; $sCMD = 'psql'
.' -p '.escapeshellarg($this->aDSNInfo['port'])
.' -d '.escapeshellarg($this->aDSNInfo['database']);
if (!$this->bVerbose) { if (!$this->bVerbose) {
$sCMD .= ' -q'; $sCMD .= ' -q';
} }
if (isset($this->aDSNInfo['hostspec'])) { if (isset($this->aDSNInfo['hostspec'])) {
$sCMD .= ' -h '.$this->aDSNInfo['hostspec']; $sCMD .= ' -h '.escapeshellarg($this->aDSNInfo['hostspec']);
} }
if (isset($this->aDSNInfo['username'])) { if (isset($this->aDSNInfo['username'])) {
$sCMD .= ' -U '.$this->aDSNInfo['username']; $sCMD .= ' -U '.escapeshellarg($this->aDSNInfo['username']);
} }
$aProcEnv = null; $aProcEnv = null;
if (isset($this->aDSNInfo['password'])) { if (isset($this->aDSNInfo['password'])) {
@ -835,12 +844,12 @@ class SetupFunctions
1 => array('pipe', 'w'), 1 => array('pipe', 'w'),
2 => array('file', '/dev/null', 'a') 2 => array('file', '/dev/null', 'a')
); );
$hGzipProcess = proc_open('zcat '.$sFilename, $aDescriptors, $ahGzipPipes); $hGzipProcess = proc_open('zcat '.escapeshellarg($sFilename), $aDescriptors, $ahGzipPipes);
if (!is_resource($hGzipProcess)) fail('unable to start zcat'); if (!is_resource($hGzipProcess)) fail('unable to start zcat');
$aReadPipe = $ahGzipPipes[1]; $aReadPipe = $ahGzipPipes[1];
fclose($ahGzipPipes[0]); fclose($ahGzipPipes[0]);
} else { } else {
$sCMD .= ' -f '.$sFilename; $sCMD .= ' -f '.escapeshellarg($sFilename);
$aReadPipe = array('pipe', 'r'); $aReadPipe = array('pipe', 'r');
} }
$aDescriptors = array( $aDescriptors = array(