Issues (1751)

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.

lib/includes/loader.web.php (63 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
    /******************************************************************
3
     loader.web.php                                        Muze Ariadne
4
     ------------------------------------------------------------------
5
     Author: Muze ([email protected])
6
     Date: 11 december 2002
7
8
     Copyright 2002 Muze
9
10
     This file is part of Ariadne.
11
12
     Ariadne is free software; you can redistribute it and/or modify
13
     it under the terms of the GNU General Public License as published
14
     by the Free Software Foundation; either version 2 of the License,
15
     or (at your option) any later version.
16
17
     Ariadne is distributed in the hope that it will be useful,
18
     but WITHOUT ANY WARRANTY; without even the implied warranty of
19
     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20
     GNU General Public License for more details.
21
22
     You should have received a copy of the GNU General Public License
23
     along with Ariadne; if not, write to the Free Software
24
     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
25
     02111-1307  USA
26
27
    -------------------------------------------------------------------
28
29
     Description:
30
31
       This is loader that contains all functions for the Ariadne web
32
       interface.
33
34
    ******************************************************************/
35
36
	$ERRMODE="htmljs"; // alternative: "text"/"html"/"js"
37
38
	define('LD_ERR_ACCESS', -1);
39
	define('LD_ERR_SESSION', -2);
40
41
	include_once($store_config['code']."includes/loader.web.auth.php");
42
	include_once($store_config['code']."objects/pobject.phtml");
43
44
	function ldCheckAllowedMethods($method = null) {
45
		global $AR;
46
		if (
47
				is_array($AR->loader->web['AllowedMethods']) && isset($method) &&
48
				!(in_array(strtoupper($method), $AR->loader->web['AllowedMethods']))
49
		) {
50
			header("HTTP/1.1 405 Method Not Allowed");
51
			exit(1);
0 ignored issues
show
Coding Style Compatibility introduced by
The function ldCheckAllowedMethods() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
52
		}
53
	}
54
55
	function debug_print( $text ) {
56
		echo "<b>".$text."</b><br>";
57
		flush();
58
	}
59
60 View Code Duplication
	function error($text) {
0 ignored issues
show
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
The function error() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L48-50) 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...
61
		global $ERRMODE;
62
		switch ($ERRMODE) {
63
			case "html" :
64
				echo "<b><font color='red'>Error: $text</font></b><BR>\n";
65
				break;
66
			case "js" :
67
				echo "\nalert('Error: $text');\n";
68
				break;
69
			case "text" :
70
				echo "\nERROR: $text\n";
71
				break;
72
			case "htmljs" :
73
			default:
74
				echo "// <b><font color='red'>Error: $text</font></b><BR>\n<!--\nalert('Error: $text');\n// -->\n";
75
				break;
76
		}
77
	}
78
79
	function ldRegisterFile($field = "file", &$error) {
0 ignored issues
show
ldRegisterFile uses the super-global variable $_FILES which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
The function ldRegisterFile() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L52-81) 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...
80
	global $ARnls, $store;
81
82
		require_once($store->get_config("code")."modules/mod_mimemagic.php");
83
		$result = Array();
84
		$http_post_file = Array('name' => '', 'type' => '', 'tmp_name' => '', 'error' => '', 'size' => '');
85
		$subfields = explode('[', $field);
86
		$field = array_shift($subfields);
87
		$subfield = false;
88
		foreach ($http_post_file as $key => $value) {
89
			$value = &$_FILES[$field][$key];
90
			foreach ($subfields as $subfield) {
91
				$subfield = substr($subfield, 0, -1);
92
				$value = &$value[$subfield];
93
			}
94
			$http_post_file[$key] = $value;
95
		}
96
		if ($subfield) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $subfield of type false|string is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
97
			$field = $subfield;
98
		}
99
100
		if ($http_post_file['error']) {
101
			switch ($http_post_file['error']) {
102
				case UPLOAD_ERR_INI_SIZE:
103
					$error = $ARnls['ariadne:err:upload_ini_size']; // "The uploaded file exceeds the upload_max_filesize directive in php.ini";
104
					break;
105
				case UPLOAD_ERR_FORM_SIZE:
106
					$error = $ARnls['ariadne:err:upload_form_size']; // The uploaded file exceeds the MAX_FILE_SIZE directive that was specified in the HTML form";
107
					break;
108
				case UPLOAD_ERR_PARTIAL:
109
					$error = $ARnls['ariadne:err:upload_partial']; // "The uploaded file was only partially uploaded";
110
					break;
111
				case UPLOAD_ERR_NO_FILE:
112
					// Note: this is not an error
113
					//$error = $ARnls['ariadne:err:upload_no_file']; // No file was uploaded";
114
					break;
115
				case UPLOAD_ERR_NO_TMP_DIR:
116
					$error = $ARnls['ariadne:err:upload_no_tmp_dir']; // "Missing a temporary folder";
117
					break;
118
				case UPLOAD_ERR_CANT_WRITE:
119
					$error = $ARnls['ariadne:err:upload_cant_write']; // "Failed to write file to disk";
120
					break;
121
				case UPLOAD_ERR_EXTENSION:
122
					$error = $ARnls['ariadne:err:upload_extension']; // "File upload stopped by extension";
123
					break;
124
125
				default:
126
					$error = sprintf($ARnls['ariadne:err:upload_error'], $http_post_file['error']); // "Unknown upload error %s";
127
					break;
128
			}
129
			return $result;
130
		}
131
132
		$file_temp = $http_post_file['tmp_name'];
133
		$file = $http_post_file['name'];
134
		if ($file && is_uploaded_file($file_temp)) {
135
			// new file uploaded -> save it before PHP deletes it
136
			$file_artemp=tempnam($store->get_config("files")."temp","upload");
137
			if (move_uploaded_file($file_temp, $file_artemp)) {
138
				// now make the new values available to wgWizKeepVars()
139
				$result[$field]=$file;
140
				$result[$field."_temp"]=basename($file_artemp);
141
				$result[$field."_size"]=(int)$http_post_file['size'];
142
				$type = get_mime_type($file_artemp);
143
				$ext  = substr($file, strrpos($file, '.'));
144
				if (!$type) {
145
					$type = get_mime_type($file, MIME_EXT);
146
				}
147
				$result[$field."_type"] = get_content_type($type, $ext);
148
			}
149
		}
150
		return $result;
151
	}
152
153
	function ldOnFinish() {
154
	global $ARCurrent, $store;
155
		$error = error_get_last();
156
		if ($error['type'] == 1) { // Fatal error
157
			$context = pobject::getContext();
158
			if ($context['scope'] == 'pinp') {
159
				pobject::pinpErrorHandler($error['type'], $error['message'], $error['file'], $error['line'], null);
160
			}
161
		}
162
		if ($ARCurrent->session) {
163
			$ARCurrent->session->save();
164
		}
165
		if ($store) {
166
			$store->close();
167
		}
168
	}
169
170
	function ldObjectNotFound($requestedpath, $requestedtemplate, $requestedargs = null ) {
0 ignored issues
show
The function ldObjectNotFound() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L157-159) 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...
171
	global $store, $AR, $ARCurrent, $args;
172
		$path=$requestedpath;
173
		if ( !$requestedargs ) {
174
			$requestedargs = $args;
175
		}
