Issues (4069)

Security Analysis    not enabled

This project does not seem to handle request data directly as such no vulnerable execution paths were found.

  Cross-Site Scripting
Cross-Site Scripting enables an attacker to inject code into the response of a web-request that is viewed by other users. It can for example be used to bypass access controls, or even to take over other users' accounts.
  File Exposure
File Exposure allows an attacker to gain access to local files that he should not be able to access. These files can for example include database credentials, or other configuration files.
  File Manipulation
File Manipulation enables an attacker to write custom data to files. This potentially leads to injection of arbitrary code on the server.
  Object Injection
Object Injection enables an attacker to inject an object into PHP code, and can lead to arbitrary code execution, file exposure, or file manipulation attacks.
  Code Injection
Code Injection enables an attacker to execute arbitrary code on the server.
  Response Splitting
Response Splitting can be used to send arbitrary responses.
  File Inclusion
File Inclusion enables an attacker to inject custom files into PHP's file loading mechanism, either explicitly passed to include, or for example via PHP's auto-loading mechanism.
  Command Injection
Command Injection enables an attacker to inject a shell command that is execute with the privileges of the web-server. This can be used to expose sensitive data, or gain access of your server.
  SQL Injection
SQL Injection enables an attacker to execute arbitrary SQL code on your database server gaining access to user data, or manipulating user data.
  XPath Injection
XPath Injection enables an attacker to modify the parts of XML document that are read. If that XML document is for example used for authentication, this can lead to further vulnerabilities similar to SQL Injection.
  LDAP Injection
LDAP Injection enables an attacker to inject LDAP statements potentially granting permission to run unauthorized queries, or modify content inside the LDAP tree.
  Header Injection
  Other Vulnerability
This category comprises other attack vectors such as manipulating the PHP runtime, loading custom extensions, freezing the runtime, or similar.
  Regex Injection
Regex Injection enables an attacker to execute arbitrary code in your PHP process.
  XML Injection
XML Injection enables an attacker to read files on your local filesystem including configuration files, or can be abused to freeze your web-server process.
  Variable Injection
Variable Injection enables an attacker to overwrite program variables with custom data, and can lead to further vulnerabilities.
Unfortunately, the security analysis is currently not available for your project. If you are a non-commercial open-source project, please contact support to gain access.

