wp/wp-includes/ID3/getid3.php
changeset 19 3d72ae0968f4
parent 16 a86126ab1dd4
child 21 48c4eec2b7e6
equal deleted inserted replaced
18:be944660c56a 19:3d72ae0968f4
    14 	define('GETID3_OS_ISWINDOWS', (stripos(PHP_OS, 'WIN') === 0));
    14 	define('GETID3_OS_ISWINDOWS', (stripos(PHP_OS, 'WIN') === 0));
    15 }
    15 }
    16 // Get base path of getID3() - ONCE
    16 // Get base path of getID3() - ONCE
    17 if (!defined('GETID3_INCLUDEPATH')) {
    17 if (!defined('GETID3_INCLUDEPATH')) {
    18 	define('GETID3_INCLUDEPATH', dirname(__FILE__).DIRECTORY_SEPARATOR);
    18 	define('GETID3_INCLUDEPATH', dirname(__FILE__).DIRECTORY_SEPARATOR);
    19 }
       
    20 // Workaround Bug #39923 (https://bugs.php.net/bug.php?id=39923)
       
    21 if (!defined('IMG_JPG') && defined('IMAGETYPE_JPEG')) {
       
    22 	define('IMG_JPG', IMAGETYPE_JPEG);
       
    23 }
    19 }
    24 if (!defined('ENT_SUBSTITUTE')) { // PHP5.3 adds ENT_IGNORE, PHP5.4 adds ENT_SUBSTITUTE
    20 if (!defined('ENT_SUBSTITUTE')) { // PHP5.3 adds ENT_IGNORE, PHP5.4 adds ENT_SUBSTITUTE
    25 	define('ENT_SUBSTITUTE', (defined('ENT_IGNORE') ? ENT_IGNORE : 8));
    21 	define('ENT_SUBSTITUTE', (defined('ENT_IGNORE') ? ENT_IGNORE : 8));
    26 }
    22 }
    27 
    23 
    55 	$open_basedirs = explode(PATH_SEPARATOR, $open_basedir);
    51 	$open_basedirs = explode(PATH_SEPARATOR, $open_basedir);
    56 	foreach ($open_basedirs as $basedir) {
    52 	foreach ($open_basedirs as $basedir) {
    57 		if (substr($basedir, -1, 1) != DIRECTORY_SEPARATOR) {
    53 		if (substr($basedir, -1, 1) != DIRECTORY_SEPARATOR) {
    58 			$basedir .= DIRECTORY_SEPARATOR;
    54 			$basedir .= DIRECTORY_SEPARATOR;
    59 		}
    55 		}
    60 		if (preg_match('#^'.preg_quote($basedir).'#', $temp_dir)) {
    56 		if (strpos($temp_dir, $basedir) === 0) {
    61 			$found_valid_tempdir = true;
    57 			$found_valid_tempdir = true;
    62 			break;
    58 			break;
    63 		}
    59 		}
    64 	}
    60 	}
    65 	if (!$found_valid_tempdir) {
    61 	if (!$found_valid_tempdir) {
   212 	 *
   208 	 *
   213 	 * @var int
   209 	 * @var int
   214 	 */
   210 	 */
   215 	public $option_fread_buffer_size = 32768;
   211 	public $option_fread_buffer_size = 32768;
   216 
   212 
       
   213 
       
   214 
       
   215 	// module-specific options
       
   216 
       
   217 	/** archive.rar
       
   218 	 * if true use PHP RarArchive extension, if false (non-extension parsing not yet written in getID3)
       
   219 	 *
       
   220 	 * @var bool
       
   221 	 */
       
   222 	public $options_archive_rar_use_php_rar_extension = true;
       
   223 
       
   224 	/** archive.gzip
       
   225 	 * Optional file list - disable for speed.
       
   226 	 * Decode gzipped files, if possible, and parse recursively (.tar.gz for example).
       
   227 	 *
       
   228 	 * @var bool
       
   229 	 */
       
   230 	public $options_archive_gzip_parse_contents = false;
       
   231 
       
   232 	/** audio.midi
       
   233 	 * if false only parse most basic information, much faster for some files but may be inaccurate
       
   234 	 *
       
   235 	 * @var bool
       
   236 	 */
       
   237 	public $options_audio_midi_scanwholefile = true;
       
   238 
       
   239 	/** audio.mp3
       
   240 	 * Forces getID3() to scan the file byte-by-byte and log all the valid audio frame headers - extremely slow,
       
   241 	 * unrecommended, but may provide data from otherwise-unusable files.
       
   242 	 *
       
   243 	 * @var bool
       
   244 	 */
       
   245 	public $options_audio_mp3_allow_bruteforce = false;
       
   246 
       
   247 	/** audio.mp3
       
   248 	 * number of frames to scan to determine if MPEG-audio sequence is valid
       
   249 	 * Lower this number to 5-20 for faster scanning
       
   250 	 * Increase this number to 50+ for most accurate detection of valid VBR/CBR mpeg-audio streams
       
   251 	 *
       
   252 	 * @var int
       
   253 	 */
       
   254 	public $options_audio_mp3_mp3_valid_check_frames = 50;
       
   255 
       
   256 	/** audio.wavpack
       
   257 	 * Avoid scanning all frames (break after finding ID_RIFF_HEADER and ID_CONFIG_BLOCK,
       
   258 	 * significantly faster for very large files but other data may be missed
       
   259 	 *
       
   260 	 * @var bool
       
   261 	 */
       
   262 	public $options_audio_wavpack_quick_parsing = false;
       
   263 
       
   264 	/** audio-video.flv
       
   265 	 * Break out of the loop if too many frames have been scanned; only scan this
       
   266 	 * many if meta frame does not contain useful duration.
       
   267 	 *
       
   268 	 * @var int
       
   269 	 */
       
   270 	public $options_audiovideo_flv_max_frames = 100000;
       
   271 
       
   272 	/** audio-video.matroska
       
   273 	 * If true, do not return information about CLUSTER chunks, since there's a lot of them
       
   274 	 * and they're not usually useful [default: TRUE].
       
   275 	 *
       
   276 	 * @var bool
       
   277 	 */
       
   278 	public $options_audiovideo_matroska_hide_clusters    = true;
       
   279 
       
   280 	/** audio-video.matroska
       
   281 	 * True to parse the whole file, not only header [default: FALSE].
       
   282 	 *
       
   283 	 * @var bool
       
   284 	 */
       
   285 	public $options_audiovideo_matroska_parse_whole_file = false;
       
   286 
       
   287 	/** audio-video.quicktime
       
   288 	 * return all parsed data from all atoms if true, otherwise just returned parsed metadata
       
   289 	 *
       
   290 	 * @var bool
       
   291 	 */
       
   292 	public $options_audiovideo_quicktime_ReturnAtomData  = false;
       
   293 
       
   294 	/** audio-video.quicktime
       
   295 	 * return all parsed data from all atoms if true, otherwise just returned parsed metadata
       
   296 	 *
       
   297 	 * @var bool
       
   298 	 */
       
   299 	public $options_audiovideo_quicktime_ParseAllPossibleAtoms = false;
       
   300 
       
   301 	/** audio-video.swf
       
   302 	 * return all parsed tags if true, otherwise do not return tags not parsed by getID3
       
   303 	 *
       
   304 	 * @var bool
       
   305 	 */
       
   306 	public $options_audiovideo_swf_ReturnAllTagData = false;
       
   307 
       
   308 	/** graphic.bmp
       
   309 	 * return BMP palette
       
   310 	 *
       
   311 	 * @var bool
       
   312 	 */
       
   313 	public $options_graphic_bmp_ExtractPalette = false;
       
   314 
       
   315 	/** graphic.bmp
       
   316 	 * return image data
       
   317 	 *
       
   318 	 * @var bool
       
   319 	 */
       
   320 	public $options_graphic_bmp_ExtractData    = false;
       
   321 
       
   322 	/** graphic.png
       
   323 	 * If data chunk is larger than this do not read it completely (getID3 only needs the first
       
   324 	 * few dozen bytes for parsing).
       
   325 	 *
       
   326 	 * @var int
       
   327 	 */
       
   328 	public $options_graphic_png_max_data_bytes = 10000000;
       
   329 
       
   330 	/** misc.pdf
       
   331 	 * return full details of PDF Cross-Reference Table (XREF)
       
   332 	 *
       
   333 	 * @var bool
       
   334 	 */
       
   335 	public $options_misc_pdf_returnXREF = false;
       
   336 
       
   337 	/** misc.torrent
       
   338 	 * Assume all .torrent files are less than 1MB and just read entire thing into memory for easy processing.
       
   339 	 * Override this value if you need to process files larger than 1MB
       
   340 	 *
       
   341 	 * @var int
       
   342 	 */
       
   343 	public $options_misc_torrent_max_torrent_filesize = 1048576;
       
   344 
       
   345 
       
   346 
   217 	// Public variables
   347 	// Public variables
   218 
   348 
   219 	/**
   349 	/**
   220 	 * Filename of file being analysed.
   350 	 * Filename of file being analysed.
   221 	 *
   351 	 *
   255 	/**
   385 	/**
   256 	 * @var string
   386 	 * @var string
   257 	 */
   387 	 */
   258 	protected $startup_warning = '';
   388 	protected $startup_warning = '';
   259 
   389 
   260 	const VERSION           = '1.9.20-202006061653';
   390 	const VERSION           = '1.9.21-202109171300';
   261 	const FREAD_BUFFER_SIZE = 32768;
   391 	const FREAD_BUFFER_SIZE = 32768;
   262 
   392 
   263 	const ATTACHMENTS_NONE   = false;
   393 	const ATTACHMENTS_NONE   = false;
   264 	const ATTACHMENTS_INLINE = true;
   394 	const ATTACHMENTS_INLINE = true;
   265 
   395 
   635 			$class_name = 'getid3_'.$determined_format['module'];
   765 			$class_name = 'getid3_'.$determined_format['module'];
   636 			if (!class_exists($class_name)) {
   766 			if (!class_exists($class_name)) {
   637 				return $this->error('Format not supported, module "'.$determined_format['include'].'" is corrupt.');
   767 				return $this->error('Format not supported, module "'.$determined_format['include'].'" is corrupt.');
   638 			}
   768 			}
   639 			$class = new $class_name($this);
   769 			$class = new $class_name($this);
       
   770 
       
   771 			// set module-specific options
       
   772 			foreach (get_object_vars($this) as $getid3_object_vars_key => $getid3_object_vars_value) {
       
   773 				if (preg_match('#^options_([^_]+)_([^_]+)_(.+)$#i', $getid3_object_vars_key, $matches)) {
       
   774 					list($dummy, $GOVgroup, $GOVmodule, $GOVsetting) = $matches;
       
   775 					$GOVgroup = (($GOVgroup == 'audiovideo') ? 'audio-video' : $GOVgroup); // variable names can only contain 0-9a-z_ so standardize here
       
   776 					if (($GOVgroup == $determined_format['group']) && ($GOVmodule == $determined_format['module'])) {
       
   777 						$class->$GOVsetting = $getid3_object_vars_value;
       
   778 					}
       
   779 				}
       
   780 			}
       
   781 
   640 			$class->Analyze();
   782 			$class->Analyze();
   641 			unset($class);
   783 			unset($class);
   642 
   784 
   643 			// close file
   785 			// close file
   644 			fclose($this->fp);
   786 			fclose($this->fp);
  1349 				'msoffice' => array(
  1491 				'msoffice' => array(
  1350 							'pattern'   => '^\\xD0\\xCF\\x11\\xE0\\xA1\\xB1\\x1A\\xE1', // D0CF11E == DOCFILE == Microsoft Office Document
  1492 							'pattern'   => '^\\xD0\\xCF\\x11\\xE0\\xA1\\xB1\\x1A\\xE1', // D0CF11E == DOCFILE == Microsoft Office Document
  1351 							'group'     => 'misc',
  1493 							'group'     => 'misc',
  1352 							'module'    => 'msoffice',
  1494 							'module'    => 'msoffice',
  1353 							'mime_type' => 'application/octet-stream',
  1495 							'mime_type' => 'application/octet-stream',
       
  1496 							'fail_id3'  => 'ERROR',
       
  1497 							'fail_ape'  => 'ERROR',
       
  1498 						),
       
  1499 
       
  1500 				// TORRENT             - .torrent
       
  1501 				'torrent' => array(
       
  1502 							'pattern'   => '^(d8\\:announce|d7\\:comment)',
       
  1503 							'group'     => 'misc',
       
  1504 							'module'    => 'torrent',
       
  1505 							'mime_type' => 'application/x-bittorrent',
  1354 							'fail_id3'  => 'ERROR',
  1506 							'fail_id3'  => 'ERROR',
  1355 							'fail_ape'  => 'ERROR',
  1507 							'fail_ape'  => 'ERROR',
  1356 						),
  1508 						),
  1357 
  1509 
  1358 				 // CUE  - data       - CUEsheet (index to single-file disc images)
  1510 				 // CUE  - data       - CUEsheet (index to single-file disc images)
  1487 				foreach ($this->info[$comment_name]['comments'] as $tag_key => $valuearray) {
  1639 				foreach ($this->info[$comment_name]['comments'] as $tag_key => $valuearray) {
  1488 					foreach ($valuearray as $key => $value) {
  1640 					foreach ($valuearray as $key => $value) {
  1489 						if (is_string($value)) {
  1641 						if (is_string($value)) {
  1490 							$value = trim($value, " \r\n\t"); // do not trim nulls from $value!! Unicode characters will get mangled if trailing nulls are removed!
  1642 							$value = trim($value, " \r\n\t"); // do not trim nulls from $value!! Unicode characters will get mangled if trailing nulls are removed!
  1491 						}
  1643 						}
  1492 						if ($value) {
  1644 						if (isset($value) && $value !== "") {
  1493 							if (!is_numeric($key)) {
  1645 							if (!is_numeric($key)) {
  1494 								$this->info['tags'][trim($tag_name)][trim($tag_key)][$key] = $value;
  1646 								$this->info['tags'][trim($tag_name)][trim($tag_key)][$key] = $value;
  1495 							} else {
  1647 							} else {
  1496 								$this->info['tags'][trim($tag_name)][trim($tag_key)][]     = $value;
  1648 								$this->info['tags'][trim($tag_name)][trim($tag_key)][]     = $value;
  1497 							}
  1649 							}
  2094 
  2246 
  2095 				case SEEK_END:
  2247 				case SEEK_END:
  2096 					$this->data_string_position = $this->data_string_length + $bytes;
  2248 					$this->data_string_position = $this->data_string_length + $bytes;
  2097 					break;
  2249 					break;
  2098 			}
  2250 			}
  2099 			return 0;
  2251 			return 0; // fseek returns 0 on success
  2100 		} else {
  2252 		}
  2101 			$pos = $bytes;
  2253 
  2102 			if ($whence == SEEK_CUR) {
  2254 		$pos = $bytes;
  2103 				$pos = $this->ftell() + $bytes;
  2255 		if ($whence == SEEK_CUR) {
  2104 			} elseif ($whence == SEEK_END) {
  2256 			$pos = $this->ftell() + $bytes;
  2105 				$pos = $this->getid3->info['filesize'] + $bytes;
  2257 		} elseif ($whence == SEEK_END) {
  2106 			}
  2258 			$pos = $this->getid3->info['filesize'] + $bytes;
  2107 			if (!getid3_lib::intValueSupported($pos)) {
  2259 		}
  2108 				throw new getid3_exception('cannot fseek('.$pos.') because beyond PHP filesystem limit', 10);
  2260 		if (!getid3_lib::intValueSupported($pos)) {
  2109 			}
  2261 			throw new getid3_exception('cannot fseek('.$pos.') because beyond PHP filesystem limit', 10);
  2110 		}
  2262 		}
  2111 		return fseek($this->getid3->fp, $bytes, $whence);
  2263 
       
  2264 		// https://github.com/JamesHeinrich/getID3/issues/327
       
  2265 		$result = fseek($this->getid3->fp, $bytes, $whence);
       
  2266 		if ($result !== 0) { // fseek returns 0 on success
       
  2267 			throw new getid3_exception('cannot fseek('.$pos.'). resource/stream does not appear to support seeking', 10);
       
  2268 		}
       
  2269 		return $result;
  2112 	}
  2270 	}
  2113 
  2271 
  2114 	/**
  2272 	/**
  2115 	 * @return string|false
  2273 	 * @return string|false
  2116 	 *
  2274 	 *
  2222 	 *
  2380 	 *
  2223 	 * @throws Exception
  2381 	 * @throws Exception
  2224 	 * @throws getid3_exception
  2382 	 * @throws getid3_exception
  2225 	 */
  2383 	 */
  2226 	public function saveAttachment($name, $offset, $length, $image_mime=null) {
  2384 	public function saveAttachment($name, $offset, $length, $image_mime=null) {
       
  2385 		$fp_dest = null;
       
  2386 		$dest = null;
  2227 		try {
  2387 		try {
  2228 
  2388 
  2229 			// do not extract at all
  2389 			// do not extract at all
  2230 			if ($this->getid3->option_save_attachments === getID3::ATTACHMENTS_NONE) {
  2390 			if ($this->getid3->option_save_attachments === getID3::ATTACHMENTS_NONE) {
  2231 
  2391