176
		if (!$path) {
177
			error("Empty path requested with template: $requestedtemplate");
178
		} else {
179
			$prevPath = null;
180 View Code Duplication
			while ($path !== $prevPath && !$store->exists($path)) {
181
				$prevPath = $path;
182
				$path     = $store->make_path($path, "..");
183
			}
184
			if(count($ARCurrent->arCallStack) == 0) {
185
				$arCallArgs = $requestedargs;
186
			} else {
187
				$arCallArgs = @array_pop($ARCurrent->arCallStack);
188
				@array_push($ARCurrent->arCallStack, $arCallArgs);
189
			}
190
			if ($prevPath==$path) {
191
				error("Database is not initialised, please run <a href=\"".$AR->dir->www."install/install.php\">the installer</a>");
192
			} else {
193
				// make sure the config check has been run:
194
				$ob = current( $store->call('system.get.phtml', array(), $store->get($path) ) );
195
				$ob->loadConfig(); //CheckConfig();
196
197
				$ob->pushContext( array(
198
					"arSuperContext" => Array(),
199
					"arCurrentObject" => $ob,
200
					"scope" => "php",
201
					"arCallFunction" => $requestedtemplate
202
				) );
203
204
				$eventData = new baseObject();
205
				$eventData->arCallPath = $requestedpath;
0 ignored issues
show
The property arCallPath does not seem to exist in baseObject.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
206
				$eventData->arCallFunction = $requestedtemplate;
0 ignored issues
show
The property arCallFunction does not seem to exist in baseObject.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
207
				$eventData->arCallArgs = $arCallArgs;
0 ignored issues
show
The property arCallArgs does not seem to exist in baseObject.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
208
				$eventData = ar_events::fire( 'onnotfound', $eventData );
209
				if ( $eventData ) {
210
					// no results: page couldn't be found, show user definable 404 message
211
					$arCallArgs = (array) $eventData->arCallArgs;
212
					$requestedargs = $arCallArgs;
213
					$myarCallArgs = array_merge($arCallArgs,
214
						Array(	"arRequestedPath" => $requestedpath,
215
						 		"arRequestedTemplate" => $requestedtemplate,
216
								"arRequestedArgs" => $requestedargs
217
						)
218
					);
219
					$store->call("user.notfound.html",$myarCallArgs,
220
						 $store->get($path));
221
				}
222
223
				$ob->popContext();
224
			}
225
		}
226
	}
227
228
229
230
231 View Code Duplication
	function ldSetRoot($session='', $nls='') {
0 ignored issues
show
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
The function ldSetRoot() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L90-92) 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...
232
	global $store, $AR, $ARCurrent, $root, $rootoptions;
233
234
		$root=$AR->root;
235
		$rootoptions="";
236
		if ($session && !$AR->hideSessionIDfromURL) {
237
			$rootoptions.="/-".$session."-";
238
			$ARCurrent->session->id=$session;
239
		}
240
		if ($nls) {
241
			$rootoptions.="/$nls";
242
			$ARCurrent->nls=$nls;
243
		}
244
		$root.=$rootoptions;
245
		if ($store) { // loader.php uses this function before the store is initialized.
246
			$store->root=$root;
247
			$store->rootoptions=$rootoptions;
248
		}
249
	}
250
251
	function ldSetNls($nls) {
0 ignored issues
show
The function ldSetNls() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L94-96) 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...
252
	global $ARCurrent, $ARnls;
253
254
		$session=$ARCurrent->session->id;
255
		ldSetRoot($session, $nls);
256
257
		if( is_object( $ARnls ) ) {
258
			$ARnls->setLanguage($nls);
259
		}
260
	}
261
262
	function ldGetRequestedHost() {
0 ignored issues
show
ldGetRequestedHost uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
The function ldGetRequestedHost() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L110-112) 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...
263
	global $AR;
264
		$requestedHost = $_SERVER['HTTP_X_FORWARDED_HOST'];
265
		if (!$requestedHost) {
266
			$requestedHost = $_SERVER['HTTP_HOST'];
267
		}
268
		$protocol = 'http://';
269
		if ($_SERVER['HTTPS']=='on') {
270
			$protocol = 'https://';
271
		}
272
		return $protocol . $requestedHost;
273
	}
274
275
	function ldSetSession($session='') {
0 ignored issues
show
ldSetSession uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
The function ldSetSession() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L98-100) 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...
276
		global $AR, $ARCurrent;
277
		$nls=$ARCurrent->nls;
278
		if ($AR->hideSessionIDfromURL) {
279
			$cookies = (array) ldGetCredentials();
280
			$https = ($_SERVER['HTTPS']=='on');
281
			if( !isset($cookies[$ARCurrent->session->id])  && $ARCurrent->session->id !== 0) {
282
				$data = array();
283
				$data['timestamp']=time();
284
				$cookie=ldEncodeCookie($data);
285
				$cookiename = "ARSessionCookie[".$ARCurrent->session->id."]";
286
				debug("setting cookie (".$ARCurrent->session->id.")(".$cookie.")");
287
				header('P3P: CP="NOI CUR OUR"');
288
				setcookie('ARCurrentSession', $ARCurrent->session->id, 0, '/', false, $https, true);
289
				setcookie($cookiename,$cookie, 0, '/', false, $https, true);
290
			}
291
		}
292
		ldSetRoot($session, $nls);
293
	}
294
295 View Code Duplication
	function ldStartSession($sessionid='') {
0 ignored issues
show
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
The function ldStartSession() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L102-104) 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...
296
	global $ARCurrent, $AR, $ariadne;
297
298
		require($ariadne."/configs/sessions.phtml");
299
		$ARCurrent->session=new session($session_config,$sessionid);
0 ignored issues
show
The variable $session_config does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
300
		ldSetSession($ARCurrent->session->id);
301
	}
302
303
	function ldGetCookieSession() {
0 ignored issues
show
ldGetCookieSession uses the super-global variable $_COOKIE which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
304
		return $_COOKIE['ARCurrentSession'];
305
	}
306
307
	function ldSetCache($file, $time, $image, $headers) {
0 ignored issues
show
The function ldSetCache() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L106-108) 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...
308
	global $store;
309
310
		debug("ldSetCache($file, $time, [image], [headers])","object");
311 View Code Duplication
		if ($time==-2) {
312
			$time=0;
313
		} else {
314
			$time=time()+($time*3600);
315
		}
316
		if (!preg_match("/\.\./",$file)) {
317
			if ($image) {
318
				$path=substr($file, 1, strrpos($file, "/")-1);
319 View Code Duplication
				if (!file_exists($store->get_config("files")."cache/".$path)) {
320
					ldMkDir("cache/".$path);
321
					ldMkDir("cacheheaders/".$path);
322
				}
323
324
				$imagetemp   = tempnam($store->get_config("files")."cache/".$path."/","ARCacheImage");
325
				$headertemp  = tempnam($store->get_config("files")."cacheheaders/".$path."/","ARCacheImage");
326
327
				$fileimage   = $store->get_config("files")."cache".$file;
328
				$fileheaders = $store->get_config("files")."cacheheaders".$file;
329
330
				$fpi=@fopen($imagetemp, "wb");
331
				$fph=@fopen($headertemp, "wb");
332
333
				if($fpi && $fph) {
334
					fwrite($fph, $headers);
335
					fclose($fph);
336
					$imagesize = fwrite($fpi, $image);
337
					fclose($fpi);
338
339
					if ( !touch($imagetemp, $time)) {
340
						debug("ldSetCache: ERROR: couldn't touch image","object");
341
					}
342
343
					if (filesize($imagetemp) == $imagesize ) {
344
						rename($headertemp,$fileheaders);
345
						rename($imagetemp,$fileimage);
346
					} else {
347
						@unlink($imagetemp);
348
						@unlink($headertemp);
349
					}
350
				} else {
351
					if($fpi) {
352
						fclose($fpi);
353
						@unlink($imagetemp);
354
					}
355
					if($fph) {
356
						fclose($fph);
357
						@unlink($headertemp);
358
					}
359
				}
360
			}
361
		}
