PluginProbe ʕ •ᴥ•ʔ
Matomo Analytics – Powerful, Privacy-First Insights for WordPress / 4.3.0
Matomo Analytics – Powerful, Privacy-First Insights for WordPress v4.3.0
5.11.1 5.11.0 5.10.2 5.10.1 trunk 1.0.2 1.0.3 1.0.4 1.0.5 1.0.6 1.1.0 1.1.1 1.1.2 1.1.3 1.2.0 1.3.0 1.3.1 1.3.2 4.0.0 4.0.1 4.0.2 4.0.3 4.0.4 4.1.0 4.1.1 4.1.2 4.1.3 4.10.0 4.11.0 4.12.0 4.13.0 4.13.2 4.13.3 4.13.4 4.13.5 4.14.0 4.14.1 4.14.2 4.15.0 4.15.1 4.15.2 4.15.3 4.2.0 4.3.0 4.3.1 4.4.1 4.4.2 4.5.0 4.6.0 5.0.1 5.0.2 5.0.3 5.0.4 5.0.5 5.0.6 5.0.7 5.0.8 5.1.0 5.1.1 5.1.2 5.1.3 5.1.4 5.1.5 5.1.6 5.1.7 5.10.0 5.2.0 5.2.1 5.2.2 5.3.0 5.3.1 5.3.2 5.3.3 5.6.0 5.6.1 5.7.0 5.7.1 5.8.0 5.8.1 5.8.2
matomo / app / libs / upgradephp / upgrade.php
matomo / app / libs / upgradephp Last commit date
README 6 years ago upgrade.php 6 years ago
upgrade.php
735 lines
1 <?php
2 /**
3 * api: php
4 * title: upgrade.php
5 * description: Emulates functions from new PHP versions on older interpreters.
6 * version: 17
7 * license: Public Domain
8 * url: http://freshmeat.net/projects/upgradephp
9 * type: functions
10 * category: library
11 * priority: auto
12 * load_if: (PHP_VERSION<5.2)
13 * sort: -255
14 * provides: upgrade-php, api:php5, json
15 *
16 *
17 * By loading this library you get PHP version independence. It provides
18 * downwards compatibility to older PHP interpreters by emulating missing
19 * functions or constants using IDENTICAL NAMES. So this doesn't slow down
20 * script execution on setups where the native functions already exist. It
21 * is meant as quick drop-in solution. It spares you from rewriting code or
22 * using cumbersome workarounds instead of the more powerful v5 functions.
23 *
24 * It cannot mirror PHP5s extended OO-semantics and functionality into PHP4
25 * however. A few features are added here that weren't part of PHP yet. And
26 * some other function collections are separated out into the ext/ directory.
27 * It doesn't produce many custom error messages (YAGNI), and instead leaves
28 * reporting to invoked functions or for native PHP execution.
29 *
30 * And further this is PUBLIC DOMAIN (no copyright, no license, no warranty)
31 * so therefore compatible to ALL open source licenses. You could rip this
32 * paragraph out to republish this instead only under more restrictive terms
33 * or your favorite license (GNU LGPL/GPL, BSDL, MPL/CDDL, Artistic/PHPL, ..)
34 *
35 * Any contribution is appreciated. <milky*users#sf#net>
36 *
37 */
38 use Piwik\SettingsServer;
39
40 /**
41 * ------------------------------ 5.2 ---
42 * @group 5_2
43 * @since 5.2
44 *
45 * Additions of PHP 5.2.0
46 * - some listed here might have appeared earlier or in release candidates
47 *
48 * @emulated
49 * error_get_last
50 * preg_last_error
51 * lchown
52 * lchgrp
53 * E_RECOVERABLE_ERROR
54 * M_SQRTPI
55 * M_LNPI
56 * M_EULER
57 * M_SQRT3
58 *
59 * @missing
60 * sys_getloadavg
61 * inet_ntop
62 * inet_pton
63 * array_fill_keys
64 * array_intersect_key
65 * array_intersect_ukey
66 * array_diff_key
67 * array_diff_ukey
68 * array_product
69 * pdo_drivers
70 * ftp_ssl_connect
71 * XmlReader
72 * XmlWriter
73 * PDO*
74 *
75 * @unimplementable
76 * stream_*
77 *
78 */
79
80 /**
81 * Constants for future 64-bit integer support.
82 *
83 */
84 if (!defined("PHP_INT_SIZE")) { define("PHP_INT_SIZE", 4); }
85 if (!defined("PHP_INT_MAX")) { define("PHP_INT_MAX", 2147483647); }
86
87 /*
88 These functions emulate the "character type" extension, which is
89 present in PHP first since version 4.3 per default. In this variant
90 only ASCII and Latin-1 characters are being handled. The first part
91 is eventually faster.
92 */
93
94
95 /**
96 * Sets the default client character set.
97 *
98 * @compat
99 * Procedural style
100 * @bugs
101 * PHP documentation says this function exists in PHP 5 >= 5.0.5,
102 * but it also depends on the versions of external libraries, e.g.,
103 * php_mysqli.dll and libmysql.dll.
104 *
105 * @param $link mysqli MySQLi connection resource
106 * @param $charset string Character set
107 * @return bool TRUE on success, FALSE on failure
108 */
109 if (in_array('mysqli', @get_loaded_extensions()) && !function_exists('mysqli_set_charset')) {
110 function mysqli_set_charset($link, $charset)
111 {
112 return mysqli_query($link, "SET NAMES '$charset'");
113 }
114 }
115
116 /**
117 * parse_ini_file() replacement.
118 * Behaves like parse_ini_file($filename, $process_sections);
119 *
120 * @author Andrew Sohn <asohn (at) aircanopy (dot) net>
121 * @author anthon (dot) pang (at) gmail (dot) com
122 *
123 * @param string $filename
124 * @param bool $process_sections (defaults to false)
125 * @return array
126 */
127 if(function_exists('parse_ini_file')) {
128 // provide a wrapper
129 function _parse_ini_file($filename, $process_sections = false) {
130 if(!file_exists($filename)) {
131 return false;
132 }
133
134 return parse_ini_file($filename, $process_sections);
135 }
136 } else {
137 // we can't redefine parse_ini_file() if it has been disabled
138 function _parse_ini_file($filename, $process_sections = false)
139 {
140 if(!file_exists($filename)) {
141 return false;
142 }
143
144 if(function_exists('file_get_contents')) {
145 $ini = file_get_contents($filename);
146 } else if(function_exists('file')) {
147 if($ini = file($filename)) {
148 $ini = implode("\n", $ini);
149 }
150 } else if(function_exists('fopen') && function_exists('fread')) {
151 $handle = fopen($filename, 'r');
152 if(!$handle) {
153 return false;
154 }
155 $ini = fread($handle, filesize($filename));
156 fclose($handle);
157 } else {
158 return false;
159 }
160
161 if($ini === false) {
162 return false;
163 }
164 if(is_string($ini)) { $ini = explode("\n", str_replace("\r", "\n", $ini)); }
165 if (count($ini) == 0) { return array(); }
166
167 $sections = array();
168 $values = array();
169 $result = array();
170 $globals = array();
171 $i = 0;
172 foreach ($ini as $line) {
173 $line = trim($line);
174 $line = str_replace("\t", " ", $line);
175
176 // Comments
177 if (!preg_match('/^[a-zA-Z0-9[]/', $line)) {continue;}
178
179 // Sections
180 if ($line[0] == '[') {
181 $tmp = explode(']', $line);
182 $sections[] = trim(substr($tmp[0], 1));
183 $i++;
184 continue;
185 }
186
187 // Key-value pair
188 list($key, $value) = explode('=', $line, 2);
189 $key = trim($key);
190 $value = trim($value);
191 if (strstr($value, ";")) {
192 $tmp = explode(';', $value);
193 if (count($tmp) == 2) {
194 if ((($value[0] != '"') && ($value[0] != "'")) ||
195 preg_match('/^".*"\s*;/', $value) || preg_match('/^".*;[^"]*$/', $value) ||
196 preg_match("/^'.*'\s*;/", $value) || preg_match("/^'.*;[^']*$/", $value) ){
197 $value = $tmp[0];
198 }
199 } else {
200 if ($value[0] == '"') {
201 $value = preg_replace('/^"(.*)".*/', '$1', $value);
202 } elseif ($value[0] == "'") {
203 $value = preg_replace("/^'(.*)'.*/", '$1', $value);
204 } else {
205 $value = $tmp[0];
206 }
207 }
208 }
209
210 $value = trim($value);
211 $value = trim($value, "'\"");
212
213 if ($i == 0) {
214 if (substr($key, -2) == '[]') {
215 $globals[substr($key, 0, -2)][] = $value;
216 } else {
217 $globals[$key] = $value;
218 }
219 } else {
220 if (substr($key, -2) == '[]') {
221 $values[$i-1][substr($key, 0, -2)][] = $value;
222 } else {
223 $values[$i-1][$key] = $value;
224 }
225 }
226 }
227
228 for ($j = 0; $j < $i; $j++) {
229 if (isset($values[$j])) {
230 if ($process_sections === true) {
231 $result[$sections[$j]] = $values[$j];
232 } else {
233 $result[] = $values[$j];
234 }
235 } else {
236 if ($process_sections === true) {
237 $result[$sections[$j]] = array();
238 }
239 }
240 }
241
242 return $result + $globals;
243 }
244 }
245
246 /**
247 * glob() replacement.
248 * Behaves like glob($pattern, $flags)
249 *
250 * @author BigueNique AT yahoo DOT ca
251 * @author anthon (dot) pang (at) gmail (dot) com
252 *
253 * @param string $pattern
254 * @param int $flags GLOBL_ONLYDIR, GLOB_MARK, GLOB_NOSORT (other flags not supported; defaults to 0)
255 * @return array
256 */
257 if(function_exists('glob')) {
258 // provide a wrapper
259 function _glob($pattern, $flags = 0) {
260 return glob($pattern, $flags);
261 }
262 } else if(function_exists('opendir') && function_exists('readdir')) {
263 // we can't redefine glob() if it has been disabled
264 function _glob($pattern, $flags = 0) {
265 $path = dirname($pattern);
266 $filePattern = basename($pattern);
267 if(is_dir($path) && ($handle = opendir($path)) !== false) {
268 $matches = array();
269 while(($file = readdir($handle)) !== false) {
270 if(($file[0] != '.')
271 && fnmatch($filePattern, $file)
272 && (!($flags & GLOB_ONLYDIR) || is_dir("$path/$file"))) {
273 $matches[] = "$path/$file" . ($flags & GLOB_MARK ? '/' : '');
274 }
275 }
276 closedir($handle);
277 if(!($flags & GLOB_NOSORT)) {
278 sort($matches);
279 }
280 return $matches;
281 }
282 return false;
283 }
284 } else {
285 function _glob($pattern, $flags = 0) {
286 return false;
287 }
288 }
289
290 /**
291 * Reads entire file into a string.
292 * This function is not 100% compatible with the native function.
293 *
294 * @see http://php.net/file_get_contents
295 * @since PHP 4.3.0
296 *
297 * @param string $filename Name of the file to read.
298 * @return string The read data or false on failure.
299 */
300 if (!function_exists('file_get_contents'))
301 {
302 function file_get_contents($filename)
303 {
304 $fhandle = fopen($filename, "r");
305 $fcontents = fread($fhandle, filesize($filename));
306 fclose($fhandle);
307 return $fcontents;
308 }
309 }
310
311 /**
312 * Safe serialize() and unserialize() replacements
313 *
314 * @license Public Domain
315 *
316 * @author anthon (dot) pang (at) gmail (dot) com
317 */
318
319 /*
320 * Arbitrary limits for safe_unserialize()
321 */
322 define('MAX_SERIALIZED_INPUT_LENGTH', 4096);
323 define('MAX_SERIALIZED_ARRAY_LENGTH', 256);
324 define('MAX_SERIALIZED_ARRAY_DEPTH', 3);
325
326
327 /**
328 * Safe serialize() replacement
329 * - output a strict subset of PHP's native serialized representation
330 * - does not serialize objects
331 *
332 * @param mixed $value
333 * @return string
334 * @throw Exception if $value is malformed or contains unsupported types (e.g., resources, objects)
335 */
336 function _safe_serialize( $value )
337 {
338 if(is_null($value))
339 {
340 return 'N;';
341 }
342 if(is_bool($value))
343 {
344 return 'b:'.(int)$value.';';
345 }
346 if(is_int($value))
347 {
348 return 'i:'.$value.';';
349 }
350 if(is_float($value))
351 {
352 return 'd:'.str_replace(',', '.', $value).';';
353 }
354 if(is_string($value))
355 {
356 return 's:'.strlen($value).':"'.$value.'";';
357 }
358 if(is_array($value))
359 {
360 $out = '';
361 foreach($value as $k => $v)
362 {
363 $out .= _safe_serialize($k) . _safe_serialize($v);
364 }
365
366 return 'a:'.count($value).':{'.$out.'}';
367 }
368
369 // safe_serialize cannot serialize resources or objects
370 return false;
371 }
372
373 /**
374 * Wrapper for _safe_serialize() that handles exceptions and multibyte encoding issue
375 *
376 * @param mixed $value
377 * @return string
378 */
379 function safe_serialize( $value )
380 {
381 // ensure we use the byte count for strings even when strlen() is overloaded by mb_strlen()
382 if (function_exists('mb_internal_encoding') &&
383 (((int) ini_get('mbstring.func_overload')) & 2))
384 {
385 $mbIntEnc = mb_internal_encoding();
386 mb_internal_encoding('ASCII');
387 }
388
389 $out = _safe_serialize($value);
390
391 if (isset($mbIntEnc))
392 {
393 mb_internal_encoding($mbIntEnc);
394 }
395 return $out;
396 }
397
398 /**
399 * Safe unserialize() replacement
400 * - accepts a strict subset of PHP's native serialized representation
401 * - does not unserialize objects
402 *
403 * @param string $str
404 * @return mixed
405 * @throw Exception if $str is malformed or contains unsupported types (e.g., resources, objects)
406 */
407 function _safe_unserialize($str)
408 {
409 if(strlen($str) > MAX_SERIALIZED_INPUT_LENGTH)
410 {
411 // input exceeds MAX_SERIALIZED_INPUT_LENGTH
412 return false;
413 }
414
415 if(empty($str) || !is_string($str))
416 {
417 return false;
418 }
419
420 $stack = array();
421 $expected = array();
422
423 /*
424 * states:
425 * 0 - initial state, expecting a single value or array
426 * 1 - terminal state
427 * 2 - in array, expecting end of array or a key
428 * 3 - in array, expecting value or another array
429 */
430 $state = 0;
431 while($state != 1)
432 {
433 $type = isset($str[0]) ? $str[0] : '';
434
435 if($type == '}')
436 {
437 $str = substr($str, 1);
438 }
439 else if($type == 'N' && $str[1] == ';')
440 {
441 $value = null;
442 $str = substr($str, 2);
443 }
444 else if($type == 'b' && preg_match('/^b:([01]);/', $str, $matches))
445 {
446 $value = $matches[1] == '1' ? true : false;
447 $str = substr($str, 4);
448 }
449 else if($type == 'i' && preg_match('/^i:(-?[0-9]+);(.*)/s', $str, $matches))
450 {
451 $value = (int)$matches[1];
452 $str = $matches[2];
453 }
454 else if($type == 'd' && preg_match('/^d:(-?[0-9]+\.?[0-9]*(E[+-][0-9]+)?);(.*)/s', $str, $matches))
455 {
456 $value = (float)$matches[1];
457 $str = $matches[3];
458 }
459 else if($type == 's' && preg_match('/^s:([0-9]+):"(.*)/s', $str, $matches) && substr($matches[2], (int)$matches[1], 2) == '";')
460 {
461 $value = substr($matches[2], 0, (int)$matches[1]);
462 $str = substr($matches[2], (int)$matches[1] + 2);
463 }
464 else if($type == 'a' && preg_match('/^a:([0-9]+):{(.*)/s', $str, $matches) && $matches[1] < MAX_SERIALIZED_ARRAY_LENGTH)
465 {
466 $expectedLength = (int)$matches[1];
467 $str = $matches[2];
468 }
469 else
470 {
471 // object or unknown/malformed type
472 return false;
473 }
474
475 switch($state)
476 {
477 case 3: // in array, expecting value or another array
478 if($type == 'a')
479 {
480 if(count($stack) >= MAX_SERIALIZED_ARRAY_DEPTH)
481 {
482 // array nesting exceeds MAX_SERIALIZED_ARRAY_DEPTH
483 return false;
484 }
485
486 $stack[] = &$list;
487 $list[$key] = array();
488 $list = &$list[$key];
489 $expected[] = $expectedLength;
490 $state = 2;
491 break;
492 }
493 if($type != '}')
494 {
495 $list[$key] = $value;
496 $state = 2;
497 break;
498 }
499
500 // missing array value
501 return false;
502
503 case 2: // in array, expecting end of array or a key
504 if($type == '}')
505 {
506 if(count($list) < end($expected))
507 {
508 // array size less than expected
509 return false;
510 }
511
512 unset($list);
513 $list = &$stack[count($stack)-1];
514 array_pop($stack);
515
516 // go to terminal state if we're at the end of the root array
517 array_pop($expected);
518 if(count($expected) == 0) {
519 $state = 1;
520 }
521 break;
522 }
523 if($type == 'i' || $type == 's')
524 {
525 if(count($list) >= MAX_SERIALIZED_ARRAY_LENGTH)
526 {
527 // array size exceeds MAX_SERIALIZED_ARRAY_LENGTH
528 return false;
529 }
530 if(count($list) >= end($expected))
531 {
532 // array size exceeds expected length
533 return false;
534 }
535
536 $key = $value;
537 $state = 3;
538 break;
539 }
540
541 // illegal array index type
542 return false;
543
544 case 0: // expecting array or value
545 if($type == 'a')
546 {
547 if(count($stack) >= MAX_SERIALIZED_ARRAY_DEPTH)
548 {
549 // array nesting exceeds MAX_SERIALIZED_ARRAY_DEPTH
550 return false;
551 }
552
553 $data = array();
554 $list = &$data;
555 $expected[] = $expectedLength;
556 $state = 2;
557 break;
558 }
559 if($type != '}')
560 {
561 $data = $value;
562 $state = 1;
563 break;
564 }
565
566 // not in array
567 return false;
568 }
569 }
570
571 if(!empty($str))
572 {
573 // trailing data in input
574 return false;
575 }
576 return $data;
577 }
578
579 /**
580 * Wrapper for _safe_unserialize() that handles exceptions and multibyte encoding issue
581 *
582 * @param string $str
583 * @return mixed
584 */
585 function safe_unserialize( $str )
586 {
587 // ensure we use the byte count for strings even when strlen() is overloaded by mb_strlen()
588 if (function_exists('mb_internal_encoding') &&
589 (((int) ini_get('mbstring.func_overload')) & 2))
590 {
591 $mbIntEnc = mb_internal_encoding();
592 mb_internal_encoding('ASCII');
593 }
594
595 $out = _safe_unserialize($str);
596
597 if (isset($mbIntEnc))
598 {
599 mb_internal_encoding($mbIntEnc);
600 }
601 return $out;
602 }
603
604 /**
605 * readfile() replacement.
606 * Behaves similar to readfile($filename);
607 *
608 * @author anthon (dot) pang (at) gmail (dot) com
609 *
610 * @param string $filename
611 * @param bool $useIncludePath
612 * @param resource $context
613 * @return int the number of bytes read from the file, or false if an error occurs
614 */
615 function _readfile($filename, $byteStart, $byteEnd, $useIncludePath = false, $context = null)
616 {
617 $count = @filesize($filename);
618
619 // built-in function has a 2 MB limit when using mmap
620 if (function_exists('readfile')
621 && $count <= (2 * 1024 * 1024)
622 && $byteStart == 0
623 && $byteEnd == $count
624 ) {
625 return @readfile($filename, $useIncludePath, $context);
626 }
627
628 // when in doubt (or when readfile() function is disabled)
629 $handle = @fopen($filename, SettingsServer::isWindows() ? "rb" : "r");
630 if ($handle) {
631 fseek($handle, $byteStart);
632
633 for ($pos = $byteStart; $pos < $byteEnd && !feof($handle); $pos = ftell($handle)) {
634 echo fread($handle, min(8192, $byteEnd - $pos));
635
636 @ob_flush();
637 @flush();
638 }
639
640 fclose($handle);
641 return $byteEnd - $byteStart;
642 }
643 return false;
644 }
645
646 /**
647 * utf8_encode replacement
648 *
649 * @param string $data
650 * @return string
651 */
652 if (!function_exists('utf8_encode')) {
653 function utf8_encode($data) {
654 if (function_exists('iconv')) {
655 return @iconv('ISO-8859-1', 'UTF-8', $data);
656 }
657 return $data;
658 }
659 }
660
661 /**
662 * utf8_decode replacement
663 *
664 * @param string $data
665 * @return string
666 */
667 if (!function_exists('utf8_decode')) {
668 function utf8_decode($data) {
669 if (function_exists('iconv')) {
670 return @iconv('UTF-8', 'ISO-8859-1', $data);
671 }
672 return $data;
673 }
674 }
675
676 /**
677 * Use strtolower if mb_strtolower doesn't exist (i.e., php not compiled with --enable-mbstring)
678 * This is not a functional replacement for mb_strtolower.
679 *
680 * @param string $input
681 * @param string $charset
682 */
683 if(!function_exists('mb_strtolower')) {
684 function mb_strtolower($input, $charset = '') {
685 return strtolower($input);
686 }
687 }
688
689 /**
690 * Use strlen if mb_strlen doesn't exist (i.e., php not compiled with --enable-mbstring)
691 * This is not a functional replacement for mb_strlen.
692 *
693 * @param string $input
694 * @param string $charset
695 */
696 if(!function_exists('mb_strlen')) {
697 function mb_strlen($input, $charset = '') {
698 return strlen($input);
699 }
700 }
701
702 /**
703 * On ubuntu in some cases, there is a bug that gzopen does not exist and one must use gzopen64 instead
704 */
705 if (!function_exists('gzopen')
706 && function_exists('gzopen64')) {
707 function gzopen($filename , $mode = 'r', $use_include_path = 0 )
708 {
709 return gzopen64($filename , $mode, $use_include_path);
710 }
711 }
712
713 if (!function_exists('dump')) {
714 function dump () {
715
716 }
717 }
718
719 /**
720 * Need to catch that PHP7 error object on php5
721 */
722 if( !class_exists('\Error')) {
723 class Error {
724
725 }
726 }
727
728 if(!function_exists('fnmatch')) {
729
730 function fnmatch($pattern, $string) {
731 return preg_match("#^".strtr(preg_quote($pattern, '#'), array('\*' => '.*', '\?' => '.'))."$#i", $string);
732 } // end
733
734 } // end if
735