/application/libraries/getid3/module.audio-video.asf.php
PHP | 1862 lines | 1154 code | 392 blank | 316 comment | 112 complexity | b542342119f02f24fa48a7bb09994f00 MD5 | raw file
Possible License(s): GPL-3.0, LGPL-2.1, Apache-2.0
Large files files are truncated, but you can click here to view the full file
- <?php
- // +----------------------------------------------------------------------+
- // | PHP version 5 |
- // +----------------------------------------------------------------------+
- // | Copyright (c) 2002-2009 James Heinrich, Allan Hansen |
- // +----------------------------------------------------------------------+
- // | This source file is subject to version 2 of the GPL license, |
- // | that is bundled with this package in the file license.txt and is |
- // | available through the world-wide-web at the following url: |
- // | http://www.gnu.org/copyleft/gpl.html |
- // +----------------------------------------------------------------------+
- // | getID3() - http://getid3.sourceforge.net or http://www.getid3.org |
- // +----------------------------------------------------------------------+
- // | Authors: James Heinrich <infoŘgetid3*org> |
- // | Allan Hansen <ahŘartemis*dk> |
- // +----------------------------------------------------------------------+
- // | module.audio-video.php |
- // | Module for analyzing Microsoft ASF, WMA and WMV files. |
- // | dependencies: module.audio-video.riff.php |
- // +----------------------------------------------------------------------+
- //
- // $Id: module.audio-video.asf.php,v 1.7 2006/12/01 22:39:48 ah Exp $
- class getid3_asf extends getid3_handler
- {
- const Extended_Stream_Properties_Object = '14E6A5CB-C672-4332-8399-A96952065B5A';
- const Padding_Object = '1806D474-CADF-4509-A4BA-9AABCB96AAE8';
- const Payload_Ext_Syst_Pixel_Aspect_Ratio = '1B1EE554-F9EA-4BC8-821A-376B74E4C4B8';
- const Script_Command_Object = '1EFB1A30-0B62-11D0-A39B-00A0C90348F6';
- const No_Error_Correction = '20FB5700-5B55-11CF-A8FD-00805F5C442B';
- const Content_Branding_Object = '2211B3FA-BD23-11D2-B4B7-00A0C955FC6E';
- const Content_Encryption_Object = '2211B3FB-BD23-11D2-B4B7-00A0C955FC6E';
- const Digital_Signature_Object = '2211B3FC-BD23-11D2-B4B7-00A0C955FC6E';
- const Extended_Content_Encryption_Object = '298AE614-2622-4C17-B935-DAE07EE9289C';
- const Simple_Index_Object = '33000890-E5B1-11CF-89F4-00A0C90349CB';
- const Degradable_JPEG_Media = '35907DE0-E415-11CF-A917-00805F5C442B';
- const Payload_Extension_System_Timecode = '399595EC-8667-4E2D-8FDB-98814CE76C1E';
- const Binary_Media = '3AFB65E2-47EF-40F2-AC2C-70A90D71D343';
- const Timecode_Index_Object = '3CB73FD0-0C4A-4803-953D-EDF7B6228F0C';
- const Metadata_Library_Object = '44231C94-9498-49D1-A141-1D134E457054';
- const Reserved_3 = '4B1ACBE3-100B-11D0-A39B-00A0C90348F6';
- const Reserved_4 = '4CFEDB20-75F6-11CF-9C0F-00A0C90349CB';
- const Command_Media = '59DACFC0-59E6-11D0-A3AC-00A0C90348F6';
- const Header_Extension_Object = '5FBF03B5-A92E-11CF-8EE3-00C00C205365';
- const Media_Object_Index_Parameters_Obj = '6B203BAD-3F11-4E84-ACA8-D7613DE2CFA7';
- const Header_Object = '75B22630-668E-11CF-A6D9-00AA0062CE6C';
- const Content_Description_Object = '75B22633-668E-11CF-A6D9-00AA0062CE6C';
- const Error_Correction_Object = '75B22635-668E-11CF-A6D9-00AA0062CE6C';
- const Data_Object = '75B22636-668E-11CF-A6D9-00AA0062CE6C';
- const Web_Stream_Media_Subtype = '776257D4-C627-41CB-8F81-7AC7FF1C40CC';
- const Stream_Bitrate_Properties_Object = '7BF875CE-468D-11D1-8D82-006097C9A2B2';
- const Language_List_Object = '7C4346A9-EFE0-4BFC-B229-393EDE415C85';
- const Codec_List_Object = '86D15240-311D-11D0-A3A4-00A0C90348F6';
- const Reserved_2 = '86D15241-311D-11D0-A3A4-00A0C90348F6';
- const File_Properties_Object = '8CABDCA1-A947-11CF-8EE4-00C00C205365';
- const File_Transfer_Media = '91BD222C-F21C-497A-8B6D-5AA86BFC0185';
- const Old_RTP_Extension_Data = '96800C63-4C94-11D1-837B-0080C7A37F95';
- const Advanced_Mutual_Exclusion_Object = 'A08649CF-4775-4670-8A16-6E35357566CD';
- const Bandwidth_Sharing_Object = 'A69609E6-517B-11D2-B6AF-00C04FD908E9';
- const Reserved_1 = 'ABD3D211-A9BA-11CF-8EE6-00C00C205365';
- const Bandwidth_Sharing_Exclusive = 'AF6060AA-5197-11D2-B6AF-00C04FD908E9';
- const Bandwidth_Sharing_Partial = 'AF6060AB-5197-11D2-B6AF-00C04FD908E9';
- const JFIF_Media = 'B61BE100-5B4E-11CF-A8FD-00805F5C442B';
- const Stream_Properties_Object = 'B7DC0791-A9B7-11CF-8EE6-00C00C205365';
- const Video_Media = 'BC19EFC0-5B4D-11CF-A8FD-00805F5C442B';
- const Audio_Spread = 'BFC3CD50-618F-11CF-8BB2-00AA00B4E220';
- const Metadata_Object = 'C5F8CBEA-5BAF-4877-8467-AA8C44FA4CCA';
- const Payload_Ext_Syst_Sample_Duration = 'C6BD9450-867F-4907-83A3-C77921B733AD';
- const Group_Mutual_Exclusion_Object = 'D1465A40-5A79-4338-B71B-E36B8FD6C249';
- const Extended_Content_Description_Object = 'D2D0A440-E307-11D2-97F0-00A0C95EA850';
- const Stream_Prioritization_Object = 'D4FED15B-88D3-454F-81F0-ED5C45999E24';
- const Payload_Ext_System_Content_Type = 'D590DC20-07BC-436C-9CF7-F3BBFBF1A4DC';
- const Old_File_Properties_Object = 'D6E229D0-35DA-11D1-9034-00A0C90349BE';
- const Old_ASF_Header_Object = 'D6E229D1-35DA-11D1-9034-00A0C90349BE';
- const Old_ASF_Data_Object = 'D6E229D2-35DA-11D1-9034-00A0C90349BE';
- const Index_Object = 'D6E229D3-35DA-11D1-9034-00A0C90349BE';
- const Old_Stream_Properties_Object = 'D6E229D4-35DA-11D1-9034-00A0C90349BE';
- const Old_Content_Description_Object = 'D6E229D5-35DA-11D1-9034-00A0C90349BE';
- const Old_Script_Command_Object = 'D6E229D6-35DA-11D1-9034-00A0C90349BE';
- const Old_Marker_Object = 'D6E229D7-35DA-11D1-9034-00A0C90349BE';
- const Old_Component_Download_Object = 'D6E229D8-35DA-11D1-9034-00A0C90349BE';
- const Old_Stream_Group_Object = 'D6E229D9-35DA-11D1-9034-00A0C90349BE';
- const Old_Scalable_Object = 'D6E229DA-35DA-11D1-9034-00A0C90349BE';
- const Old_Prioritization_Object = 'D6E229DB-35DA-11D1-9034-00A0C90349BE';
- const Bitrate_Mutual_Exclusion_Object = 'D6E229DC-35DA-11D1-9034-00A0C90349BE';
- const Old_Inter_Media_Dependency_Object = 'D6E229DD-35DA-11D1-9034-00A0C90349BE';
- const Old_Rating_Object = 'D6E229DE-35DA-11D1-9034-00A0C90349BE';
- const Index_Parameters_Object = 'D6E229DF-35DA-11D1-9034-00A0C90349BE';
- const Old_Color_Table_Object = 'D6E229E0-35DA-11D1-9034-00A0C90349BE';
- const Old_Language_List_Object = 'D6E229E1-35DA-11D1-9034-00A0C90349BE';
- const Old_Audio_Media = 'D6E229E2-35DA-11D1-9034-00A0C90349BE';
- const Old_Video_Media = 'D6E229E3-35DA-11D1-9034-00A0C90349BE';
- const Old_Image_Media = 'D6E229E4-35DA-11D1-9034-00A0C90349BE';
- const Old_Timecode_Media = 'D6E229E5-35DA-11D1-9034-00A0C90349BE';
- const Old_Text_Media = 'D6E229E6-35DA-11D1-9034-00A0C90349BE';
- const Old_MIDI_Media = 'D6E229E7-35DA-11D1-9034-00A0C90349BE';
- const Old_Command_Media = 'D6E229E8-35DA-11D1-9034-00A0C90349BE';
- const Old_No_Error_Concealment = 'D6E229EA-35DA-11D1-9034-00A0C90349BE';
- const Old_Scrambled_Audio = 'D6E229EB-35DA-11D1-9034-00A0C90349BE';
- const Old_No_Color_Table = 'D6E229EC-35DA-11D1-9034-00A0C90349BE';
- const Old_SMPTE_Time = 'D6E229ED-35DA-11D1-9034-00A0C90349BE';
- const Old_ASCII_Text = 'D6E229EE-35DA-11D1-9034-00A0C90349BE';
- const Old_Unicode_Text = 'D6E229EF-35DA-11D1-9034-00A0C90349BE';
- const Old_HTML_Text = 'D6E229F0-35DA-11D1-9034-00A0C90349BE';
- const Old_URL_Command = 'D6E229F1-35DA-11D1-9034-00A0C90349BE';
- const Old_Filename_Command = 'D6E229F2-35DA-11D1-9034-00A0C90349BE';
- const Old_ACM_Codec = 'D6E229F3-35DA-11D1-9034-00A0C90349BE';
- const Old_VCM_Codec = 'D6E229F4-35DA-11D1-9034-00A0C90349BE';
- const Old_QuickTime_Codec = 'D6E229F5-35DA-11D1-9034-00A0C90349BE';
- const Old_DirectShow_Transform_Filter = 'D6E229F6-35DA-11D1-9034-00A0C90349BE';
- const Old_DirectShow_Rendering_Filter = 'D6E229F7-35DA-11D1-9034-00A0C90349BE';
- const Old_No_Enhancement = 'D6E229F8-35DA-11D1-9034-00A0C90349BE';
- const Old_Unknown_Enhancement_Type = 'D6E229F9-35DA-11D1-9034-00A0C90349BE';
- const Old_Temporal_Enhancement = 'D6E229FA-35DA-11D1-9034-00A0C90349BE';
- const Old_Spatial_Enhancement = 'D6E229FB-35DA-11D1-9034-00A0C90349BE';
- const Old_Quality_Enhancement = 'D6E229FC-35DA-11D1-9034-00A0C90349BE';
- const Old_Number_of_Channels_Enhancement = 'D6E229FD-35DA-11D1-9034-00A0C90349BE';
- const Old_Frequency_Response_Enhancement = 'D6E229FE-35DA-11D1-9034-00A0C90349BE';
- const Old_Media_Object = 'D6E229FF-35DA-11D1-9034-00A0C90349BE';
- const Mutex_Language = 'D6E22A00-35DA-11D1-9034-00A0C90349BE';
- const Mutex_Bitrate = 'D6E22A01-35DA-11D1-9034-00A0C90349BE';
- const Mutex_Unknown = 'D6E22A02-35DA-11D1-9034-00A0C90349BE';
- const Old_ASF_Placeholder_Object = 'D6E22A0E-35DA-11D1-9034-00A0C90349BE';
- const Old_Data_Unit_Extension_Object = 'D6E22A0F-35DA-11D1-9034-00A0C90349BE';
- const Web_Stream_Format = 'DA1E6B13-8359-4050-B398-388E965BF00C';
- const Payload_Ext_System_File_Name = 'E165EC0E-19ED-45D7-B4A7-25CBD1E28E9B';
- const Marker_Object = 'F487CD01-A951-11CF-8EE6-00C00C205365';
- const Timecode_Index_Parameters_Object = 'F55E496D-9797-4B5D-8C8B-604DFE9BFB24';
- const Audio_Media = 'F8699E40-5B4D-11CF-A8FD-00805F5C442B';
- const Media_Object_Index_Object = 'FEB103F8-12AD-4C64-840F-2A1D2F7AD48C';
- const Alt_Extended_Content_Encryption_Obj = 'FF889EF1-ADEE-40DA-9E71-98704BB928CE';
- public function Analyze() {
- $getid3 = $this->getid3;
- $getid3->include_module('audio-video.riff');
- !isset($getid3->info['audio']) and $getid3->info['audio'] = array();
- !isset($getid3->info['video']) and $getid3->info['video'] = array();
- $getid3->info['asf']['comments'] = $getid3->info['asf']['header_object'] = array();
- $info_audio = &$getid3->info['audio'];
- $info_video = &$getid3->info['video'];
- $info_asf = &$getid3->info['asf'];
- $info_asf_comments = &$info_asf['comments'];
- $info_asf_header_object = &$info_asf['header_object'];
- // ASF structure:
- // * Header Object [required]
- // * File Properties Object [required] (global file attributes)
- // * Stream Properties Object [required] (defines media stream & characteristics)
- // * Header Extension Object [required] (additional functionality)
- // * Content Description Object (bibliographic information)
- // * Script Command Object (commands for during playback)
- // * Marker Object (named jumped points within the file)
- // * Data Object [required]
- // * Data Packets
- // * Index Object
- // Header Object: (mandatory, one only)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for header object - getid3_asf::Header_Object
- // Object Size QWORD 64 // size of header object, including 30 bytes of Header Object header
- // Number of Header Objects DWORD 32 // number of objects in header object
- // Reserved1 BYTE 8 // hardcoded: 0x01
- // Reserved2 BYTE 8 // hardcoded: 0x02
- $getid3->info['fileformat'] = 'asf';
- fseek($getid3->fp, $getid3->info['avdataoffset'], SEEK_SET);
- $header_object_data = fread($getid3->fp, 30);
- $info_asf_header_object['objectid_guid'] = getid3_asf::BytestringToGUID(substr($header_object_data, 0, 16));
- if ($info_asf_header_object['objectid_guid'] != getid3_asf::Header_Object) {
- throw new getid3_exception('ASF header GUID {'.$info_asf_header_object['objectid_guid'].'} does not match expected "getid3_asf::Header_Object" GUID {'.getid3_asf::Header_Object.'}');
- }
- getid3_lib::ReadSequence('LittleEndian2Int', $info_asf_header_object, $header_object_data, 16,
- array(
- 'objectsize' => 8,
- 'headerobjects' => 4,
- 'reserved1' => 1,
- 'reserved2' => 1
- )
- );
- $asf_header_data = fread($getid3->fp, $info_asf_header_object['objectsize'] - 30);
- $offset = 0;
- for ($header_objects_counter = 0; $header_objects_counter < $info_asf_header_object['headerobjects']; $header_objects_counter++) {
- $next_object_guid = substr($asf_header_data, $offset, 16);
- $offset += 16;
- $next_object_size = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 8));
- $offset += 8;
- $next_object_guidtext = getid3_asf::BytestringToGUID($next_object_guid);
- switch ($next_object_guidtext) {
- case getid3_asf::File_Properties_Object:
- // File Properties Object: (mandatory, one only)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for file properties object - getid3_asf::File_Properties_Object
- // Object Size QWORD 64 // size of file properties object, including 104 bytes of File Properties Object header
- // File ID GUID 128 // unique ID - identical to File ID in Data Object
- // File Size QWORD 64 // entire file in bytes. Invalid if Broadcast Flag == 1
- // Creation Date QWORD 64 // date & time of file creation. Maybe invalid if Broadcast Flag == 1
- // Data Packets Count QWORD 64 // number of data packets in Data Object. Invalid if Broadcast Flag == 1
- // Play Duration QWORD 64 // playtime, in 100-nanosecond units. Invalid if Broadcast Flag == 1
- // Send Duration QWORD 64 // time needed to send file, in 100-nanosecond units. Players can ignore this value. Invalid if Broadcast Flag == 1
- // Preroll QWORD 64 // time to buffer data before starting to play file, in 1-millisecond units. If <> 0, PlayDuration and PresentationTime have been offset by this amount
- // Flags DWORD 32 //
- // * Broadcast Flag bits 1 (0x01) // file is currently being written, some header values are invalid
- // * Seekable Flag bits 1 (0x02) // is file seekable
- // * Reserved bits 30 (0xFFFFFFFC) // reserved - set to zero
- // Minimum Data Packet Size DWORD 32 // in bytes. should be same as Maximum Data Packet Size. Invalid if Broadcast Flag == 1
- // Maximum Data Packet Size DWORD 32 // in bytes. should be same as Minimum Data Packet Size. Invalid if Broadcast Flag == 1
- // Maximum Bitrate DWORD 32 // maximum instantaneous bitrate in bits per second for entire file, including all data streams and ASF overhead
- $info_asf['file_properties_object'] = array();
- $info_asf_file_properties_object = &$info_asf['file_properties_object'];
- $info_asf_file_properties_object['objectid_guid'] = $next_object_guidtext;
- $info_asf_file_properties_object['objectsize'] = $next_object_size;
- $info_asf_file_properties_object['fileid_guid'] = getid3_asf::BytestringToGUID(substr($asf_header_data, $offset, 16));
- $offset += 16;
- getid3_lib::ReadSequence('LittleEndian2Int', $info_asf_file_properties_object, $asf_header_data, $offset,
- array(
- 'filesize' => 8,
- 'creation_date' => 8,
- 'data_packets' => 8,
- 'play_duration' => 8,
- 'send_duration' => 8,
- 'preroll' => 8,
- 'flags_raw' => 4,
- 'min_packet_size' => 4,
- 'max_packet_size' => 4,
- 'max_bitrate' => 4
- )
- );
- $offset += 64;
- if ($info_asf_file_properties_object['filesize'] > $getid3->info['filesize']) {
- $getid3->warning('Probable truncated file: file_properties_object.filesize ('.number_format($info_asf_file_properties_object['filesize']).') > filesize ('.number_format($getid3->info['filesize']).')');
- }
- $info_asf_file_properties_object['creation_date_unix'] = getid3_asf::FiletimeToUNIXtime($info_asf_file_properties_object['creation_date']);
- $info_asf_file_properties_object['flags']['broadcast'] = (bool)($info_asf_file_properties_object['flags_raw'] & 0x0001);
- $info_asf_file_properties_object['flags']['seekable'] = (bool)($info_asf_file_properties_object['flags_raw'] & 0x0002);
- $getid3->info['playtime_seconds'] = ($info_asf_file_properties_object['play_duration'] / 10000000) - ($info_asf_file_properties_object['preroll'] / 1000);
- $getid3->info['bitrate'] = ($info_asf_file_properties_object['filesize'] * 8) / $getid3->info['playtime_seconds'];
- break;
- case getid3_asf::Stream_Properties_Object:
- // Stream Properties Object: (mandatory, one per media stream)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for stream properties object - getid3_asf::Stream_Properties_Object
- // Object Size QWORD 64 // size of stream properties object, including 78 bytes of Stream Properties Object header
- // Stream Type GUID 128 // getid3_asf::Audio_Media, getid3_asf::Video_Media or getid3_asf::Command_Media
- // Error Correction Type GUID 128 // getid3_asf::Audio_Spread for audio-only streams, getid3_asf::No_Error_Correction for other stream types
- // Time Offset QWORD 64 // 100-nanosecond units. typically zero. added to all timestamps of samples in the stream
- // Type-Specific Data Length DWORD 32 // number of bytes for Type-Specific Data field
- // Error Correction Data Length DWORD 32 // number of bytes for Error Correction Data field
- // Flags WORD 16 //
- // * Stream Number bits 7 (0x007F) // number of this stream. 1 <= valid <= 127
- // * Reserved bits 8 (0x7F80) // reserved - set to zero
- // * Encrypted Content Flag bits 1 (0x8000) // stream contents encrypted if set
- // Reserved DWORD 32 // reserved - set to zero
- // Type-Specific Data BYTESTREAM variable // type-specific format data, depending on value of Stream Type
- // Error Correction Data BYTESTREAM variable // error-correction-specific format data, depending on value of Error Correct Type
- // There is one getid3_asf::Stream_Properties_Object for each stream (audio, video) but the
- // stream number isn't known until halfway through decoding the structure, hence it
- // it is decoded to a temporary variable and then stuck in the appropriate index later
- $stream_properties_object_data['objectid_guid'] = $next_object_guidtext;
- $stream_properties_object_data['objectsize'] = $next_object_size;
- getid3_lib::ReadSequence('LittleEndian2Int', $stream_properties_object_data, $asf_header_data, $offset,
- array(
- 'stream_type' => -16,
- 'error_correct_type' => -16,
- 'time_offset' => 8,
- 'type_data_length' => 4,
- 'error_data_length' => 4,
- 'flags_raw' => 2
- )
- );
- $stream_properties_stream_number = $stream_properties_object_data['flags_raw'] & 0x007F;
- $stream_properties_object_data['flags']['encrypted'] = (bool)($stream_properties_object_data['flags_raw'] & 0x8000);
- $stream_properties_object_data['stream_type_guid'] = getid3_asf::BytestringToGUID($stream_properties_object_data['stream_type']);
- $stream_properties_object_data['error_correct_guid'] = getid3_asf::BytestringToGUID($stream_properties_object_data['error_correct_type']);
- $offset += 54; // 50 bytes + 4 bytes reserved - DWORD
- $stream_properties_object_data['type_specific_data'] = substr($asf_header_data, $offset, $stream_properties_object_data['type_data_length']);
- $offset += $stream_properties_object_data['type_data_length'];
- $stream_properties_object_data['error_correct_data'] = substr($asf_header_data, $offset, $stream_properties_object_data['error_data_length']);
- $offset += $stream_properties_object_data['error_data_length'];
- switch ($stream_properties_object_data['stream_type_guid']) {
- case getid3_asf::Audio_Media:
- $info_audio['dataformat'] = (@$info_audio['dataformat'] ? $info_audio['dataformat'] : 'asf');
- $info_audio['bitrate_mode'] = (@$info_audio['bitrate_mode'] ? $info_audio['bitrate_mode'] : 'cbr');
- $audiodata = getid3_riff::RIFFparseWAVEFORMATex(substr($stream_properties_object_data['type_specific_data'], 0, 16));
- unset($audiodata['raw']);
- $info_audio = getid3_riff::array_merge_noclobber($audiodata, $info_audio);
- break;
- case getid3_asf::Video_Media:
- $info_video['dataformat'] = (@$info_video['dataformat'] ? $info_video['dataformat'] : 'asf');
- $info_video['bitrate_mode'] = (@$info_video['bitrate_mode'] ? $info_video['bitrate_mode'] : 'cbr');
- break;
- /* does nothing but eat memory
- case getid3_asf::Command_Media:
- default:
- // do nothing
- break;
- */
- }
- $info_asf['stream_properties_object'][$stream_properties_stream_number] = $stream_properties_object_data;
- unset($stream_properties_object_data); // clear for next stream, if any
- break;
- case getid3_asf::Header_Extension_Object:
- // Header Extension Object: (mandatory, one only)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for Header Extension object - getid3_asf::Header_Extension_Object
- // Object Size QWORD 64 // size of Header Extension object, including 46 bytes of Header Extension Object header
- // Reserved Field 1 GUID 128 // hardcoded: getid3_asf::Reserved_1
- // Reserved Field 2 WORD 16 // hardcoded: 0x00000006
- // Header Extension Data Size DWORD 32 // in bytes. valid: 0, or > 24. equals object size minus 46
- // Header Extension Data BYTESTREAM variable // array of zero or more extended header objects
- $info_asf['header_extension_object'] = array();
- $info_asf_header_extension_object = &$info_asf['header_extension_object'];
- $info_asf_header_extension_object['objectid_guid'] = $next_object_guidtext;
- $info_asf_header_extension_object['objectsize'] = $next_object_size;
- $info_asf_header_extension_object['reserved_1_guid'] = getid3_asf::BytestringToGUID(substr($asf_header_data, $offset, 16));
- $offset += 16;
- if ($info_asf_header_extension_object['reserved_1_guid'] != getid3_asf::Reserved_1) {
- $getid3->warning('header_extension_object.reserved_1 GUID ('.$info_asf_header_extension_object['reserved_1_guid'].') does not match expected "getid3_asf::Reserved_1" GUID ('.getid3_asf::Reserved_1.')');
- break;
- }
- $info_asf_header_extension_object['reserved_2'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- if ($info_asf_header_extension_object['reserved_2'] != 6) {
- $getid3->warning('header_extension_object.reserved_2 ('.getid3_lib::PrintHexBytes($info_asf_header_extension_object['reserved_2']).') does not match expected value of "6"');
- break;
- }
- $info_asf_header_extension_object['extension_data_size'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 4));
- $offset += 4;
- $info_asf_header_extension_object['extension_data'] = substr($asf_header_data, $offset, $info_asf_header_extension_object['extension_data_size']);
- $offset += $info_asf_header_extension_object['extension_data_size'];
- break;
- case getid3_asf::Codec_List_Object:
- // Codec List Object: (optional, one only)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for Codec List object - getid3_asf::Codec_List_Object
- // Object Size QWORD 64 // size of Codec List object, including 44 bytes of Codec List Object header
- // Reserved GUID 128 // hardcoded: 86D15241-311D-11D0-A3A4-00A0C90348F6
- // Codec Entries Count DWORD 32 // number of entries in Codec Entries array
- // Codec Entries array of: variable //
- // * Type WORD 16 // 0x0001 = Video Codec, 0x0002 = Audio Codec, 0xFFFF = Unknown Codec
- // * Codec Name Length WORD 16 // number of Unicode characters stored in the Codec Name field
- // * Codec Name WCHAR variable // array of Unicode characters - name of codec used to create the content
- // * Codec Description Length WORD 16 // number of Unicode characters stored in the Codec Description field
- // * Codec Description WCHAR variable // array of Unicode characters - description of format used to create the content
- // * Codec Information Length WORD 16 // number of Unicode characters stored in the Codec Information field
- // * Codec Information BYTESTREAM variable // opaque array of information bytes about the codec used to create the content
- $info_asf['codec_list_object'] = array();
- $info_asf_codec_list_object = &$info_asf['codec_list_object'];
- $info_asf_codec_list_object['objectid_guid'] = $next_object_guidtext;
- $info_asf_codec_list_object['objectsize'] = $next_object_size;
- $info_asf_codec_list_object['reserved_guid'] = getid3_asf::BytestringToGUID(substr($asf_header_data, $offset, 16));
- $offset += 16;
- if ($info_asf_codec_list_object['reserved_guid'] != '86D15241-311D-11D0-A3A4-00A0C90348F6') {
- $getid3->warning('codec_list_object.reserved GUID {'.$info_asf_codec_list_object['reserved_guid'].'} does not match expected "getid3_asf::Reserved_1" GUID {86D15241-311D-11D0-A3A4-00A0C90348F6}');
- break;
- }
- $info_asf_codec_list_object['codec_entries_count'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 4));
- $offset += 4;
- for ($codec_entry_counter = 0; $codec_entry_counter < $info_asf_codec_list_object['codec_entries_count']; $codec_entry_counter++) {
- $info_asf_codec_list_object['codec_entries'][$codec_entry_counter] = array();
- $info_asf_codec_list_object_codecentries_current = &$info_asf_codec_list_object['codec_entries'][$codec_entry_counter];
- $info_asf_codec_list_object_codecentries_current['type_raw'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- $info_asf_codec_list_object_codecentries_current['type'] = getid3_asf::ASFCodecListObjectTypeLookup($info_asf_codec_list_object_codecentries_current['type_raw']);
- $codec_name_length = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2)) * 2; // 2 bytes per character
- $offset += 2;
- $info_asf_codec_list_object_codecentries_current['name'] = substr($asf_header_data, $offset, $codec_name_length);
- $offset += $codec_name_length;
- $codec_description_length = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2)) * 2; // 2 bytes per character
- $offset += 2;
- $info_asf_codec_list_object_codecentries_current['description'] = substr($asf_header_data, $offset, $codec_description_length);
- $offset += $codec_description_length;
- $codec_information_length = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- $info_asf_codec_list_object_codecentries_current['information'] = substr($asf_header_data, $offset, $codec_information_length);
- $offset += $codec_information_length;
- if ($info_asf_codec_list_object_codecentries_current['type_raw'] == 2) { // audio codec
- if (strpos($info_asf_codec_list_object_codecentries_current['description'], ',') === false) {
- $getid3->warning('[asf][codec_list_object][codec_entries]['.$codec_entry_counter.'][description] expected to contain comma-seperated list of parameters: "'.$info_asf_codec_list_object_codecentries_current['description'].'"');
- } else {
- list($audio_codec_bitrate, $audio_codec_frequency, $audio_codec_channels) = explode(',', $this->TrimConvert($info_asf_codec_list_object_codecentries_current['description']));
- $info_audio['codec'] = $this->TrimConvert($info_asf_codec_list_object_codecentries_current['name']);
- if (!isset($info_audio['bitrate']) && strstr($audio_codec_bitrate, 'kbps')) {
- $info_audio['bitrate'] = (int)(trim(str_replace('kbps', '', $audio_codec_bitrate)) * 1000);
- }
- if (!isset($info_video['bitrate']) && isset($info_audio['bitrate']) && isset($info_asf['file_properties_object']['max_bitrate']) && ($info_asf_codec_list_object['codec_entries_count'] > 1)) {
- $info_video['bitrate'] = $info_asf['file_properties_object']['max_bitrate'] - $info_audio['bitrate'];
- }
- if (!@$info_video['bitrate'] && @$info_audio['bitrate'] && @$getid3->info['bitrate']) {
- $info_video['bitrate'] = $getid3->info['bitrate'] - $info_audio['bitrate'];
- }
- $audio_codec_frequency = (int)trim(str_replace('kHz', '', $audio_codec_frequency));
- static $sample_rate_lookup = array(
- 8 => 8000, 8000 => 8000,
- 11 => 11025, 11025 => 11025,
- 12 => 12000, 12000 => 12000,
- 16 => 16000, 16000 => 16000,
- 22 => 22050, 22050 => 22050,
- 24 => 24000, 24000 => 24000,
- 32 => 32000, 32000 => 32000,
- 44 => 44100, 44100 => 44100,
- 48 => 48000, 48000 => 48000,
- );
- $info_audio['sample_rate'] = @$sample_rate_lookup[$audio_codec_frequency];
- if (!$info_audio['sample_rate']) {
- $getid3->warning('unknown frequency: "'.$audio_codec_frequency.'" ('.$this->TrimConvert($info_asf_codec_list_object_codecentries_current['description']).')');
- break;
- }
- if (!isset($info_audio['channels'])) {
- if (strstr($audio_codec_channels, 'stereo')) {
- $info_audio['channels'] = 2;
- } elseif (strstr($audio_codec_channels, 'mono')) {
- $info_audio['channels'] = 1;
- }
- }
- }
- }
- }
- break;
- case getid3_asf::Script_Command_Object:
- // Script Command Object: (optional, one only)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for Script Command object - getid3_asf::Script_Command_Object
- // Object Size QWORD 64 // size of Script Command object, including 44 bytes of Script Command Object header
- // Reserved GUID 128 // hardcoded: 4B1ACBE3-100B-11D0-A39B-00A0C90348F6
- // Commands Count WORD 16 // number of Commands structures in the Script Commands Objects
- // Command Types Count WORD 16 // number of Command Types structures in the Script Commands Objects
- // Command Types array of: variable //
- // * Command Type Name Length WORD 16 // number of Unicode characters for Command Type Name
- // * Command Type Name WCHAR variable // array of Unicode characters - name of a type of command
- // Commands array of: variable //
- // * Presentation Time DWORD 32 // presentation time of that command, in milliseconds
- // * Type Index WORD 16 // type of this command, as a zero-based index into the array of Command Types of this object
- // * Command Name Length WORD 16 // number of Unicode characters for Command Name
- // * Command Name WCHAR variable // array of Unicode characters - name of this command
- // shortcut
- $info_asf['script_command_object'] = array();
- $info_asf_script_command_object = &$info_asf['script_command_object'];
- $info_asf_script_command_object['objectid_guid'] = $next_object_guidtext;
- $info_asf_script_command_object['objectsize'] = $next_object_size;
- $info_asf_script_command_object['reserved_guid'] = getid3_asf::BytestringToGUID(substr($asf_header_data, $offset, 16));
- $offset += 16;
- if ($info_asf_script_command_object['reserved_guid'] != '4B1ACBE3-100B-11D0-A39B-00A0C90348F6') {
- $getid3->warning('script_command_object.reserved GUID {'.$info_asf_script_command_object['reserved_guid'].'} does not match expected GUID {4B1ACBE3-100B-11D0-A39B-00A0C90348F6}');
- break;
- }
- $info_asf_script_command_object['commands_count'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- $info_asf_script_command_object['command_types_count'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- for ($command_types_counter = 0; $command_types_counter < $info_asf_script_command_object['command_types_count']; $command_types_counter++) {
- $command_type_name_length = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2)) * 2; // 2 bytes per character
- $offset += 2;
- $info_asf_script_command_object['command_types'][$command_types_counter]['name'] = substr($asf_header_data, $offset, $command_type_name_length);
- $offset += $command_type_name_length;
- }
- for ($commands_counter = 0; $commands_counter < $info_asf_script_command_object['commands_count']; $commands_counter++) {
- $info_asf_script_command_object['commands'][$commands_counter]['presentation_time'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 4));
- $offset += 4;
- $info_asf_script_command_object['commands'][$commands_counter]['type_index'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- $command_type_name_length = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2)) * 2; // 2 bytes per character
- $offset += 2;
- $info_asf_script_command_object['commands'][$commands_counter]['name'] = substr($asf_header_data, $offset, $command_type_name_length);
- $offset += $command_type_name_length;
- }
- break;
- case getid3_asf::Marker_Object:
- // Marker Object: (optional, one only)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for Marker object - getid3_asf::Marker_Object
- // Object Size QWORD 64 // size of Marker object, including 48 bytes of Marker Object header
- // Reserved GUID 128 // hardcoded: 4CFEDB20-75F6-11CF-9C0F-00A0C90349CB
- // Markers Count DWORD 32 // number of Marker structures in Marker Object
- // Reserved WORD 16 // hardcoded: 0x0000
- // Name Length WORD 16 // number of bytes in the Name field
- // Name WCHAR variable // name of the Marker Object
- // Markers array of: variable //
- // * Offset QWORD 64 // byte offset into Data Object
- // * Presentation Time QWORD 64 // in 100-nanosecond units
- // * Entry Length WORD 16 // length in bytes of (Send Time + Flags + Marker Description Length + Marker Description + Padding)
- // * Send Time DWORD 32 // in milliseconds
- // * Flags DWORD 32 // hardcoded: 0x00000000
- // * Marker Description Length DWORD 32 // number of bytes in Marker Description field
- // * Marker Description WCHAR variable // array of Unicode characters - description of marker entry
- // * Padding BYTESTREAM variable // optional padding bytes
- $info_asf['marker_object'] = array();
- $info_asf_marker_object = &$info_asf['marker_object'];
- $info_asf_marker_object['objectid_guid'] = $next_object_guidtext;
- $info_asf_marker_object['objectsize'] = $next_object_size;
- $info_asf_marker_object['reserved_guid'] = getid3_asf::BytestringToGUID(substr($asf_header_data, $offset, 16));
- $offset += 16;
- if ($info_asf_marker_object['reserved_guid'] != '4CFEDB20-75F6-11CF-9C0F-00A0C90349CB') {
- $getid3->warning('marker_object.reserved GUID {'.$info_asf_marker_object['reserved_guid'].'} does not match expected GUID {4CFEDB20-75F6-11CF-9C0F-00A0C90349CB}');
- break;
- }
- $info_asf_marker_object['markers_count'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 4));
- $offset += 4;
- $info_asf_marker_object['reserved_2'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- if ($info_asf_marker_object['reserved_2'] != 0) {
- $getid3->warning('marker_object.reserved_2 ('.getid3_lib::PrintHexBytes($info_asf_marker_object['reserved_2']).') does not match expected value of "0"');
- break;
- }
- $info_asf_marker_object['name_length'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- $info_asf_marker_object['name'] = substr($asf_header_data, $offset, $info_asf_marker_object['name_length']);
- $offset += $info_asf_marker_object['name_length'];
- for ($markers_counter = 0; $markers_counter < $info_asf_marker_object['markers_count']; $markers_counter++) {
- getid3_lib::ReadSequence('LittleEndian2Int', $info_asf_marker_object['markers'][$markers_counter], $asf_header_data, $offset,
- array(
- 'offset' => 8,
- 'presentation_time' => 8,
- 'entry_length' => 2,
- 'send_time' => 4,
- 'flags' => 4,
- 'marker_description_length' => 4
- )
- );
- $offset += 30;
- $info_asf_marker_object['markers'][$markers_counter]['marker_description'] = substr($asf_header_data, $offset, $info_asf_marker_object['markers'][$markers_counter]['marker_description_length']);
- $offset += $info_asf_marker_object['markers'][$markers_counter]['marker_description_length'];
- $padding_length = $info_asf_marker_object['markers'][$markers_counter]['entry_length'] - 4 - 4 - 4 - $info_asf_marker_object['markers'][$markers_counter]['marker_description_length'];
- if ($padding_length > 0) {
- $info_asf_marker_object['markers'][$markers_counter]['padding'] = substr($asf_header_data, $offset, $padding_length);
- $offset += $padding_length;
- }
- }
- break;
- case getid3_asf::Bitrate_Mutual_Exclusion_Object:
- // Bitrate Mutual Exclusion Object: (optional)
- // Field Name Field Type Size (bits)
- // Object ID GUID 128 // GUID for Bitrate Mutual Exclusion object - getid3_asf::Bitrate_Mutual_Exclusion_Object
- // Object Size QWORD 64 // size of Bitrate Mutual Exclusion object, including 42 bytes of Bitrate Mutual Exclusion Object header
- // Exlusion Type GUID 128 // nature of mutual exclusion relationship. one of: (getid3_asf::Mutex_Bitrate, getid3_asf::Mutex_Unknown)
- // Stream Numbers Count WORD 16 // number of video streams
- // Stream Numbers WORD variable // array of mutually exclusive video stream numbers. 1 <= valid <= 127
- // shortcut
- $info_asf['bitrate_mutual_exclusion_object'] = array();
- $info_asf_bitrate_mutual_exclusion_object = &$info_asf['bitrate_mutual_exclusion_object'];
- $info_asf_bitrate_mutual_exclusion_object['objectid_guid'] = $next_object_guidtext;
- $info_asf_bitrate_mutual_exclusion_object['objectsize'] = $next_object_size;
- $info_asf_bitrate_mutual_exclusion_object['reserved_guid'] = getid3_asf::BytestringToGUID(substr($asf_header_data, $offset, 16));
- $offset += 16;
- if ($info_asf_bitrate_mutual_exclusion_object['reserved_guid'] != getid3_asf::Mutex_Bitrate && $info_asf_bitrate_mutual_exclusion_object['reserved_guid'] != getid3_asf::Mutex_Unknown) {
- $getid3->warning('bitrate_mutual_exclusion_object.reserved GUID {'.$info_asf_bitrate_mutual_exclusion_object['reserved_guid'].'} does not match expected "getid3_asf::Mutex_Bitrate" GUID {'.getid3_asf::Mutex_Bitrate.'} or "getid3_asf::Mutex_Unknown" GUID {'.getid3_asf::Mutex_Unknown.'}');
- break;
- }
- $info_asf_bitrate_mutual_exclusion_object['stream_numbers_count'] = getid3_lib::LittleEndian2Int(substr($asf_header_data, $offset, 2));
- $offset += 2;
- for ($stream_number_counter = 0; $stream_number_counter < $info_asf_bitrate_mutual_exclusion_object['stream_numbers_count']; $stream_number_counter++) {
- $info_asf_bitrate_mut…
Large files files are truncated, but you can click here to view the full file