362
	}
363
364
	function ldMkDir($dir) {
0 ignored issues
show
The function ldMkDir() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.soap.php (L205-217) 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...
365
	global $store;
366
367
		debug("ldMkDir($dir)","object");
368
		$curr=$store->get_config("files");
369
		@mkdir($curr.'/'.$dir, 0755, true);
370
	}
371
372 View Code Duplication
	function ldGetUserCookie($cookiename="ARUserCookie") {
0 ignored issues
show
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
ldGetUserCookie uses the super-global variable $_COOKIE which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
The function ldGetUserCookie() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L114-117) 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...
373
		$cookie = false;
374
375
		if( $_COOKIE[$cookiename] && !($cookiename == "ARSessionCookie") && !($cookiename == 'ARCurrentSession') ) {
376
			$ARUserCookie = $_COOKIE[$cookiename];
377
			debug("ldGetUserCookie() = $ARUserCookie","object");
378
			$cookie = json_decode($ARUserCookie,true);
379
			if ($cookie === null) {
380
				$cookie = unserialize($ARUserCookie);
381
			}
382
		}
383
		return $cookie;
384
	}
385
386
	function ldSetConsentedCookie($cookie, $cookiename="ARUserCookie", $expire=0, $path="/", $domain="", $secure=0) {
387
		// Sets a cookie, but only when ARCookieConsent has been given.
388
		return ldSetUserCookie($cookie, $cookiename, $expire, $path, $domain, $secure, true);
0 ignored issues
show
The call to ldSetUserCookie() has too many arguments starting with true.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
389
	}
390
391
	function ldSetUserCookie($cookie, $cookiename="ARUserCookie", $expire=0, $path="/", $domain="", $secure=0, $consentneeded=false) {
0 ignored issues
show
The function ldSetUserCookie() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L119-122) 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...
392
		$result = false;
393
394
		if (substr($cookiename, 0, strlen('ARSessionCookie'))=='ARSessionCookie' || $cookiename=='ARCurrentSession' ) {
395
			return false;
396
		}
397
398
		$cookieconsent = ldGetUserCookie("ARCookieConsent");
399
		if (!$consentneeded || ($cookieconsent == true)) { // Only set cookies when consent has been given, or no consent is needed for this cookie.
400 View Code Duplication
			if( $cookiename != "ARSessionCookie" && $cookiename != "ARCurrentSession" ) {
401
				$ARUserCookie=json_encode($cookie);
402
				debug("ldSetUserCookie(".$ARUserCookie.")","object");
403
				header('P3P: CP="NOI CUR OUR"');
404
				$result = setcookie($cookiename,$ARUserCookie, $expire, $path, $domain, $secure);
405
			}
406
		} else {
407
			debug("ldSetUserCookie: no consent. (".$ARUserCookie.")","object");
0 ignored issues
show
The variable $ARUserCookie seems only to be defined at a later point. Did you maybe move this code here without moving the variable definition?

This error can happen if you refactor code and forget to move the variable initialization.

Let’s take a look at a simple example:

function someFunction() {
    $x = 5;
    echo $x;
}

The above code is perfectly fine. Now imagine that we re-order the statements:

function someFunction() {
    echo $x;
    $x = 5;
}

In that case, $x would be read before it is initialized. This was a very basic example, however the principle is the same for the found issue.

Loading history...
408
		}
409
		return $result;
410
	}
411
412
	function ldRedirect($uri) {
0 ignored issues
show
The function ldRedirect() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L133-134) 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...
413
		return ldHeader("Location: $uri");
414
	}
415
416
	function ldHeader($header,$replace=true) {
0 ignored issues
show
The function ldHeader() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L136-137) 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...
417
	global $ARCurrent;
418
		$result=false;
419
		if ( !Headers_sent() && !$ARCurrent->arNoHeaders ) {
420
			$result=true;
421
			list($key,$value) = explode(':',$header,2);
0 ignored issues
show
The assignment to $value is unused. Consider omitting it like so list($first,,$third).

This checks looks for assignemnts to variables using the list(...) function, where not all assigned variables are subsequently used.

Consider the following code example.

<?php

function returnThreeValues() {
    return array('a', 'b', 'c');
}

list($a, $b, $c) = returnThreeValues();

print $a . " - " . $c;

Only the variables $a and $c are used. There was no need to assign $b.

Instead, the list call could have been.

list($a,, $c) = returnThreeValues();
Loading history...
422
			Header($header,$replace);
423 View Code Duplication
			if($replace){
424
				$ARCurrent->ldHeaders[strtolower($key)]=$header;
425
			} else {
426
				$ARCurrent->ldHeaders[strtolower($key)].=$header;
427
			}
428
		}
429
		return $result;
430
	}
431
432
	function ldSetBrowserCache( $settings ) {
433
		if ($settings === false) {
434
			return ldHeader("Cache-control: no-store, no-cache, must-revalidate, max-age=0, private");
435
		}
436
		$cacheControl = "Cache-control: ";
437
		$cacheControl .= ($settings['browserCachePrivate'] ? "private" : "public");
438
		$cacheControl .= ($settings['browserCacheNoStore'] ? ", no-store" : "");
439
		$cacheControl .= ($settings['browserCacheNoCache'] ? ", no-cache" : "");
440
		$cacheControl .= ($settings['browserCacheMustRevalidate'] ? ", must-revalidate" : "");
441
		$cacheControl .= ($settings['browserCacheProxyRevalidate'] ? ", proxy-revalidate" : "");
442
		$cacheControl .= ($settings['browserCacheNoTransform'] ? ", no-transform" : "");
443
		$cacheControl .= ($settings['browserCacheMaxAge'] ? ", max-age=" . $settings['browserCacheMaxAge'] : ", max-age=0");
444
		$cacheControl .= ($settings['browserCacheSMaxAge'] ? ", s-max-age=" . $settings['browserCacheMaxAge'] : "");
445
446
		ldHeader($cacheControl);
447
	}
448
449
	function ldSetClientCache( $cache_on, $expires = null, $modified = null ) {
0 ignored issues
show
The parameter $modified is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
The function ldSetClientCache() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L139-141) 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...
450
		$now = time();
451
		if ($cache_on) {
452
			if ( !isset($expires) ) {
453
				$expires = $now + 1800;
454
			}
455
456
			// Give the client the max-age
457
			$maxage = $expires - $now;
458
			ldHeader("Cache-control: public, max-age=$maxage, must-revalidate");
459
			ldHeader("X-Ariadne-Expires: $expires");
460
		} else {
461
			ldHeader("Cache-control: no-store, no-cache, must-revalidate, max-age=0, private");
462
		}
463
		return $result;
0 ignored issues
show
The variable $result does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
464
	}
465
466 View Code Duplication
	function ldSetContent($mimetype, $size=0) {
0 ignored issues
show
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
The function ldSetContent() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L143-145) 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...
467
		global $ARCurrent;
468
		$result=ldHeader("Content-Type: ".$mimetype);
469
		$ARCurrent->arContentTypeSent = true;
470
		if ($size) {
471
			$result=ldHeader("Content-Length: ".$size);
472
		}