modules/Administration/UpgradeWizard.php (5 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
if(!defined('sugarEntry') || !sugarEntry) die('Not A Valid Entry Point');
3
/*********************************************************************************
4
 * SugarCRM Community Edition is a customer relationship management program developed by
5
 * SugarCRM, Inc. Copyright (C) 2004-2013 SugarCRM Inc.
6
7
 * SuiteCRM is an extension to SugarCRM Community Edition developed by Salesagility Ltd.
8
 * Copyright (C) 2011 - 2014 Salesagility Ltd.
9
 *
10
 * This program is free software; you can redistribute it and/or modify it under
11
 * the terms of the GNU Affero General Public License version 3 as published by the
12
 * Free Software Foundation with the addition of the following permission added
13
 * to Section 15 as permitted in Section 7(a): FOR ANY PART OF THE COVERED WORK
14
 * IN WHICH THE COPYRIGHT IS OWNED BY SUGARCRM, SUGARCRM DISCLAIMS THE WARRANTY
15
 * OF NON INFRINGEMENT OF THIRD PARTY RIGHTS.
16
 * 
17
 * This program is distributed in the hope that it will be useful, but WITHOUT
18
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
19
 * FOR A PARTICULAR PURPOSE.  See the GNU Affero General Public License for more
20
 * details.
21
 * 
22
 * You should have received a copy of the GNU Affero General Public License along with
23
 * this program; if not, see http://www.gnu.org/licenses or write to the Free
24
 * Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
25
 * 02110-1301 USA.
26
 * 
27
 * You can contact SugarCRM, Inc. headquarters at 10050 North Wolfe Road,
28
 * SW2-130, Cupertino, CA 95014, USA. or at email address [email protected].
29
 * 
30
 * The interactive user interfaces in modified source and object code versions
31
 * of this program must display Appropriate Legal Notices, as required under
32
 * Section 5 of the GNU Affero General Public License version 3.
33
 * 
34
 * In accordance with Section 7(b) of the GNU Affero General Public License version 3,
35
 * these Appropriate Legal Notices must retain the display of the "Powered by
36
 * SugarCRM" logo and "Supercharged by SuiteCRM" logo. If the display of the logos is not
37
 * reasonably feasible for  technical reasons, the Appropriate Legal Notices must
38
 * display the words  "Powered by SugarCRM" and "Supercharged by SuiteCRM".
39
 ********************************************************************************/
40
41
42
require_once('modules/Administration/UpgradeWizardCommon.php');
43
require_once('ModuleInstall/PackageManager/PackageManagerDisplay.php');
44
require_once('ModuleInstall/ModuleScanner.php');
45
global $mod_strings;
46
$uh = new UpgradeHistory();
47
48
function unlinkTempFiles() {
0 ignored issues
show
The function unlinkTempFiles() has been defined more than once; this definition is ignored, only the first definition in install/install_utils.php (L1764-1778) is considered.

This check looks for functions that have already been defined in other files.

Some Codebases, like WordPress, make a practice of defining functions multiple times. This may lead to problems with the detection of function parameters and types. If you really need to do this, you can mark the duplicate definition with the @ignore annotation.

/**
 * @ignore
 */
function getUser() {

}

function getUser($id, $realm) {

}

See also the PhpDoc documentation for @ignore.

Loading history...
49
	global $sugar_config;
50
	@unlink($_FILES['upgrade_zip']['tmp_name']);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
51
	@unlink("upload://".$_FILES['upgrade_zip']['name']);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
52
}
53
54
$base_upgrade_dir       = "upload://upgrades";
55
$base_tmp_upgrade_dir   = sugar_cached('upgrades/temp');
56
57
// make sure dirs exist
58
foreach( $GLOBALS['subdirs'] as $subdir ){
59
    if(!file_exists("$base_upgrade_dir/$subdir")) {
60
        sugar_mkdir("$base_upgrade_dir/$subdir", 0770, true);
61
    }
62
}
63
64
// get labels and text that are specific to either Module Loader or Upgrade Wizard
65
if( $view == "module") {
66
	$uploaddLabel = $mod_strings['LBL_UW_UPLOAD_MODULE'];
67
	$descItemsQueued = $mod_strings['LBL_UW_DESC_MODULES_QUEUED'];
68
	$descItemsInstalled = $mod_strings['LBL_UW_DESC_MODULES_INSTALLED'];
69
}
70
else {
71
72
	$uploaddLabel = $mod_strings['LBL_UPLOAD_UPGRADE'];
73
	$descItemsQueued = $mod_strings['DESC_FILES_QUEUED'];
74
	$descItemsInstalled = $mod_strings['DESC_FILES_INSTALLED'];
75
}
76
77
//
78
// check that the upload limit is set to 6M or greater
79
//
80
81
define('SUGARCRM_MIN_UPLOAD_MAX_FILESIZE_BYTES', 6 * 1024 * 1024);  // 6 Megabytes
82
83
$upload_max_filesize = ini_get('upload_max_filesize');
84
$upload_max_filesize_bytes = return_bytes($upload_max_filesize);
85
if($upload_max_filesize_bytes < constant('SUGARCRM_MIN_UPLOAD_MAX_FILESIZE_BYTES'))
86
{
87
	$GLOBALS['log']->debug("detected upload_max_filesize: $upload_max_filesize");
88
	print('<p class="error">' . $mod_strings['MSG_INCREASE_UPLOAD_MAX_FILESIZE'] . ' '
89
		. get_cfg_var('cfg_file_path') . "</p>\n");
90
}
91
92
//
93
// process "run" commands
94
//
95
96
if( isset( $_REQUEST['run'] ) && ($_REQUEST['run'] != "") ){
97
    $run = $_REQUEST['run'];
98
99
    if( $run == "upload" ){
100
        $perform = false;
101
        if(isset($_REQUEST['release_id']) && $_REQUEST['release_id'] != ""){
102
            require_once('ModuleInstall/PackageManager.php');
103
            $pm = new PackageManager();
104
            $tempFile = $pm->download('','',$_REQUEST['release_id']);
105
            $perform = true;
106
            $base_filename = urldecode($tempFile);
107
        } elseif(!empty($_REQUEST['load_module_from_dir'])) {
108
        	//copy file to proper location then call performSetup
109
        	copy($_REQUEST['load_module_from_dir'].'/'.$_REQUEST['upgrade_zip_escaped'], "upload://".$_REQUEST['upgrade_zip_escaped']);
110
111
        	$perform = true;
112
            $base_filename = urldecode( $_REQUEST['upgrade_zip_escaped'] );
113
        } else {
114
            if( empty( $_FILES['upgrade_zip']['tmp_name'] ) ){
115
                echo $mod_strings['ERR_UW_NO_UPLOAD_FILE'];
116
            } else{
117
                $upload = new UploadFile('upgrade_zip');
118
                if(!$upload->confirm_upload() ||
119
                    strtolower(pathinfo($upload->get_stored_file_name(), PATHINFO_EXTENSION)) != 'zip' ||
120
                    !$upload->final_move($upload->get_stored_file_name())
121
                    ) {
122
    			    unlinkTempFiles();
123
                    sugar_die("Invalid Package");
124
            	} else {
125
    			     $tempFile = "upload://".$upload->get_stored_file_name();
126
                     $perform = true;
127
                     $base_filename = urldecode( $_REQUEST['upgrade_zip_escaped'] );
128
    		    }
129
            }
130
        }
131
        if($perform) {
132
            $manifest_file = extractManifest( $tempFile );
0 ignored issues
show
The call to extractManifest() misses a required argument $base_tmp_upgrade_dir.

This check looks for function calls that miss required arguments.

Loading history...
133
			if(is_file($manifest_file))
134
			{
135
    			//SCAN THE MANIFEST FILE TO MAKE SURE NO COPIES OR ANYTHING ARE HAPPENING IN IT
136
	    		$ms = new ModuleScanner();
137
	    		$ms->lockConfig();
138
		    	$fileIssues = $ms->scanFile($manifest_file);
139
    			if(!empty($fileIssues)){
140
    				echo '<h2>' . $mod_strings['ML_MANIFEST_ISSUE'] . '</h2><br>';
141
    				$ms->displayIssues();
142
    				die();
143
    			}
144
    			list($manifest, $installdefs) = MSLoadManifest($manifest_file);
145
    			if($ms->checkConfig($manifest_file)) {
146
    				echo '<h2>' . $mod_strings['ML_MANIFEST_ISSUE'] . '</h2><br>';
147
    				$ms->displayIssues();
148
    				die();
149
    			}
150
    			validate_manifest( $manifest );
151
152
			    $upgrade_zip_type = $manifest['type'];
153
154
    			// exclude the bad permutations
155
    			if( $view == "module" )	{
156
    				if ($upgrade_zip_type != "module" && $upgrade_zip_type != "theme" && $upgrade_zip_type != "langpack") {
157
    					unlinkTempFiles();
158
    					 die($mod_strings['ERR_UW_NOT_ACCEPTIBLE_TYPE']);
159
    				}
160
    			} elseif( $view == "default" ) {
161
    				if($upgrade_zip_type != "patch" ) {
162
    					unlinkTempFiles();
163
    					die($mod_strings['ERR_UW_ONLY_PATCHES']);
164
    				}
165
    			}
166
167
    			$base_filename = pathinfo($tempFile, PATHINFO_BASENAME);
168
169
    			mkdir_recursive( "$base_upgrade_dir/$upgrade_zip_type" );
170
	    		$target_path = "$base_upgrade_dir/$upgrade_zip_type/$base_filename";
171
			    $target_manifest = remove_file_extension( $target_path ) . "-manifest.php";
172
173
    			if( isset($manifest['icon']) && $manifest['icon'] != "" ){
174
	    			 $icon_location = extractFile( $tempFile ,$manifest['icon'] );
0 ignored issues
show
The call to extractFile() misses a required argument $base_tmp_upgrade_dir.

This check looks for function calls that miss required arguments.

Loading history...
175
    				 copy($icon_location, remove_file_extension( $target_path )."-icon.".pathinfo($icon_location, PATHINFO_EXTENSION));
176
	    		}
177
178
				if(rename( $tempFile , $target_path )) {
179
					 copy( $manifest_file, $target_manifest );
180
					$GLOBALS['ML_STATUS_MESSAGE'] = $base_filename.$mod_strings['LBL_UW_UPLOAD_SUCCESS'];
181
                } else{
182
					 $GLOBALS['ML_STATUS_MESSAGE'] = $mod_strings['ERR_UW_UPLOAD_ERROR'];
183
				}
184
			} else {
185
				unlinkTempFiles();
186
				die($mod_strings['ERR_UW_NO_MANIFEST']);
187
			}
188
        }
189
    } else if( $run == $mod_strings['LBL_UW_BTN_DELETE_PACKAGE'] ){
190
        if(!empty ($_REQUEST['install_file']) ){
191
            die($mod_strings['ERR_UW_NO_UPLOAD_FILE']);
192
        }
193
194
        $delete_me = hashToFile($delete_me);
195
196
        $checkFile = strtolower($delete_me);
197
198
        if(substr($delete_me, -4) != ".zip" || substr($delete_me, 0, 9) != "upload://" ||
199
        strpos($checkFile, "..") !== false || !file_exists($checkFile)) {
200
            die("<span class='error'>File is not a zipped archive.</span>");
201
        }
202
		if(unlink($delete_me)) { // successful deletion?
203
			echo "Package $delete_me has been removed.<br>";
204
		} else {
205
			die("Problem removing package $delete_me.");
206
		}
207
    }
208
}
209
210
if( $view == "module") {
211
	print( getClassicModuleTitle($mod_strings['LBL_MODULE_NAME'], array($mod_strings['LBL_MODULE_LOADER_TITLE']), false) );
212
}
213
else {
214
	print( getClassicModuleTitle($mod_strings['LBL_MODULE_NAME'], array($mod_strings['LBL_MODULE_NAME'],$mod_strings['LBL_UPGRADE_WIZARD_TITLE']), false) );
215
}
216
217
// upload link
218
if(!empty($GLOBALS['sugar_config']['use_common_ml_dir']) && $GLOBALS['sugar_config']['use_common_ml_dir'] && !empty($GLOBALS['sugar_config']['common_ml_dir'])){
219
	//rrs
220
	$form = '<form name="move_form" action="index.php?module=Administration&view=module&action=UpgradeWizard" method="post"  ><input type=hidden name="run" value="upload" /><input type=hidden name="load_module_from_dir" id="load_module_from_dir" value="'.$GLOBALS['sugar_config']['common_ml_dir'].'" /><input type=hidden name="upgrade_zip_escaped" value="" />';
221
	$form .= '<br>'.$mod_strings['LBL_MODULE_UPLOAD_DISABLE_HELP_TEXT'].'</br>';
222
	$form .='<table width="100%" class="edit view"><tr><th align="left">'.$mod_strings['LBL_ML_NAME'].'</th><th align="left">'.$mod_strings['LBL_ML_ACTION'].'</th></tr>';
223
	if ($handle = opendir($GLOBALS['sugar_config']['common_ml_dir'])) {
224
		while (false !== ($filename = readdir($handle))) {
225
	        if($filename == '.' || $filename == '..' || !preg_match("#.*\.zip\$#", $filename)) {
226
                continue;
227
            }
228
	        $form .= '<tr><td>'.$filename.'</td><td><input type=button class="button" value="'.$mod_strings['LBL_UW_BTN_UPLOAD'].'" onClick="document.move_form.upgrade_zip_escaped.value = escape( \''.$filename.'\');document.move_form.submit();" /></td></tr>';
229
	    }
230
	}
231
	$form .= '</table></form>';
232
//rrs
233
234
}else{
235
    $form =<<<eoq
236
<form name="the_form" enctype="multipart/form-data" action="{$form_action}" method="post"  >
237
<table width="100%" border="0" cellspacing="0" cellpadding="0" class="edit view">
238
<tr><td>
239
<table width="450" border="0" cellspacing="0" cellpadding="0">
240
<tr><td style="white-space:nowrap; padding-right: 10px !important;">
241
{$uploaddLabel}
242
<input type="file" name="upgrade_zip" size="40" />
243
</td>
244
<td>
245
<input type=button class="button" value="{$mod_strings['LBL_UW_BTN_UPLOAD']}" onClick="document.the_form.upgrade_zip_escaped.value = escape( document.the_form.upgrade_zip.value );document.the_form.submit();" />
246
<input type=hidden name="run" value="upload" />
247
<input type=hidden name="upgrade_zip_escaped" value="" />
248
</td>
249
</tr>
250
</table></td></tr></table>
251
</form>
252
eoq;
253
}
254
255
$hidden_fields = "<input type=hidden name=\"run\" value=\"upload\" />";
256
$hidden_fields .= "<input type=hidden name=\"mode\"/>";
257
258
$form2 = PackageManagerDisplay::buildPackageDisplay($form, $hidden_fields, $form_action, array('module'));
259
$form3 =<<<eoq3
260
261
262
eoq3;
263
264
echo $form2.$form3;
265
266
// scan for new files (that are not installed)
267
/*print( "$descItemsQueued<br>\n");
268
print( "<ul>\n" );
269
$upgrade_contents = findAllFiles( "$base_upgrade_dir", array() );
270
$upgrades_available = 0;
271
272
print( "<table>\n" );
273
print( "<tr><th></th><th align=left>{$mod_strings['LBL_ML_NAME']}</th><th>{$mod_strings['LBL_ML_TYPE']}</th><th>{$mod_strings['LBL_ML_VERSION']}</th><th>{$mod_strings['LBL_ML_PUBLISHED']}</th><th>{$mod_strings['LBL_ML_UNINSTALLABLE']}</th><th>{$mod_strings['LBL_ML_DESCRIPTION']}</th></tr>\n" );
274
foreach($upgrade_contents as $upgrade_content)
275
{
276
	if(!preg_match("#.*\.zip\$#", $upgrade_content))
277
	{
278
		continue;
279
	}
280
281
	$upgrade_content = clean_path($upgrade_content);
282
	$the_base = basename($upgrade_content);
283
	$the_md5 = md5_file($upgrade_content);
284
	$md5_matches = $uh->findByMd5($the_md5);
285
286
	if(0 == sizeof($md5_matches))
287
	{
288
		$target_manifest = remove_file_extension( $upgrade_content ) . '-manifest.php';
289
		require_once($target_manifest);
290
291
		$name = empty($manifest['name']) ? $upgrade_content : $manifest['name'];
292
		$version = empty($manifest['version']) ? '' : $manifest['version'];
293
		$published_date = empty($manifest['published_date']) ? '' : $manifest['published_date'];
294
		$icon = '';
295
		$description = empty($manifest['description']) ? 'None' : $manifest['description'];
296
		$uninstallable = empty($manifest['is_uninstallable']) ? 'No' : 'Yes';
297
		$type = getUITextForType( $manifest['type'] );
298
		$manifest_type = $manifest['type'];
299
300
		if($view == 'default' && $manifest_type != 'patch')
301
		{
302
			continue;
303
		}
304
305
		if($view == 'module'
306
			&& $manifest_type != 'module' && $manifest_type != 'theme' && $manifest_type != 'langpack')
307
		{
308
			continue;
309
		}
310
311
		if(empty($manifest['icon']))
312
		{
313
			$icon = getImageForType( $manifest['type'] );
314
		}
315
		else
316
		{
317
			$path_parts = pathinfo( $manifest['icon'] );
318
			$icon = "<!--not_in_theme!--><img src=\"" . remove_file_extension( $upgrade_content ) . "-icon." . $path_parts['extension'] . "\" alt =''>";
319
		}
320
321
		$upgrades_available++;
322
		print( "<tr><td>$icon</td><td>$name</td><td>$type</td><td>$version</td><td>$published_date</td><td>$uninstallable</td><td>$description</td>\n" );
323
324
		$upgrade_content = urlencode($upgrade_content);
325
326
		$form2 =<<<eoq
327
            <form action="{$form_action}_prepare" method="post">
328
            <td><input type=submit name="btn_mode" onclick="this.form.mode.value='Install';this.form.submit();" value="{$mod_strings['LBL_UW_BTN_INSTALL']}" /></td>
329
            <input type=hidden name="install_file" value="{$upgrade_content}" />
330
			<input type=hidden name="mode"/>
331
            </form>
332
333
            <form action="{$form_action}" method="post">
334
            <td><input type=submit name="run" value="{$mod_strings['LBL_UW_BTN_DELETE_PACKAGE']}" /></td>
335
            <input type=hidden name="install_file" value="{$upgrade_content}" />
336
            </form>
337
            </tr>
338
eoq;
339
		echo $form2;
340
    }
341
}
342
print( "</table>\n" );
343
344
if( $upgrades_available == 0 ){
345
    print($mod_strings['LBL_UW_NONE']);
346
}
347
print( "</ul>\n" );
348
349
?>
350
*/
351
352
$GLOBALS['log']->info( "Upgrade Wizard view");
353
?>
354
</td>
355
</tr>
356
</table></td></tr></table>
357