473
		return $result;
474
	}
475
476
	function ldGetServerVar($server_var = "") {
0 ignored issues
show
ldGetServerVar uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
The function ldGetServerVar() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L147-150) 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...
477
		if (!$server_var) {
478
			return $_SERVER;
479
		}
480
		return $_SERVER[$server_var];
481
	}
482
483 View Code Duplication
	function ldGetClientVar($client_var) {
0 ignored issues
show
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
The function ldGetClientVar() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L152-155) 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...
484
		// not all environment variables should be disclosed
485
		switch($client_var) {
486
			case "REMOTE_ADDR": $result = getenv("REMOTE_ADDR"); break;
487
			case "HTTP_USER_AGENT": $result = getenv("HTTP_USER_AGENT"); break;
488
			case "HTTP_ACCEPT": $result = getenv("HTTP_ACCEPT"); break;
489
			case "HTTP_ACCEPT_LANGUAGE": $result = getenv("HTTP_ACCEPT_LANGUAGE"); break;
490
			default: $result = false; break;
491
		}
492
		return $result;
493
	}
494
495
	function ldDisablePostProcessing() {
0 ignored issues
show
The function ldDisablePostProcessing() has been defined more than once; this definition is ignored, only the first definition in lib/includes/loader.cmd.php (L181-184) 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...
496
		global $ARCurrent,$ldXSSProtectionActive,$ldOutputBufferActive;
497
498
		// only disable the cache when we don't have xss protection active
499
		if($ldXSSProtectionActive !== true  && $ldOutputBufferActive === true) {
500
			/*
501
				kill the innermost output buffer, if there is any other buffering layers active
502
				in the end this will remove the outputbuffer used in the loader
503
			*/
504
505
			ob_end_flush();
506
507
			// because we are forceing the output, we can't cache it anymore, disable it for safety sake
508
			$ARCurrent->arDontCache = true;
509
			$ldOutputBufferActive=false;
510
			return true;
511
		} else if ($ldXSSProtectionActive === true) {
512
			return false;
513
		} else if ($ldOutputBufferActive === false) {
514
			return 2;
515
		}
516
	}
517
518
	function ldProcessCacheControl() {
0 ignored issues
show
ldProcessCacheControl uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
519
		global $ARCurrent;
520
		if (isset($_SERVER["HTTP_CACHE_CONTROL"])) {
521
			$cc = $_SERVER["HTTP_CACHE_CONTROL"];
522
			$parts = explode(',', $cc);
523
			foreach($parts as $part) {
524
				$part = trim ($part);
525
				list($key,$value) = explode('=', $part,2);
526
				$key = trim($key);
527
				switch($key) {
528
					case "no-cache":
529
					case "no-store":
530
					case "no-transform":
531
					case "only-if-cached":
532
						$ARCurrent->RequestCacheControl[$key] = true;
533
						break;
534
					case "max-age":
535
					case "max-stale":
536
					case "min-fresh":
537
						$value = (int)filter_var($value,FILTER_SANITIZE_NUMBER_INT);
538
						$ARCurrent->RequestCacheControl[$key] = $value;
539
						break;
540
					default:
541
						// do nothing
542
						break;
543
				}
544
			}
545
		}
546
	}
547
548
	function ldGatherXSSInput(&$xss, $input) {
549
		if (is_array($input)) {
550
			foreach ($input as $value) {
551
				ldGatherXSSInput($xss, $value);
552
			}
553
		} else {
554
			$input = (string)$input;
555
			if (strlen($input) > 10) {
556
				if (preg_match('/[\'"<>]/', $input)) {
557
					$xss[strlen($input)][$input] = $input;
558
				}
559
			}
560
		}
561
	}
562
563
	function ldCheckAllowedTemplate($template) {
564
		// Check if a template is allowed to be called directly from the URL.
565
		if ($template == "system.list.folders.json.php") {
566
			// FIXME: this template is used to fetch folders in explore - it should be renamed to explore.list.folders.json.php;
567
			return true;
568
		} else if ($template == "system.list.objects.json.php") {
569
			// FIXME: this template is used to fetch objects in explore - it should be renamed to explore.list.objects.json.php;
570
			return true;
571
		} else if (preg_match('/^(system|ftp|webdav|soap)\./', $template)) {
572
			// Disallow all direct calls to system.*, ftp.*, webdav.*, soap.* templates;
573
			// FTP, webdav, soap should use their own loader instead.
574
			return false;
575
		}
576
577
		return true;
578
	}
579
580
	function ldCacheRequest($AR_PATH_INFO=null) {
581
		ob_start();
582
583
		global $ARCurrent;
584
		$ARCurrent->refreshCacheOnShutdown = true;
585
		ldProcessRequest($AR_PATH_INFO);
586
		ob_end_clean();
587
	}
588
589
	function ldProcessRequest($AR_PATH_INFO=null) {
0 ignored issues
show
ldProcessRequest uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
ldProcessRequest uses the super-global variable $_GET which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
ldProcessRequest uses the super-global variable $_POST which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
ldProcessRequest uses the super-global variable $_FILES which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
590
		global $AR;
591
		global $ARCurrent;
592
		global $store_config;
593
		global $auth_config;
594
		global $cache_config;
595
		global $store;
596
		global $context;
597
		global $DB;
598
		global $path;
599
		global $function;
600
		global $nls;
601
602
		$writecache = false;
603
604
		// go check for a sessionid
605
		$root=$AR->root;
606
		$session_id=0;
607
		$re="^/-(.{4})-/";
608
609
		$originalPathInfo = $AR_PATH_INFO; // Store this to pass to the refresh cache on shutdown function;
610
611
		if (preg_match( '|'.$re.'|' , $AR_PATH_INFO , $matches )) {
612
			$session_id=$matches[1];
613
			$AR_PATH_INFO=substr($AR_PATH_INFO,strlen($matches[0])-1);
614
			$AR->hideSessionIDfromURL=false;
615
		} elseif ($AR->hideSessionIDfromURL) {
616
			$cookies = (array) ldGetCredentials();
617
			$current = ldGetCookieSession();
618
			if ( array_key_exists( $current, $cookies ) ) {
619
				$session_id = $current;
620
			}
621
		} elseif (isset($_SERVER['PHP_AUTH_USER'])) {
622
			$cookies = (array) ldGetCredentials();
623
			$current = ldGetCookieSession();
624
			if ( array_key_exists( $current, $cookies ) ) {
625
				$session_id = $current;
626
			}
627
		}
628
629
		// set the default user (public)
630
		$AR->login="public";
631
632
633
		// look for the template
634
		$split=strrpos($AR_PATH_INFO, "/");
635
		$path=substr($AR_PATH_INFO,0,$split+1);
636
		$function=substr($AR_PATH_INFO,$split+1);
637
		if (!$function ) {
638
			if (!isset($arDefaultFunction) || $arDefaultFunction == '' ) {
0 ignored issues
show
The variable $arDefaultFunction seems only to be defined at a later point. As such the call to isset() seems to always evaluate to false.

This check marks calls to isset(...) or empty(...) that are found before the variable itself is defined. These will always have the same result.

This is likely the result of code being shifted around. Consider removing these calls.

Loading history...
639
				$arDefaultFunction="view.html";
640
			}
641
			$function=$arDefaultFunction;
642
			if (isset($arFunctionPrefix) && $arFunctionPrefix != '' ) {
0 ignored issues
show
The variable $arFunctionPrefix does not exist. Did you mean $function?

This check looks for variables that are accessed but have not been defined. It raises an issue if it finds another variable that has a similar name.

The variable may have been renamed without also renaming all references.

Loading history...
643
				$function=$arFunctionPrefix.$function;
644
			}
645
			$AR_PATH_INFO.=$function;
646
		}
647
648
		// yes, the extra '=' is needed, don't remove it. trust me.
649
		$ldCacheFilename=strtolower($AR_PATH_INFO)."=";
650
		// for the new multiple domains per site option (per language), we need this
651
		// since the nls isn't literaly in the url anymore.
652
		$ldCacheFilename.=str_replace(':','=',str_replace('/','',$AR->host)).'=';
653
654
		$qs = ldGetServerVar("QUERY_STRING");
655
		if ($qs != '') {
656
			$ldCacheFilename.=sha1($qs);
657
		}
658
659
		if ( $session_id ) {
660
			$cachedimage=$store_config["files"]."cache/session".$ldCacheFilename;
661
			$cachedheader=$store_config["files"]."cacheheaders/session".$ldCacheFilename;
662
		} else {
663
			$cachedimage=$store_config["files"]."cache/normal".$ldCacheFilename;
664
			$cachedheader=$store_config["files"]."cacheheaders/normal".$ldCacheFilename;
665
		}
666
667
		if ($AR->ESI) {
668
			ob_start();
669
		}
670
671
		$timecheck=time();
672
673
		if (file_exists($cachedimage)) {
674
			$staleTotalTime = filemtime($cachedimage) - filectime($cachedimage);
675
			$staleCurrent = $timecheck - filectime($cachedimage);
676
			if( $staleTotalTime != 0) {
677
				$stalePercentage = sprintf("%.2f", 100 * $staleCurrent / $staleTotalTime);
678
			} else {
679
				$stalePercentage = 100;
680
			}
681
			if ($stalePercentage < 0) {
682
				$stalePercentage = 0;
683
			} else if ($stalePercentage > 100) {
684
				$stalePercentage = 100;
685
			}
686
			if (!headers_sent()) {
687
				header("X-Ariadne-Cache-Stale: $stalePercentage%");
688
			}
689
		}
690
691
		// add min-fresh if the client asked for it
692
		if (isset($ARCurrent->RequestCacheControl["min-fresh"])) {
693
			$timecheck += $ARCurrent->RequestCacheControl["min-fresh"];
694
		}
695
696
		if (
697
			file_exists($cachedimage) &&
698
			((($mtime=@filemtime($cachedimage)) > $timecheck) || ($mtime==0)) &&
699
			($_SERVER["REQUEST_METHOD"]!="POST") &&
700
			($ARCurrent->RequestCacheControl["no-cache"] != true ) &&
701
			($ARCurrent->refreshCacheOnShutdown !== true)
702
		) {
703
			$ctime=filemtime($cachedimage); // FIXME: Waarom moet dit mtime zijn? Zonder mtime werkt de if-modified-since niet;
704
705
			if (rand(20,80) < $stalePercentage) {
0 ignored issues
show
The variable $stalePercentage does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
706
				header("X-Ariadne-Cache-Refresh: refreshing on shutdown");
707
				register_shutdown_function("ldCacheRequest", $originalPathInfo); // Rerun the request with the original path info;
708
			} else {
709
				header("X-Ariadne-Cache-Refresh: skipped, still fresh enough");
710
			}
711
712
			if (!$AR->ESI && $_SERVER['HTTP_IF_MODIFIED_SINCE'] && strtotime($_SERVER['HTTP_IF_MODIFIED_SINCE']) >= $ctime) {
713
				// the mtime is used as expiration time, the ctime is the correct last modification time.
714
				// as an object clears the cache upon a save.
715
716
				// Send the original headers - they will already contain the correct max-age and expires values;
717 View Code Duplication
				if (file_exists($cachedheader)) {
718
					$filedata = file($cachedheader);
719
					if (is_array($filedata)) {
720
						while (list($key, $header)=each($filedata)) {
0 ignored issues
show
The assignment to $key is unused. Consider omitting it like so list($first,,$third).

This checks looks for assignemnts to variables using the list(...) function, where not all assigned variables are subsequently used.

Consider the following code example.

<?php

function returnThreeValues() {
    return array('a', 'b', 'c');
}

list($a, $b, $c) = returnThreeValues();

print $a . " - " . $c;

Only the variables $a and $c are used. There was no need to assign $b.

Instead, the list call could have been.

list($a,, $c) = returnThreeValues();
Loading history...
721
							ldHeader($header);
722
						}
723
					}
724
				}
725
				header("X-Ariadne-Cache: Hit");
726
				ldHeader("HTTP/1.1 304 Not Modified");
727
			} else {
728 View Code Duplication
				if (file_exists($cachedheader)) {
729
					// Cache header file also contains information about Cache-control;
730
					$filedata = file($cachedheader);
731
					if (is_array($filedata)) {
732
						while (list($key, $header)=each($filedata)) {
0 ignored issues
show
The assignment to $key is unused. Consider omitting it like so list($first,,$third).

This checks looks for assignemnts to variables using the list(...) function, where not all assigned variables are subsequently used.

Consider the following code example.

<?php

function returnThreeValues() {
    return array('a', 'b', 'c');
}

list($a, $b, $c) = returnThreeValues();

print $a . " - " . $c;

Only the variables $a and $c are used. There was no need to assign $b.

Instead, the list call could have been.

list($a,, $c) = returnThreeValues();
Loading history...
733
							ldHeader($header);
734
						}
735
					}
736
				}
737
				header("X-Ariadne-Cache: Hit"); // Send this after the cached headers to overwrite the cached cache-miss header;
738
739
				if ($AR->ESI) {
740
					if (false && $_SERVER['HTTP_IF_MODIFIED_SINCE'] && (strtotime($_SERVER['HTTP_IF_MODIFIED_SINCE']) >= $ctime)) {
741
						ldHeader("HTTP/1.1 304 Not modified");
742
					} else {
743
						$data = file_get_contents($cachedimage);
744
						include_once($store_config['code']."modules/mod_esi.php");
745
746
						// Replace the session IDs before the ESI process call to pass the correct session ID information...
747 View Code Duplication
						if ($session_id && !$AR->hideSessionIDfromURL) {
748
							$tag = '{arSessionID}';
749
							$data = str_replace($tag, "-$session_id-", $data);
750
						}
751
752
						$data = ESI::esiProcess($data);
753
754
						// ... and then replace the session IDs that were generated in de ESI case;
755
						$tag = '{arSessionID}';
756
						if ($session_id && !$AR->hideSessionIDfromURL) {
757
							$data = str_replace($tag, "-$session_id-", $data);
758
						} else if ($session_id && $AR->hideSessionIDfromURL ) {
759
							$data = str_replace($tag, '', $data);
760
						}
761
						$data_len = strlen($data);
762
						header("Content-Length: ".$data_len);
763
						echo $data;
764
					}
765
766
				} else if ($session_id) {
767
					$tag = '{arSessionID}';
0 ignored issues
show
$tag is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
768
					$data = file_get_contents($cachedimage);
769
					$tag = '{arSessionID}';
770 View Code Duplication
					if (!$AR->hideSessionIDfromURL) {
771
						$data = str_replace($tag, "-$session_id-", $data);
772
					} else {
773
						$data = str_replace($tag, '', $data);
774
					}
775
					$data_len = strlen($data);
776
					header("Content-Length: ".$data_len);
777
					echo $data;
778
				} else {
779
					$data_len = filesize($cachedimage);
780
					header("Content-Length: ".$data_len);
781
					readfile($cachedimage);
782
				}
783
			}
784
			$writecache = false; // Prevent recaching cached image;
785
		} else {
786
			if (!headers_sent()) {
787
				header("X-Ariadne-Cache: Miss");
788
			}
789
790
			/*
791
				start output buffering
792
			*/
793
			ob_start();
794
			global $ldOutputBufferActive;
795
			$ldOutputBufferActive = true;
796
			ob_implicit_flush(0);
797
798
			// look for the language
799
			$split=strpos(substr($AR_PATH_INFO, 1), "/");
800
			$ARCurrent->nls=substr($path, 1, $split);
801
			if (!isset($AR->nls->list[$ARCurrent->nls]) ) {
802
				// not a valid language
803
				$ARCurrent->nls="";
804
				$nls=$AR->nls->default;
805
				// but we can find out if the user has any preferences
806
				preg_match_all("%([a-zA-Z]{2}|\\*)[a-zA-Z-]*(?:;q=([0-9.]+))?%", $_SERVER["HTTP_ACCEPT_LANGUAGE"], $regs, PREG_SET_ORDER);
807
				$ARCurrent->acceptlang=array();
808
				$otherlangs=array();
809
				$otherq=false;
810 View Code Duplication
				foreach ($regs as $reg) {
0 ignored issues
show
The expression $regs of type null|array<integer,array<integer,string>> is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
811
					if (!isset($reg[2])) {
812
						$reg[2]=1;
813
					}
814
					if ($reg[1]=="*") {
815
						$otherq=$reg[2];
816
					} else if ($AR->nls->list[$reg[1]]) {
817
						$otherlangs[]=$reg[1];
818
						$ARCurrent->acceptlang[$reg[1]]=$reg[2];
819
					}
820
				}
821 View Code Duplication
				if ($otherq !== false) {
822
					$otherlangs=array_diff(array_keys($AR->nls->list), $otherlangs);
823
					foreach ($otherlangs as $lang) {
824
						$ARCurrent->acceptlang[$lang]=$otherq;
825
					}
826
				}
827
				arsort($ARCurrent->acceptlang);
828
			} else {
829
				// valid language
830
				$path=substr($path, $split+1);
831
				// ldSetNls($ARCurrent->nls);
832
				$nls=$ARCurrent->nls;
833
			}
834
835
			$args=array_merge($_GET,$_POST);
836
837
			// instantiate the store
838
			$inst_store = $store_config["dbms"]."store";
839
			$store=new $inst_store($root,$store_config);
840
			//$store->rootoptions = $rootoptions;
841
842
			if ($session_id) {
843
				ldStartSession($session_id);
844
			}
845
846
			// instantiate the ARnls
847
			if( $ARCurrent->nls != "" ) {
848
				ldSetNls($nls);
849
			}
850
851
852
			if (substr($function, -6)==".phtml") {
853
				// system template: no language check
854
				$ARCurrent->nolangcheck=1;
855
			}
856
			$ext = pathinfo($function, PATHINFO_EXTENSION);
857
			switch ( $ext ) {
858
				case 'css':
859
					ldSetContent('text/css; charset=utf-8');
860
				break;
861
				case 'js':
862
					ldSetContent('application/javascript; charset=utf-8');
863
				break;
864
				case 'json':
865
					ldSetContent('application/json; charset=utf-8');
866
				break;
867
				case 'xml':
868
					ldSetContent('text/xml; charset=utf-8');
869
				break;
870
				case 'jpg':
871
					ldSetContent('image/jpeg');
872
				break;
873
				case 'gif':
874
					ldSetContent('image/gif');
875
				break;
876
				case 'png':
877
					ldSetContent('image/png');
878
				break;
879
				case 'svg':
880
					ldSetContent('image/svg+xml');
881
				break;
882
				default:
883
					ldSetContent('text/html; charset=utf-8');
884
				break;
885
			}
886
			$ARCurrent->arContentTypeSent = true;
887
888
			register_shutdown_function("ldOnFinish");
889
890
			$auth_class = "mod_auth_".$auth_config["method"];
891
			$mod_auth = new $auth_class($auth_config);
892
			$username = ( isset($args["ARLogin"]) ? $args["ARLogin"] : null );
893
			$password = ( isset($args["ARPassword"]) ? $args["ARPassword"] : null );
894
			if (!$username && $_SERVER['REQUEST_METHOD'] != "GET") {
895
				debug('logging in with basic auth');
896
				$username = $_SERVER["PHP_AUTH_USER"];
897
				$password = $_SERVER["PHP_AUTH_PW"];
898
			}
899
900
			$result = $mod_auth->checkLogin($username, $password, $path);
901
			if ($result!==true) {
902
				if ($result == LD_ERR_ACCESS) {
903
					ldAccessDenied($path, $ARnls["accessdenied"], $args, $function);
0 ignored issues
show
The variable $ARnls does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
The call to ldAccessDenied() has too many arguments starting with $args.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
904
					$function = false;
905
				} else if ($result == LD_ERR_SESSION && !$AR->hideSessionIDfromURL ) {
906
					ldAccessTimeout($path, $ARnls["sessiontimeout"], $args, $function);
907
					$function = false;
908
				} else if ($result == LD_ERR_EXPIRED) {
909
					ldAccessPasswordExpired($path, $ARnls["sessionpasswordexpired"], $args, $function);
910
					$function = false;
911
				}
912
			}
913
914
			// valid new login, without a session, morph to login.redirect.php to redirect to a session containing url
915
			if( !$session_id && $args["ARLogin"] && $args["ARPassword"] && $function !== false && !$AR->hideSessionIDfromURL ) {
916 View Code Duplication
				if (!$ARCurrent->session->get("oldArCallArgs", 1)) {
917
					$ARCurrent->session->put("oldGET", $_GET, 1);
918
					$ARCurrent->session->put("oldPOST", $_POST, 1);
919
					$ARCurrent->session->put("oldArCallArgs", $args, 1);
920
					$ARCurrent->session->save(0, true);
921
				}
922
				if ($arDefaultFunction !== $function) {
0 ignored issues
show
The variable $arDefaultFunction does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
923
					$args["arRequestedTemplate"] = $function;
924
				} else {
925
					$args["arRequestedTemplate"] = "";
926
				}
927
				$function = "login.redirect.php";
928
			} else if( $session_id ) {
929
				if ($ARCurrent->session->get("ARSessionTimedout", 1)) {
930 View Code Duplication
					if (!$ARCurrent->session->get("oldArCallArgs", 1)) {
931
						$ARCurrent->session->put("oldGET", $_GET, 1);
932
						$ARCurrent->session->put("oldPOST", $_POST, 1);
933
						$ARCurrent->session->put("oldArCallArgs", $args, 1);
934
						$ARCurrent->session->save(0, true);
935
					}
936
				} else {
937
					if ($ARCurrent->session->get("oldArCallArgs", 1)) {
938
						$_GET = array_merge( $_GET, (array)$ARCurrent->session->get("oldGET", 1) );
939
						$_POST = array_merge( $_POST, (array)$ARCurrent->session->get("oldPOST", 1) );
940
						$args = $ARCurrent->session->get("oldArCallArgs", 1);
941
						$args = array_merge( $_GET, $_POST, $args); // $args, $_GET, $_POST );
942
						$ARCurrent->session->put("oldArCallArgs", "", 1);
943
						$ARCurrent->session->put("oldGET", "", 1);
944
						$ARCurrent->session->put("oldPOST", "", 1);
945
					}
946
				}
947
			}
948
949
			$xss_vars = array();
950
			ldGatherXSSInput($xss_vars, $_GET);
951
			ldGatherXSSInput($xss_vars, $_POST);
952
			$filenames = array_map(function ($e) { return $e['name']; }, $_FILES);
953
			ldGatherXSSInput($xss_vars, $filenames);
954
955
			ldGatherXSSInput( $xss_vars, $function );
956
			ldGatherXSSInput( $xss_vars, $path );
957
			global $ldXSSProtectionActive;
958
			if (count($xss_vars)) {
959
				$ldXSSProtectionActive = true;
960
			}
961
962
			if ($function!==false) {
963
				// finally call the requested object
964
				unset($store->total);
965
				if (ldCheckAllowedTemplate($function) ) {
966
					$store->call($function, $args, $store->get($path));
967
					$writecache = true;
968
				}
969
				if (!$store->total) {
970
					ldObjectNotFound($path, $function, $args);
0 ignored issues
show
The call to ldObjectNotFound() has too many arguments starting with $args.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
971
				}
972
			}
973
974
			if (count($xss_vars)) {
975
				$image = ob_get_contents();
976
				ob_clean();
977
978
				$header = $ARCurrent->ldHeaders["content-type"];
979
				$xssDetected = false;
980
				preg_match('/^content-type:\s+([^ ;]+)/i', $header, $matches);
981
				$mimetype = strtolower($matches[1]);
982
				if (substr($mimetype, 0, 5) == 'text/') {
983
					krsort($xss_vars, SORT_NUMERIC);
984
					foreach ($xss_vars as $values) {
985
						if (is_array($values)) {
986
							foreach ($values as $value) {
987
								$occurances = substr_count($image, $value);
988
								if ($occurances > 0 ) {
989
									$xssDetected = true;
990
									break 2;
991
								}
992
							}
993
						}
994
					}
995
				}
996
997
				if ($xssDetected) {
998
					$newargs = array();
999
					$newargs["arRequestedArgs"]     = $args;
1000
					$newargs["arRequestedTemplate"] = $function;
1001
					$newargs["arSuspectedArgs"]     = $xss_vars;
1002
					$newargs["arResultOutput"]      = $image;
1003
					$store->call('user.xss.html', $newargs, $store->get($path));
1004
				} else {
1005
					echo $image;
1006
				}
1007
			}
1008
		}
1009
1010
		// now check for outputbuffering (caching)
1011
		if ($image=ob_get_contents()) {
1012
			// Calculate browser side cache settings based on settings collected in the call chain;
1013
			//
1014
			// Rules: do not cache wins. short cache time wins over longer cache time. Unset values don't get to play.
1015
			//
1016
			// Overlord rule: if the request method was not a get, or debugging was used, do not cache. Ever.
1017
			//
1018
			// If pinp says arDontCache, then do not cache;
1019
			//
1020
			// If ESI was used and hit a cached image, use the cache settings from the cache image;
1021
			if ($_SERVER['REQUEST_METHOD']!='GET' || ($DB["wasUsed"] > 0)) {
1022
				// Do not cache on client.
1023
				ldSetBrowserCache(false);
1024
			} else if (is_array($ARCurrent->cache) && ($file=array_pop($ARCurrent->cache))) {
1025
				// This will generate an error, do not cache on client;
1026
				ldSetBrowserCache(false);
1027
			} else if ($ARCurrent->arDontCache) {
1028
				// PINP told us not to cache;
1029
				ldSetBrowserCache(false);
1030
			} else if (!$writecache) {
1031
				// Image came from the cache, it already has browser cache headers;
1032
			} else {
1033
				// Defaults for browser caching;
1034
				// Calls without session: public, max-age 1800;
1035
				// Calls with session without call chain (disk templates): private, no-cache no-store must-revalidate max-age=0
1036
				// Calls with session with call chain (pinp templates): private, max-age=1800;
1037
				// FIXME: Make the calls with session less trigger happy on not caching;
1038
1039
				/* if ($session_id && sizeof($ARCurrent->cacheCallChainSettings)) {
1040
					// With session and pinp templates;
1041
					$browserCachePrivate = true;
1042
					$browserCacheMaxAge = 1800;
1043
					$browserCacheNoStore = false;
1044
					$browserCacheNoCache = false;
1045
					$browserCacheMustRevalidate = false;
1046
				} else */
1047
				if ($session_id) {
1048
					// With session, disk templates only
1049
					$browserCachePrivate = true;
1050
					$browserCacheMaxAge = 0;
1051
					$browserCacheNoStore = true;
1052
					$browserCacheNoCache = true;
1053
					$browserCacheMustRevalidate = true;
1054
				} else {
1055
					// Without session and all other corner cases;
1056
					$browserCachePrivate = false;
1057
					$defaultMaxAge = 1800;
1058
					$browserCacheNoStore = false;
1059
					$browserCacheNoCache = false;
1060
					$browserCacheMustRevalidate = false;
1061
				}
1062
1063
				$browserCachecacheSetting = 0; // Default = inherit;
0 ignored issues
show
$browserCachecacheSetting is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
1064
1065
				// FIXME: The defaults for with session ID are now to not cache;
1066
				if(is_array($ARCurrent->cacheCallChainSettings) ) {
1067
					foreach ($ARCurrent->cacheCallChainSettings as $objectId => $pathCacheSetting) {
1068
						$browserCachePrivate = $browserCachePrivate || $pathCacheSetting['browserCachePrivate']; // If anyone says 'private', make it so.
1069
						$browserCacheNoStore = $browserCacheNoStore || $pathCacheSetting['browserCacheNoStore']; // If anyone says 'no-store', make it so.
1070
						$browserCacheNoCache = $browserCacheNoCache || $pathCacheSetting['browserCacheNoCache']; // If anyone says 'no-cache', make it so.
1071
						$browserCacheMustRevalidate = $browserCacheMustRevalidate || $pathCacheSetting['browserCacheMustRevalidate']; // If anyone says 'must-revalidate', make it so.
1072
						$browserCacheNoTransform = $browserCacheNoTransform || $pathCacheSetting['browserCacheNoTransform']; // If anyone says 'no-transform', make it so.
0 ignored issues
show
The variable $browserCacheNoTransform does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
1073
						$browserCacheProxyRevalidate = $browserCacheProxyRevalidate || $pathCacheSetting['browserCacheProxyRevalidate']; // If anyone says 'proxy-revalidate', make it so.
0 ignored issues
show
The variable $browserCacheProxyRevalidate does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
1074
1075 View Code Duplication
						if (isset($pathCacheSetting['browserCacheMaxAge']) && is_numeric($pathCacheSetting['browserCacheMaxAge'])) {
1076
							if (isset($browserCacheMaxAge)) {
1077
								$browserCacheMaxAge = min($browserCacheMaxAge, $pathCacheSetting['browserCacheMaxAge']);
1078
							} else {
1079
								$browserCacheMaxAge = $pathCacheSetting['browserCacheMaxAge'];
1080
							}
1081
						}
1082
1083 View Code Duplication
						if (isset($pathCacheSetting['browserCacheSMaxAge']) && is_numeric($pathCacheSetting['browserCacheMaxAge'])) {
1084
							if (isset($browserCacheSMaxAge)) {
1085
								$browserCacheSMaxAge = min($browserCacheSMaxAge, $pathCacheSetting['browserCacheSMaxAge']);
1086
							} else {
1087
								$browserCacheSMaxAge = $pathCacheSetting['browserCacheSMaxAge'];
1088
							}
1089
						}
1090
					}
1091
1092
					if (!isset($browserCacheMaxAge) && isset($defaultMaxAge)) {
1093
						$browserCacheMaxAge = $defaultMaxAge;
1094
					}
1095
				}	
1096
1097
				ldSetBrowserCache(
1098
					array(
1099
						"browserCachePrivate" => $browserCachePrivate,
1100
						"browserCacheNoStore" => $browserCacheNoStore,
1101
						"browserCacheNoCache" => $browserCacheNoCache,
1102
						"browserCacheMustRevalidate" => $browserCacheMustRevalidate,
1103
						"browserCacheNoTransform" => $browserCacheNoTransform,
1104
						"browserCacheProxyRevalidate" => $browserCacheProxyRevalidate,
1105
						"browserCacheMaxAge" => $browserCacheMaxAge,
0 ignored issues
show
The variable $browserCacheMaxAge does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
1106
						"browserCacheSMaxAge" => $browserCacheSMaxAge
0 ignored issues
show
The variable $browserCacheSMaxAge does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
1107
					)
1108
				);
1109
			}
1110
1111
1112
			$image_len = strlen($image);
1113
1114
			if ($ARCurrent->session && $ARCurrent->session->id) {
1115
				$ldCacheFilename = "/session".$ldCacheFilename;
1116
				$image = str_replace('-'.$ARCurrent->session->id.'-', '{arSessionID}', $image);
1117
			} else {
1118
				$ldCacheFilename = "/normal".$ldCacheFilename;
1119
			}
1120
			// because we have the full content, we can now also calculate the content length
1121
			ldHeader("Content-Length: ".$image_len);
1122
1123
1124
			// flush the buffer, this will send the contents to the browser
1125
			ob_end_flush();
1126
			debug("loader: ob_end_flush()","all");
1127
1128
1129
			// Calculate server side cache settings based on settings collected in the call chain;
1130
			//
1131
			// Rules: do not cache wins. short cache time wins over longer cache time. Unset values don't get to play.
1132
			//
1133
			// Overlord rule: if the request method was not a get, or debugging was used, do not cache. Ever.
1134
			//
1135
			// If pinp says arDontCache, then do not cache;
1136
			//
1137
			// If ESI was used and hit a cached image, do not write the image;
1138
1139
			if ($_SERVER['REQUEST_METHOD']!='GET' || ($DB["wasUsed"] > 0)) {
1140
				// Do not cache on server.
1141
				// header("X-Ariadne-Cache-Skipped: DB Used");
1142
			} else if (is_array($ARCurrent->cache) && ($file=array_pop($ARCurrent->cache))) {
1143
				error("cached() opened but not closed with savecache()");
1144
				// header("X-Ariadne-Cache-Skipped: cached problem.");
1145
			} else if ($ARCurrent->arDontCache) {
1146
				// PINP told us not to cache;
1147
				// header("X-Ariadne-Cache-Skipped: arDontCache");
1148
			} else if (!$writecache) {
1149
				// ESI was used and hit a cached image, do not write the image;
1150
				// header("X-Ariadne-Cache-Skipped: cached image used");
1151
			} else {
1152
				// header("X-Ariadne-Cache-Skipped: Writing cache now");
1153
				// Cache setting values:
1154
				// -2 = Refresh on change; Set the cache time on server to 999 hours (unlimited);
1155
				// -1 = Do not cache
1156
				// 0  = Inherit
1157
				// > 0: Refresh on request. The number is the amount of hours that the cache is 'fresh'. This can be a fraction/float value;
1158
1159
				$cacheSetting = 0; // Default = inherit;
1160
				$serverCachePrivate = 0; // do not allow caching of  sessions
1161
				if( is_array($ARCurrent->cacheCallChainSettings)) {
1162
					foreach ($ARCurrent->cacheCallChainSettings as $objectId => $pathCacheSetting) {
1163
						// FIXME: also 'resolve' $serverCachePrivate
1164
						$serverCache = $pathCacheSetting['serverCache'];
1165
1166
						if ($serverCache == 0 || !isset($serverCache)) {
1167
							// This path does not want to play;
1168
							$serverCache = $pathCacheSetting['serverCacheDefault'];
1169
						}
1170
1171
						if ($serverCache == -2) {
1172
							// Sorry, we meant that the cache image should be valid forever;
1173
							$serverCache = 999;
1174
						}
1175
1176
						if ($cacheSetting == 0) {
1177
							$cacheSetting = $serverCache;
1178
						} else {
1179
							$cacheSetting = min($serverCache, $cacheSetting);
1180
						}
1181
1182
						if ($cacheSetting == -1) {
1183
							// If someone told us to not cache, skip checking because nothing anyone else tells us will change this fact.
1184
							break;
1185
						}
1186
					}
1187
				}
1188
				// header("X-Ariadne-Cache-Setting: $cacheSetting");
1189
				if ($ARCurrent->session->id && $cacheSetting > 0) {
1190
					// we have a session id, can we cache ?
1191
					// FIXME: add support for $serverCachePrivate in the config and cache dialog
1192
					if ( ! ( $serverCachePrivate === 1  || $ARCurrent->arDoCachePrivate != false ) ) {
1193
						$cacheSetting = -1;
1194
					}
1195
				}
1196
1197
				if ($cacheSetting > 0) {
1198
					// If we are allowed to cache, write the image now.
1199
					if ($store) { // Sanity check to only write cache images if a store was initialized;
1200
						// FIXME: cacheCallChainSettings contains the objects that were called for this cache image;
1201
						// FIXME: cacheTemplateChain containers the templates that were called for this cache image;
1202
1203
						ldSetCache($ldCacheFilename, $cacheSetting, $image, @implode("\n",$ARCurrent->ldHeaders));
1204
						$cachestore=new cache($cache_config);
1205
						$cachestore->save($ldCacheFilename, $ARCurrent->cacheCallChainSettings, $ARCurrent->cacheTemplateChain);
1206
					}
1207
				}
1208
			}
1209
1210
		}
1211
1212
		if ($AR->ESI > 0) {
1213
			// Prevent ESI from looping when the ESI result has ESI tags in them.
1214
			// Reducing the AR->ESI number by 1 gives the flexibility to allow 2 or 3 ESI loops if desired.
1215
			// Setting it to false would mean you only get 1 ESI loop, which might not be the desired effect.
1216
			$AR->ESI = (int) $AR->ESI;
1217
			$AR->ESI--;
1218
1219
			$image = ob_get_contents();
1220
			ob_end_clean();
1221
			include_once($store_config['code']."modules/mod_esi.php");
1222
			$image = ESI::esiProcess($image);
1223
			$image_len = strlen($image);
1224
1225
			if ($ARCurrent->arDontCache) {
1226
				// FIXME: ook de cachetime 'niet cachen' uit het cachedialoog werkend maken...  || $ARCurrent->cachetime == 0) {
1227
				ldSetBrowserCache(false);
1228
			}
1229
			ldHeader("Content-Length: ".$image_len);
1230
			echo $image;
1231
		}
1232
	}
1233
1234
	function ldGetPutHandle() {
1235
		$stdin = fopen("php://input", "r");
1236
		return new ar_content_filesFile($stdin);
1237
	}
1238
1239