[ Index ] |
PHP Cross Reference of phpwcms V1.5.0 _r431 (28.01.12) |
[Summary view] [Print] [Text view]
1 <?php 2 /** 3 * SimplePie 4 * 5 * A PHP-Based RSS and Atom Feed Framework. 6 * Takes the hard work out of managing a complete RSS/Atom solution. 7 * 8 * Copyright (c) 2004-2011, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors 9 * All rights reserved. 10 * 11 * Redistribution and use in source and binary forms, with or without modification, are 12 * permitted provided that the following conditions are met: 13 * 14 * * Redistributions of source code must retain the above copyright notice, this list of 15 * conditions and the following disclaimer. 16 * 17 * * Redistributions in binary form must reproduce the above copyright notice, this list 18 * of conditions and the following disclaimer in the documentation and/or other materials 19 * provided with the distribution. 20 * 21 * * Neither the name of the SimplePie Team nor the names of its contributors may be used 22 * to endorse or promote products derived from this software without specific prior 23 * written permission. 24 * 25 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS 26 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY 27 * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS 28 * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 29 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 30 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 31 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 32 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 33 * POSSIBILITY OF SUCH DAMAGE. 34 * 35 * @package SimplePie 36 * @version 1.2.1 37 * @copyright 2004-2011 Ryan Parman, Geoffrey Sneddon, Ryan McCue 38 * @author Ryan Parman 39 * @author Geoffrey Sneddon 40 * @author Ryan McCue 41 * @link http://simplepie.org/ SimplePie 42 * @link http://simplepie.org/support/ Please submit all bug reports and feature requests to the SimplePie forums 43 * @license http://www.opensource.org/licenses/bsd-license.php BSD License 44 * @todo phpDoc comments 45 */ 46 47 /** 48 * SimplePie Name 49 */ 50 define('SIMPLEPIE_NAME', 'SimplePie'); 51 52 /** 53 * SimplePie Version 54 */ 55 define('SIMPLEPIE_VERSION', '1.2.1-dev'); 56 57 /** 58 * SimplePie Build 59 */ 60 define('SIMPLEPIE_BUILD', '20111015034325'); 61 62 /** 63 * SimplePie Website URL 64 */ 65 define('SIMPLEPIE_URL', 'http://simplepie.org'); 66 67 /** 68 * SimplePie Useragent 69 * @see SimplePie::set_useragent() 70 */ 71 define('SIMPLEPIE_USERAGENT', SIMPLEPIE_NAME . '/' . SIMPLEPIE_VERSION . ' (Feed Parser; ' . SIMPLEPIE_URL . '; Allow like Gecko) Build/' . SIMPLEPIE_BUILD); 72 73 /** 74 * SimplePie Linkback 75 */ 76 define('SIMPLEPIE_LINKBACK', '<a href="' . SIMPLEPIE_URL . '" title="' . SIMPLEPIE_NAME . ' ' . SIMPLEPIE_VERSION . '">' . SIMPLEPIE_NAME . '</a>'); 77 78 /** 79 * No Autodiscovery 80 * @see SimplePie::set_autodiscovery_level() 81 */ 82 define('SIMPLEPIE_LOCATOR_NONE', 0); 83 84 /** 85 * Feed Link Element Autodiscovery 86 * @see SimplePie::set_autodiscovery_level() 87 */ 88 define('SIMPLEPIE_LOCATOR_AUTODISCOVERY', 1); 89 90 /** 91 * Local Feed Extension Autodiscovery 92 * @see SimplePie::set_autodiscovery_level() 93 */ 94 define('SIMPLEPIE_LOCATOR_LOCAL_EXTENSION', 2); 95 96 /** 97 * Local Feed Body Autodiscovery 98 * @see SimplePie::set_autodiscovery_level() 99 */ 100 define('SIMPLEPIE_LOCATOR_LOCAL_BODY', 4); 101 102 /** 103 * Remote Feed Extension Autodiscovery 104 * @see SimplePie::set_autodiscovery_level() 105 */ 106 define('SIMPLEPIE_LOCATOR_REMOTE_EXTENSION', 8); 107 108 /** 109 * Remote Feed Body Autodiscovery 110 * @see SimplePie::set_autodiscovery_level() 111 */ 112 define('SIMPLEPIE_LOCATOR_REMOTE_BODY', 16); 113 114 /** 115 * All Feed Autodiscovery 116 * @see SimplePie::set_autodiscovery_level() 117 */ 118 define('SIMPLEPIE_LOCATOR_ALL', 31); 119 120 /** 121 * No known feed type 122 */ 123 define('SIMPLEPIE_TYPE_NONE', 0); 124 125 /** 126 * RSS 0.90 127 */ 128 define('SIMPLEPIE_TYPE_RSS_090', 1); 129 130 /** 131 * RSS 0.91 (Netscape) 132 */ 133 define('SIMPLEPIE_TYPE_RSS_091_NETSCAPE', 2); 134 135 /** 136 * RSS 0.91 (Userland) 137 */ 138 define('SIMPLEPIE_TYPE_RSS_091_USERLAND', 4); 139 140 /** 141 * RSS 0.91 (both Netscape and Userland) 142 */ 143 define('SIMPLEPIE_TYPE_RSS_091', 6); 144 145 /** 146 * RSS 0.92 147 */ 148 define('SIMPLEPIE_TYPE_RSS_092', 8); 149 150 /** 151 * RSS 0.93 152 */ 153 define('SIMPLEPIE_TYPE_RSS_093', 16); 154 155 /** 156 * RSS 0.94 157 */ 158 define('SIMPLEPIE_TYPE_RSS_094', 32); 159 160 /** 161 * RSS 1.0 162 */ 163 define('SIMPLEPIE_TYPE_RSS_10', 64); 164 165 /** 166 * RSS 2.0 167 */ 168 define('SIMPLEPIE_TYPE_RSS_20', 128); 169 170 /** 171 * RDF-based RSS 172 */ 173 define('SIMPLEPIE_TYPE_RSS_RDF', 65); 174 175 /** 176 * Non-RDF-based RSS (truly intended as syndication format) 177 */ 178 define('SIMPLEPIE_TYPE_RSS_SYNDICATION', 190); 179 180 /** 181 * All RSS 182 */ 183 define('SIMPLEPIE_TYPE_RSS_ALL', 255); 184 185 /** 186 * Atom 0.3 187 */ 188 define('SIMPLEPIE_TYPE_ATOM_03', 256); 189 190 /** 191 * Atom 1.0 192 */ 193 define('SIMPLEPIE_TYPE_ATOM_10', 512); 194 195 /** 196 * All Atom 197 */ 198 define('SIMPLEPIE_TYPE_ATOM_ALL', 768); 199 200 /** 201 * All feed types 202 */ 203 define('SIMPLEPIE_TYPE_ALL', 1023); 204 205 /** 206 * No construct 207 */ 208 define('SIMPLEPIE_CONSTRUCT_NONE', 0); 209 210 /** 211 * Text construct 212 */ 213 define('SIMPLEPIE_CONSTRUCT_TEXT', 1); 214 215 /** 216 * HTML construct 217 */ 218 define('SIMPLEPIE_CONSTRUCT_HTML', 2); 219 220 /** 221 * XHTML construct 222 */ 223 define('SIMPLEPIE_CONSTRUCT_XHTML', 4); 224 225 /** 226 * base64-encoded construct 227 */ 228 define('SIMPLEPIE_CONSTRUCT_BASE64', 8); 229 230 /** 231 * IRI construct 232 */ 233 define('SIMPLEPIE_CONSTRUCT_IRI', 16); 234 235 /** 236 * A construct that might be HTML 237 */ 238 define('SIMPLEPIE_CONSTRUCT_MAYBE_HTML', 32); 239 240 /** 241 * All constructs 242 */ 243 define('SIMPLEPIE_CONSTRUCT_ALL', 63); 244 245 /** 246 * Don't change case 247 */ 248 define('SIMPLEPIE_SAME_CASE', 1); 249 250 /** 251 * Change to lowercase 252 */ 253 define('SIMPLEPIE_LOWERCASE', 2); 254 255 /** 256 * Change to uppercase 257 */ 258 define('SIMPLEPIE_UPPERCASE', 4); 259 260 /** 261 * PCRE for HTML attributes 262 */ 263 define('SIMPLEPIE_PCRE_HTML_ATTRIBUTE', '((?:[\x09\x0A\x0B\x0C\x0D\x20]+[^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3D\x3E]*(?:[\x09\x0A\x0B\x0C\x0D\x20]*=[\x09\x0A\x0B\x0C\x0D\x20]*(?:"(?:[^"]*)"|\'(?:[^\']*)\'|(?:[^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?)*)[\x09\x0A\x0B\x0C\x0D\x20]*'); 264 265 /** 266 * PCRE for XML attributes 267 */ 268 define('SIMPLEPIE_PCRE_XML_ATTRIBUTE', '((?:\s+(?:(?:[^\s:]+:)?[^\s:]+)\s*=\s*(?:"(?:[^"]*)"|\'(?:[^\']*)\'))*)\s*'); 269 270 /** 271 * XML Namespace 272 */ 273 define('SIMPLEPIE_NAMESPACE_XML', 'http://www.w3.org/XML/1998/namespace'); 274 275 /** 276 * Atom 1.0 Namespace 277 */ 278 define('SIMPLEPIE_NAMESPACE_ATOM_10', 'http://www.w3.org/2005/Atom'); 279 280 /** 281 * Atom 0.3 Namespace 282 */ 283 define('SIMPLEPIE_NAMESPACE_ATOM_03', 'http://purl.org/atom/ns#'); 284 285 /** 286 * RDF Namespace 287 */ 288 define('SIMPLEPIE_NAMESPACE_RDF', 'http://www.w3.org/1999/02/22-rdf-syntax-ns#'); 289 290 /** 291 * RSS 0.90 Namespace 292 */ 293 define('SIMPLEPIE_NAMESPACE_RSS_090', 'http://my.netscape.com/rdf/simple/0.9/'); 294 295 /** 296 * RSS 1.0 Namespace 297 */ 298 define('SIMPLEPIE_NAMESPACE_RSS_10', 'http://purl.org/rss/1.0/'); 299 300 /** 301 * RSS 1.0 Content Module Namespace 302 */ 303 define('SIMPLEPIE_NAMESPACE_RSS_10_MODULES_CONTENT', 'http://purl.org/rss/1.0/modules/content/'); 304 305 /** 306 * RSS 2.0 Namespace 307 * (Stupid, I know, but I'm certain it will confuse people less with support.) 308 */ 309 define('SIMPLEPIE_NAMESPACE_RSS_20', ''); 310 311 /** 312 * DC 1.0 Namespace 313 */ 314 define('SIMPLEPIE_NAMESPACE_DC_10', 'http://purl.org/dc/elements/1.0/'); 315 316 /** 317 * DC 1.1 Namespace 318 */ 319 define('SIMPLEPIE_NAMESPACE_DC_11', 'http://purl.org/dc/elements/1.1/'); 320 321 /** 322 * W3C Basic Geo (WGS84 lat/long) Vocabulary Namespace 323 */ 324 define('SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO', 'http://www.w3.org/2003/01/geo/wgs84_pos#'); 325 326 /** 327 * GeoRSS Namespace 328 */ 329 define('SIMPLEPIE_NAMESPACE_GEORSS', 'http://www.georss.org/georss'); 330 331 /** 332 * Media RSS Namespace 333 */ 334 define('SIMPLEPIE_NAMESPACE_MEDIARSS', 'http://search.yahoo.com/mrss/'); 335 336 /** 337 * Wrong Media RSS Namespace. Caused by a long-standing typo in the spec. 338 */ 339 define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG', 'http://search.yahoo.com/mrss'); 340 341 /** 342 * Wrong Media RSS Namespace #2. New namespace introduced in Media RSS 1.5. 343 */ 344 define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG2', 'http://video.search.yahoo.com/mrss'); 345 346 /** 347 * Wrong Media RSS Namespace #3. A possible typo of the Media RSS 1.5 namespace. 348 */ 349 define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG3', 'http://video.search.yahoo.com/mrss/'); 350 351 /** 352 * Wrong Media RSS Namespace #4. New spec location after the RSS Advisory Board takes it over, but not a valid namespace. 353 */ 354 define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG4', 'http://www.rssboard.org/media-rss'); 355 356 /** 357 * Wrong Media RSS Namespace #5. A possible typo of the RSS Advisory Board URL. 358 */ 359 define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG5', 'http://www.rssboard.org/media-rss/'); 360 361 /** 362 * iTunes RSS Namespace 363 */ 364 define('SIMPLEPIE_NAMESPACE_ITUNES', 'http://www.itunes.com/dtds/podcast-1.0.dtd'); 365 366 /** 367 * XHTML Namespace 368 */ 369 define('SIMPLEPIE_NAMESPACE_XHTML', 'http://www.w3.org/1999/xhtml'); 370 371 /** 372 * IANA Link Relations Registry 373 */ 374 define('SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY', 'http://www.iana.org/assignments/relation/'); 375 376 /** 377 * Whether we're running on PHP5 378 */ 379 define('SIMPLEPIE_PHP5', version_compare(PHP_VERSION, '5.0.0', '>=')); 380 381 /** 382 * No file source 383 */ 384 define('SIMPLEPIE_FILE_SOURCE_NONE', 0); 385 386 /** 387 * Remote file source 388 */ 389 define('SIMPLEPIE_FILE_SOURCE_REMOTE', 1); 390 391 /** 392 * Local file source 393 */ 394 define('SIMPLEPIE_FILE_SOURCE_LOCAL', 2); 395 396 /** 397 * fsockopen() file source 398 */ 399 define('SIMPLEPIE_FILE_SOURCE_FSOCKOPEN', 4); 400 401 /** 402 * cURL file source 403 */ 404 define('SIMPLEPIE_FILE_SOURCE_CURL', 8); 405 406 /** 407 * file_get_contents() file source 408 */ 409 define('SIMPLEPIE_FILE_SOURCE_FILE_GET_CONTENTS', 16); 410 411 /** 412 * SimplePie 413 * 414 * @package SimplePie 415 */ 416 class SimplePie 417 { 418 /** 419 * @var array Raw data 420 * @access private 421 */ 422 var $data = array(); 423 424 /** 425 * @var mixed Error string 426 * @access private 427 */ 428 var $error; 429 430 /** 431 * @var object Instance of SimplePie_Sanitize (or other class) 432 * @see SimplePie::set_sanitize_class() 433 * @access private 434 */ 435 var $sanitize; 436 437 /** 438 * @var string SimplePie Useragent 439 * @see SimplePie::set_useragent() 440 * @access private 441 */ 442 var $useragent = SIMPLEPIE_USERAGENT; 443 444 /** 445 * @var string Feed URL 446 * @see SimplePie::set_feed_url() 447 * @access private 448 */ 449 var $feed_url; 450 451 /** 452 * @var object Instance of SimplePie_File to use as a feed 453 * @see SimplePie::set_file() 454 * @access private 455 */ 456 var $file; 457 458 /** 459 * @var string Raw feed data 460 * @see SimplePie::set_raw_data() 461 * @access private 462 */ 463 var $raw_data; 464 465 /** 466 * @var int Timeout for fetching remote files 467 * @see SimplePie::set_timeout() 468 * @access private 469 */ 470 var $timeout = 10; 471 472 /** 473 * @var bool Forces fsockopen() to be used for remote files instead 474 * of cURL, even if a new enough version is installed 475 * @see SimplePie::force_fsockopen() 476 * @access private 477 */ 478 var $force_fsockopen = false; 479 480 /** 481 * @var bool Force the given data/URL to be treated as a feed no matter what 482 * it appears like 483 * @see SimplePie::force_feed() 484 * @access private 485 */ 486 var $force_feed = false; 487 488 /** 489 * @var bool Enable/Disable XML dump 490 * @see SimplePie::enable_xml_dump() 491 * @access private 492 */ 493 var $xml_dump = false; 494 495 /** 496 * @var bool Enable/Disable Caching 497 * @see SimplePie::enable_cache() 498 * @access private 499 */ 500 var $cache = true; 501 502 /** 503 * @var int Cache duration (in seconds) 504 * @see SimplePie::set_cache_duration() 505 * @access private 506 */ 507 var $cache_duration = 3600; 508 509 /** 510 * @var int Auto-discovery cache duration (in seconds) 511 * @see SimplePie::set_autodiscovery_cache_duration() 512 * @access private 513 */ 514 var $autodiscovery_cache_duration = 604800; // 7 Days. 515 516 /** 517 * @var string Cache location (relative to executing script) 518 * @see SimplePie::set_cache_location() 519 * @access private 520 */ 521 var $cache_location = './cache'; 522 523 /** 524 * @var string Function that creates the cache filename 525 * @see SimplePie::set_cache_name_function() 526 * @access private 527 */ 528 var $cache_name_function = 'md5'; 529 530 /** 531 * @var bool Reorder feed by date descending 532 * @see SimplePie::enable_order_by_date() 533 * @access private 534 */ 535 var $order_by_date = true; 536 537 /** 538 * @var mixed Force input encoding to be set to the follow value 539 * (false, or anything type-cast to false, disables this feature) 540 * @see SimplePie::set_input_encoding() 541 * @access private 542 */ 543 var $input_encoding = false; 544 545 /** 546 * @var int Feed Autodiscovery Level 547 * @see SimplePie::set_autodiscovery_level() 548 * @access private 549 */ 550 var $autodiscovery = SIMPLEPIE_LOCATOR_ALL; 551 552 /** 553 * @var string Class used for caching feeds 554 * @see SimplePie::set_cache_class() 555 * @access private 556 */ 557 var $cache_class = 'SimplePie_Cache'; 558 559 /** 560 * @var string Class used for locating feeds 561 * @see SimplePie::set_locator_class() 562 * @access private 563 */ 564 var $locator_class = 'SimplePie_Locator'; 565 566 /** 567 * @var string Class used for parsing feeds 568 * @see SimplePie::set_parser_class() 569 * @access private 570 */ 571 var $parser_class = 'SimplePie_Parser'; 572 573 /** 574 * @var string Class used for fetching feeds 575 * @see SimplePie::set_file_class() 576 * @access private 577 */ 578 var $file_class = 'SimplePie_File'; 579 580 /** 581 * @var string Class used for items 582 * @see SimplePie::set_item_class() 583 * @access private 584 */ 585 var $item_class = 'SimplePie_Item'; 586 587 /** 588 * @var string Class used for authors 589 * @see SimplePie::set_author_class() 590 * @access private 591 */ 592 var $author_class = 'SimplePie_Author'; 593 594 /** 595 * @var string Class used for categories 596 * @see SimplePie::set_category_class() 597 * @access private 598 */ 599 var $category_class = 'SimplePie_Category'; 600 601 /** 602 * @var string Class used for enclosures 603 * @see SimplePie::set_enclosures_class() 604 * @access private 605 */ 606 var $enclosure_class = 'SimplePie_Enclosure'; 607 608 /** 609 * @var string Class used for Media RSS <media:text> captions 610 * @see SimplePie::set_caption_class() 611 * @access private 612 */ 613 var $caption_class = 'SimplePie_Caption'; 614 615 /** 616 * @var string Class used for Media RSS <media:copyright> 617 * @see SimplePie::set_copyright_class() 618 * @access private 619 */ 620 var $copyright_class = 'SimplePie_Copyright'; 621 622 /** 623 * @var string Class used for Media RSS <media:credit> 624 * @see SimplePie::set_credit_class() 625 * @access private 626 */ 627 var $credit_class = 'SimplePie_Credit'; 628 629 /** 630 * @var string Class used for Media RSS <media:rating> 631 * @see SimplePie::set_rating_class() 632 * @access private 633 */ 634 var $rating_class = 'SimplePie_Rating'; 635 636 /** 637 * @var string Class used for Media RSS <media:restriction> 638 * @see SimplePie::set_restriction_class() 639 * @access private 640 */ 641 var $restriction_class = 'SimplePie_Restriction'; 642 643 /** 644 * @var string Class used for content-type sniffing 645 * @see SimplePie::set_content_type_sniffer_class() 646 * @access private 647 */ 648 var $content_type_sniffer_class = 'SimplePie_Content_Type_Sniffer'; 649 650 /** 651 * @var string Class used for item sources. 652 * @see SimplePie::set_source_class() 653 * @access private 654 */ 655 var $source_class = 'SimplePie_Source'; 656 657 /** 658 * @var mixed Set javascript query string parameter (false, or 659 * anything type-cast to false, disables this feature) 660 * @see SimplePie::set_javascript() 661 * @access private 662 */ 663 var $javascript = 'js'; 664 665 /** 666 * @var int Maximum number of feeds to check with autodiscovery 667 * @see SimplePie::set_max_checked_feeds() 668 * @access private 669 */ 670 var $max_checked_feeds = 10; 671 672 /** 673 * @var array All the feeds found during the autodiscovery process 674 * @see SimplePie::get_all_discovered_feeds() 675 * @access private 676 */ 677 var $all_discovered_feeds = array(); 678 679 /** 680 * @var string Web-accessible path to the handler_favicon.php file. 681 * @see SimplePie::set_favicon_handler() 682 * @access private 683 */ 684 var $favicon_handler = ''; 685 686 /** 687 * @var string Web-accessible path to the handler_image.php file. 688 * @see SimplePie::set_image_handler() 689 * @access private 690 */ 691 var $image_handler = ''; 692 693 /** 694 * @var array Stores the URLs when multiple feeds are being initialized. 695 * @see SimplePie::set_feed_url() 696 * @access private 697 */ 698 var $multifeed_url = array(); 699 700 /** 701 * @var array Stores SimplePie objects when multiple feeds initialized. 702 * @access private 703 */ 704 var $multifeed_objects = array(); 705 706 /** 707 * @var array Stores the get_object_vars() array for use with multifeeds. 708 * @see SimplePie::set_feed_url() 709 * @access private 710 */ 711 var $config_settings = null; 712 713 /** 714 * @var integer Stores the number of items to return per-feed with multifeeds. 715 * @see SimplePie::set_item_limit() 716 * @access private 717 */ 718 var $item_limit = 0; 719 720 /** 721 * @var array Stores the default attributes to be stripped by strip_attributes(). 722 * @see SimplePie::strip_attributes() 723 * @access private 724 */ 725 var $strip_attributes = array('bgsound', 'class', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc'); 726 727 /** 728 * @var array Stores the default tags to be stripped by strip_htmltags(). 729 * @see SimplePie::strip_htmltags() 730 * @access private 731 */ 732 var $strip_htmltags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'iframe', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style'); 733 734 /** 735 * The SimplePie class contains feed level data and options 736 * 737 * There are two ways that you can create a new SimplePie object. The first 738 * is by passing a feed URL as a parameter to the SimplePie constructor 739 * (as well as optionally setting the cache location and cache expiry). This 740 * will initialise the whole feed with all of the default settings, and you 741 * can begin accessing methods and properties immediately. 742 * 743 * The second way is to create the SimplePie object with no parameters 744 * at all. This will enable you to set configuration options. After setting 745 * them, you must initialise the feed using $feed->init(). At that point the 746 * object's methods and properties will be available to you. This format is 747 * what is used throughout this documentation. 748 * 749 * @access public 750 * @since 1.0 Preview Release 751 * @param string $feed_url This is the URL you want to parse. 752 * @param string $cache_location This is where you want the cache to be stored. 753 * @param int $cache_duration This is the number of seconds that you want to store the cache file for. 754 */ 755 function SimplePie($feed_url = null, $cache_location = null, $cache_duration = null) 756 { 757 // Other objects, instances created here so we can set options on them 758 $this->sanitize = new SimplePie_Sanitize; 759 760 // Set options if they're passed to the constructor 761 if ($cache_location !== null) 762 { 763 $this->set_cache_location($cache_location); 764 } 765 766 if ($cache_duration !== null) 767 { 768 $this->set_cache_duration($cache_duration); 769 } 770 771 // Only init the script if we're passed a feed URL 772 if ($feed_url !== null) 773 { 774 $this->set_feed_url($feed_url); 775 $this->init(); 776 } 777 } 778 779 /** 780 * Used for converting object to a string 781 */ 782 function __toString() 783 { 784 return md5(serialize($this->data)); 785 } 786 787 /** 788 * Remove items that link back to this before destroying this object 789 */ 790 function __destruct() 791 { 792 if ((version_compare(PHP_VERSION, '5.3', '<') || !gc_enabled()) && !ini_get('zend.ze1_compatibility_mode')) 793 { 794 if (!empty($this->data['items'])) 795 { 796 foreach ($this->data['items'] as $item) 797 { 798 $item->__destruct(); 799 } 800 unset($item, $this->data['items']); 801 } 802 if (!empty($this->data['ordered_items'])) 803 { 804 foreach ($this->data['ordered_items'] as $item) 805 { 806 $item->__destruct(); 807 } 808 unset($item, $this->data['ordered_items']); 809 } 810 } 811 } 812 813 /** 814 * Force the given data/URL to be treated as a feed no matter what it 815 * appears like 816 * 817 * @access public 818 * @since 1.1 819 * @param bool $enable Force the given data/URL to be treated as a feed 820 */ 821 function force_feed($enable = false) 822 { 823 $this->force_feed = (bool) $enable; 824 } 825 826 /** 827 * This is the URL of the feed you want to parse. 828 * 829 * This allows you to enter the URL of the feed you want to parse, or the 830 * website you want to try to use auto-discovery on. This takes priority 831 * over any set raw data. 832 * 833 * You can set multiple feeds to mash together by passing an array instead 834 * of a string for the $url. Remember that with each additional feed comes 835 * additional processing and resources. 836 * 837 * @access public 838 * @since 1.0 Preview Release 839 * @param mixed $url This is the URL (or array of URLs) that you want to parse. 840 * @see SimplePie::set_raw_data() 841 */ 842 function set_feed_url($url) 843 { 844 if (is_array($url)) 845 { 846 $this->multifeed_url = array(); 847 foreach ($url as $value) 848 { 849 $this->multifeed_url[] = SimplePie_Misc::fix_protocol($value, 1); 850 } 851 } 852 else 853 { 854 $this->feed_url = SimplePie_Misc::fix_protocol($url, 1); 855 } 856 } 857 858 /** 859 * Provides an instance of SimplePie_File to use as a feed 860 * 861 * @access public 862 * @param object &$file Instance of SimplePie_File (or subclass) 863 * @return bool True on success, false on failure 864 */ 865 function set_file(&$file) 866 { 867 if (is_a($file, 'SimplePie_File')) 868 { 869 $this->feed_url = $file->url; 870 $this->file =& $file; 871 return true; 872 } 873 return false; 874 } 875 876 /** 877 * Allows you to use a string of RSS/Atom data instead of a remote feed. 878 * 879 * If you have a feed available as a string in PHP, you can tell SimplePie 880 * to parse that data string instead of a remote feed. Any set feed URL 881 * takes precedence. 882 * 883 * @access public 884 * @since 1.0 Beta 3 885 * @param string $data RSS or Atom data as a string. 886 * @see SimplePie::set_feed_url() 887 */ 888 function set_raw_data($data) 889 { 890 $this->raw_data = $data; 891 } 892 893 /** 894 * Allows you to override the default timeout for fetching remote feeds. 895 * 896 * This allows you to change the maximum time the feed's server to respond 897 * and send the feed back. 898 * 899 * @access public 900 * @since 1.0 Beta 3 901 * @param int $timeout The maximum number of seconds to spend waiting to retrieve a feed. 902 */ 903 function set_timeout($timeout = 10) 904 { 905 $this->timeout = (int) $timeout; 906 } 907 908 /** 909 * Forces SimplePie to use fsockopen() instead of the preferred cURL 910 * functions. 911 * 912 * @access public 913 * @since 1.0 Beta 3 914 * @param bool $enable Force fsockopen() to be used 915 */ 916 function force_fsockopen($enable = false) 917 { 918 $this->force_fsockopen = (bool) $enable; 919 } 920 921 /** 922 * Outputs the raw XML content of the feed, after it has gone through 923 * SimplePie's filters. 924 * 925 * Used only for debugging, this function will output the XML content as 926 * text/xml. When SimplePie reads in a feed, it does a bit of cleaning up 927 * before trying to parse it. Many parts of the feed are re-written in 928 * memory, and in the end, you have a parsable feed. XML dump shows you the 929 * actual XML that SimplePie tries to parse, which may or may not be very 930 * different from the original feed. 931 * 932 * @access public 933 * @since 1.0 Preview Release 934 * @param bool $enable Enable XML dump 935 */ 936 function enable_xml_dump($enable = false) 937 { 938 $this->xml_dump = (bool) $enable; 939 } 940 941 /** 942 * Enables/disables caching in SimplePie. 943 * 944 * This option allows you to disable caching all-together in SimplePie. 945 * However, disabling the cache can lead to longer load times. 946 * 947 * @access public 948 * @since 1.0 Preview Release 949 * @param bool $enable Enable caching 950 */ 951 function enable_cache($enable = true) 952 { 953 $this->cache = (bool) $enable; 954 } 955 956 /** 957 * Set the length of time (in seconds) that the contents of a feed 958 * will be cached. 959 * 960 * @access public 961 * @param int $seconds The feed content cache duration. 962 */ 963 function set_cache_duration($seconds = 3600) 964 { 965 $this->cache_duration = (int) $seconds; 966 } 967 968 /** 969 * Set the length of time (in seconds) that the autodiscovered feed 970 * URL will be cached. 971 * 972 * @access public 973 * @param int $seconds The autodiscovered feed URL cache duration. 974 */ 975 function set_autodiscovery_cache_duration($seconds = 604800) 976 { 977 $this->autodiscovery_cache_duration = (int) $seconds; 978 } 979 980 /** 981 * Set the file system location where the cached files should be stored. 982 * 983 * @access public 984 * @param string $location The file system location. 985 */ 986 function set_cache_location($location = './cache') 987 { 988 $this->cache_location = (string) $location; 989 } 990 991 /** 992 * Determines whether feed items should be sorted into reverse chronological order. 993 * 994 * @access public 995 * @param bool $enable Sort as reverse chronological order. 996 */ 997 function enable_order_by_date($enable = true) 998 { 999 $this->order_by_date = (bool) $enable; 1000 } 1001 1002 /** 1003 * Allows you to override the character encoding reported by the feed. 1004 * 1005 * @access public 1006 * @param string $encoding Character encoding. 1007 */ 1008 function set_input_encoding($encoding = false) 1009 { 1010 if ($encoding) 1011 { 1012 $this->input_encoding = (string) $encoding; 1013 } 1014 else 1015 { 1016 $this->input_encoding = false; 1017 } 1018 } 1019 1020 /** 1021 * Set how much feed autodiscovery to do 1022 * 1023 * @access public 1024 * @see SIMPLEPIE_LOCATOR_NONE 1025 * @see SIMPLEPIE_LOCATOR_AUTODISCOVERY 1026 * @see SIMPLEPIE_LOCATOR_LOCAL_EXTENSION 1027 * @see SIMPLEPIE_LOCATOR_LOCAL_BODY 1028 * @see SIMPLEPIE_LOCATOR_REMOTE_EXTENSION 1029 * @see SIMPLEPIE_LOCATOR_REMOTE_BODY 1030 * @see SIMPLEPIE_LOCATOR_ALL 1031 * @param int $level Feed Autodiscovery Level (level can be a 1032 * combination of the above constants, see bitwise OR operator) 1033 */ 1034 function set_autodiscovery_level($level = SIMPLEPIE_LOCATOR_ALL) 1035 { 1036 $this->autodiscovery = (int) $level; 1037 } 1038 1039 /** 1040 * Allows you to change which class SimplePie uses for caching. 1041 * Useful when you are overloading or extending SimplePie's default classes. 1042 * 1043 * @access public 1044 * @param string $class Name of custom class. 1045 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1046 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1047 */ 1048 function set_cache_class($class = 'SimplePie_Cache') 1049 { 1050 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Cache')) 1051 { 1052 $this->cache_class = $class; 1053 return true; 1054 } 1055 return false; 1056 } 1057 1058 /** 1059 * Allows you to change which class SimplePie uses for auto-discovery. 1060 * Useful when you are overloading or extending SimplePie's default classes. 1061 * 1062 * @access public 1063 * @param string $class Name of custom class. 1064 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1065 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1066 */ 1067 function set_locator_class($class = 'SimplePie_Locator') 1068 { 1069 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Locator')) 1070 { 1071 $this->locator_class = $class; 1072 return true; 1073 } 1074 return false; 1075 } 1076 1077 /** 1078 * Allows you to change which class SimplePie uses for XML parsing. 1079 * Useful when you are overloading or extending SimplePie's default classes. 1080 * 1081 * @access public 1082 * @param string $class Name of custom class. 1083 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1084 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1085 */ 1086 function set_parser_class($class = 'SimplePie_Parser') 1087 { 1088 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Parser')) 1089 { 1090 $this->parser_class = $class; 1091 return true; 1092 } 1093 return false; 1094 } 1095 1096 /** 1097 * Allows you to change which class SimplePie uses for remote file fetching. 1098 * Useful when you are overloading or extending SimplePie's default classes. 1099 * 1100 * @access public 1101 * @param string $class Name of custom class. 1102 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1103 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1104 */ 1105 function set_file_class($class = 'SimplePie_File') 1106 { 1107 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_File')) 1108 { 1109 $this->file_class = $class; 1110 return true; 1111 } 1112 return false; 1113 } 1114 1115 /** 1116 * Allows you to change which class SimplePie uses for data sanitization. 1117 * Useful when you are overloading or extending SimplePie's default classes. 1118 * 1119 * @access public 1120 * @param string $class Name of custom class. 1121 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1122 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1123 */ 1124 function set_sanitize_class($class = 'SimplePie_Sanitize') 1125 { 1126 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Sanitize')) 1127 { 1128 $this->sanitize = new $class(); 1129 return true; 1130 } 1131 return false; 1132 } 1133 1134 /** 1135 * Allows you to change which class SimplePie uses for handling feed items. 1136 * Useful when you are overloading or extending SimplePie's default classes. 1137 * 1138 * @access public 1139 * @param string $class Name of custom class. 1140 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1141 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1142 */ 1143 function set_item_class($class = 'SimplePie_Item') 1144 { 1145 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Item')) 1146 { 1147 $this->item_class = $class; 1148 return true; 1149 } 1150 return false; 1151 } 1152 1153 /** 1154 * Allows you to change which class SimplePie uses for handling author data. 1155 * Useful when you are overloading or extending SimplePie's default classes. 1156 * 1157 * @access public 1158 * @param string $class Name of custom class. 1159 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1160 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1161 */ 1162 function set_author_class($class = 'SimplePie_Author') 1163 { 1164 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Author')) 1165 { 1166 $this->author_class = $class; 1167 return true; 1168 } 1169 return false; 1170 } 1171 1172 /** 1173 * Allows you to change which class SimplePie uses for handling category data. 1174 * Useful when you are overloading or extending SimplePie's default classes. 1175 * 1176 * @access public 1177 * @param string $class Name of custom class. 1178 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1179 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1180 */ 1181 function set_category_class($class = 'SimplePie_Category') 1182 { 1183 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Category')) 1184 { 1185 $this->category_class = $class; 1186 return true; 1187 } 1188 return false; 1189 } 1190 1191 /** 1192 * Allows you to change which class SimplePie uses for feed enclosures. 1193 * Useful when you are overloading or extending SimplePie's default classes. 1194 * 1195 * @access public 1196 * @param string $class Name of custom class. 1197 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1198 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1199 */ 1200 function set_enclosure_class($class = 'SimplePie_Enclosure') 1201 { 1202 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Enclosure')) 1203 { 1204 $this->enclosure_class = $class; 1205 return true; 1206 } 1207 return false; 1208 } 1209 1210 /** 1211 * Allows you to change which class SimplePie uses for <media:text> captions 1212 * Useful when you are overloading or extending SimplePie's default classes. 1213 * 1214 * @access public 1215 * @param string $class Name of custom class. 1216 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1217 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1218 */ 1219 function set_caption_class($class = 'SimplePie_Caption') 1220 { 1221 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Caption')) 1222 { 1223 $this->caption_class = $class; 1224 return true; 1225 } 1226 return false; 1227 } 1228 1229 /** 1230 * Allows you to change which class SimplePie uses for <media:copyright> 1231 * Useful when you are overloading or extending SimplePie's default classes. 1232 * 1233 * @access public 1234 * @param string $class Name of custom class. 1235 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1236 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1237 */ 1238 function set_copyright_class($class = 'SimplePie_Copyright') 1239 { 1240 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Copyright')) 1241 { 1242 $this->copyright_class = $class; 1243 return true; 1244 } 1245 return false; 1246 } 1247 1248 /** 1249 * Allows you to change which class SimplePie uses for <media:credit> 1250 * Useful when you are overloading or extending SimplePie's default classes. 1251 * 1252 * @access public 1253 * @param string $class Name of custom class. 1254 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1255 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1256 */ 1257 function set_credit_class($class = 'SimplePie_Credit') 1258 { 1259 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Credit')) 1260 { 1261 $this->credit_class = $class; 1262 return true; 1263 } 1264 return false; 1265 } 1266 1267 /** 1268 * Allows you to change which class SimplePie uses for <media:rating> 1269 * Useful when you are overloading or extending SimplePie's default classes. 1270 * 1271 * @access public 1272 * @param string $class Name of custom class. 1273 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1274 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1275 */ 1276 function set_rating_class($class = 'SimplePie_Rating') 1277 { 1278 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Rating')) 1279 { 1280 $this->rating_class = $class; 1281 return true; 1282 } 1283 return false; 1284 } 1285 1286 /** 1287 * Allows you to change which class SimplePie uses for <media:restriction> 1288 * Useful when you are overloading or extending SimplePie's default classes. 1289 * 1290 * @access public 1291 * @param string $class Name of custom class. 1292 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1293 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1294 */ 1295 function set_restriction_class($class = 'SimplePie_Restriction') 1296 { 1297 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Restriction')) 1298 { 1299 $this->restriction_class = $class; 1300 return true; 1301 } 1302 return false; 1303 } 1304 1305 /** 1306 * Allows you to change which class SimplePie uses for content-type sniffing. 1307 * Useful when you are overloading or extending SimplePie's default classes. 1308 * 1309 * @access public 1310 * @param string $class Name of custom class. 1311 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1312 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1313 */ 1314 function set_content_type_sniffer_class($class = 'SimplePie_Content_Type_Sniffer') 1315 { 1316 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Content_Type_Sniffer')) 1317 { 1318 $this->content_type_sniffer_class = $class; 1319 return true; 1320 } 1321 return false; 1322 } 1323 1324 /** 1325 * Allows you to change which class SimplePie uses item sources. 1326 * Useful when you are overloading or extending SimplePie's default classes. 1327 * 1328 * @access public 1329 * @param string $class Name of custom class. 1330 * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation 1331 * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation 1332 */ 1333 function set_source_class($class = 'SimplePie_Source') 1334 { 1335 if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Source')) 1336 { 1337 $this->source_class = $class; 1338 return true; 1339 } 1340 return false; 1341 } 1342 1343 /** 1344 * Allows you to override the default user agent string. 1345 * 1346 * @access public 1347 * @param string $ua New user agent string. 1348 */ 1349 function set_useragent($ua = SIMPLEPIE_USERAGENT) 1350 { 1351 $this->useragent = (string) $ua; 1352 } 1353 1354 /** 1355 * Set callback function to create cache filename with 1356 * 1357 * @access public 1358 * @param mixed $function Callback function 1359 */ 1360 function set_cache_name_function($function = 'md5') 1361 { 1362 if (is_callable($function)) 1363 { 1364 $this->cache_name_function = $function; 1365 } 1366 } 1367 1368 /** 1369 * Set javascript query string parameter 1370 * 1371 * @access public 1372 * @param mixed $get Javascript query string parameter 1373 */ 1374 function set_javascript($get = 'js') 1375 { 1376 if ($get) 1377 { 1378 $this->javascript = (string) $get; 1379 } 1380 else 1381 { 1382 $this->javascript = false; 1383 } 1384 } 1385 1386 /** 1387 * Set options to make SP as fast as possible. Forgoes a 1388 * substantial amount of data sanitization in favor of speed. 1389 * 1390 * @access public 1391 * @param bool $set Whether to set them or not 1392 */ 1393 function set_stupidly_fast($set = false) 1394 { 1395 if ($set) 1396 { 1397 $this->enable_order_by_date(false); 1398 $this->remove_div(false); 1399 $this->strip_comments(false); 1400 $this->strip_htmltags(false); 1401 $this->strip_attributes(false); 1402 $this->set_image_handler(false); 1403 } 1404 } 1405 1406 /** 1407 * Set maximum number of feeds to check with autodiscovery 1408 * 1409 * @access public 1410 * @param int $max Maximum number of feeds to check 1411 */ 1412 function set_max_checked_feeds($max = 10) 1413 { 1414 $this->max_checked_feeds = (int) $max; 1415 } 1416 1417 function remove_div($enable = true) 1418 { 1419 $this->sanitize->remove_div($enable); 1420 } 1421 1422 function strip_htmltags($tags = '', $encode = null) 1423 { 1424 if ($tags === '') 1425 { 1426 $tags = $this->strip_htmltags; 1427 } 1428 $this->sanitize->strip_htmltags($tags); 1429 if ($encode !== null) 1430 { 1431 $this->sanitize->encode_instead_of_strip($tags); 1432 } 1433 } 1434 1435 function encode_instead_of_strip($enable = true) 1436 { 1437 $this->sanitize->encode_instead_of_strip($enable); 1438 } 1439 1440 function strip_attributes($attribs = '') 1441 { 1442 if ($attribs === '') 1443 { 1444 $attribs = $this->strip_attributes; 1445 } 1446 $this->sanitize->strip_attributes($attribs); 1447 } 1448 1449 function set_output_encoding($encoding = 'UTF-8') 1450 { 1451 $this->sanitize->set_output_encoding($encoding); 1452 } 1453 1454 function strip_comments($strip = false) 1455 { 1456 $this->sanitize->strip_comments($strip); 1457 } 1458 1459 /** 1460 * Set element/attribute key/value pairs of HTML attributes 1461 * containing URLs that need to be resolved relative to the feed 1462 * 1463 * @access public 1464 * @since 1.0 1465 * @param array $element_attribute Element/attribute key/value pairs 1466 */ 1467 function set_url_replacements($element_attribute = array('a' => 'href', 'area' => 'href', 'blockquote' => 'cite', 'del' => 'cite', 'form' => 'action', 'img' => array('longdesc', 'src'), 'input' => 'src', 'ins' => 'cite', 'q' => 'cite')) 1468 { 1469 $this->sanitize->set_url_replacements($element_attribute); 1470 } 1471 1472 /** 1473 * Set the handler to enable the display of cached favicons. 1474 * 1475 * @access public 1476 * @param str $page Web-accessible path to the handler_favicon.php file. 1477 * @param str $qs The query string that the value should be passed to. 1478 */ 1479 function set_favicon_handler($page = false, $qs = 'i') 1480 { 1481 if ($page !== false) 1482 { 1483 $this->favicon_handler = $page . '?' . $qs . '='; 1484 } 1485 else 1486 { 1487 $this->favicon_handler = ''; 1488 } 1489 } 1490 1491 /** 1492 * Set the handler to enable the display of cached images. 1493 * 1494 * @access public 1495 * @param str $page Web-accessible path to the handler_image.php file. 1496 * @param str $qs The query string that the value should be passed to. 1497 */ 1498 function set_image_handler($page = false, $qs = 'i') 1499 { 1500 if ($page !== false) 1501 { 1502 $this->sanitize->set_image_handler($page . '?' . $qs . '='); 1503 } 1504 else 1505 { 1506 $this->image_handler = ''; 1507 } 1508 } 1509 1510 /** 1511 * Set the limit for items returned per-feed with multifeeds. 1512 * 1513 * @access public 1514 * @param integer $limit The maximum number of items to return. 1515 */ 1516 function set_item_limit($limit = 0) 1517 { 1518 $this->item_limit = (int) $limit; 1519 } 1520 1521 function init() 1522 { 1523 // Check absolute bare minimum requirements. 1524 if ((function_exists('version_compare') && version_compare(PHP_VERSION, '4.3.0', '<')) || !extension_loaded('xml') || !extension_loaded('pcre')) 1525 { 1526 return false; 1527 } 1528 // Then check the xml extension is sane (i.e., libxml 2.7.x issue on PHP < 5.2.9 and libxml 2.7.0 to 2.7.2 on any version) if we don't have xmlreader. 1529 elseif (!extension_loaded('xmlreader')) 1530 { 1531 static $xml_is_sane = null; 1532 if ($xml_is_sane === null) 1533 { 1534 $parser_check = xml_parser_create(); 1535 xml_parse_into_struct($parser_check, '<foo>&</foo>', $values); 1536 xml_parser_free($parser_check); 1537 $xml_is_sane = isset($values[0]['value']); 1538 } 1539 if (!$xml_is_sane) 1540 { 1541 return false; 1542 } 1543 } 1544 1545 if (isset($_GET[$this->javascript])) 1546 { 1547 SimplePie_Misc::output_javascript(); 1548 exit; 1549 } 1550 1551 // Pass whatever was set with config options over to the sanitizer. 1552 $this->sanitize->pass_cache_data($this->cache, $this->cache_location, $this->cache_name_function, $this->cache_class); 1553 $this->sanitize->pass_file_data($this->file_class, $this->timeout, $this->useragent, $this->force_fsockopen); 1554 1555 if ($this->feed_url !== null || $this->raw_data !== null) 1556 { 1557 $this->error = null; 1558 $this->data = array(); 1559 $this->multifeed_objects = array(); 1560 $cache = false; 1561 1562 if ($this->feed_url !== null) 1563 { 1564 $parsed_feed_url = SimplePie_Misc::parse_url($this->feed_url); 1565 // Decide whether to enable caching 1566 if ($this->cache && $parsed_feed_url['scheme'] !== '') 1567 { 1568 $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, call_user_func($this->cache_name_function, $this->feed_url), 'spc'); 1569 } 1570 // If it's enabled and we don't want an XML dump, use the cache 1571 if ($cache && !$this->xml_dump) 1572 { 1573 // Load the Cache 1574 $this->data = $cache->load(); 1575 if (!empty($this->data)) 1576 { 1577 // If the cache is for an outdated build of SimplePie 1578 if (!isset($this->data['build']) || $this->data['build'] !== SIMPLEPIE_BUILD) 1579 { 1580 $cache->unlink(); 1581 $this->data = array(); 1582 } 1583 // If we've hit a collision just rerun it with caching disabled 1584 elseif (isset($this->data['url']) && $this->data['url'] !== $this->feed_url) 1585 { 1586 $cache = false; 1587 $this->data = array(); 1588 } 1589 // If we've got a non feed_url stored (if the page isn't actually a feed, or is a redirect) use that URL. 1590 elseif (isset($this->data['feed_url'])) 1591 { 1592 // If the autodiscovery cache is still valid use it. 1593 if ($cache->mtime() + $this->autodiscovery_cache_duration > time()) 1594 { 1595 // Do not need to do feed autodiscovery yet. 1596 if ($this->data['feed_url'] === $this->data['url']) 1597 { 1598 $cache->unlink(); 1599 $this->data = array(); 1600 } 1601 else 1602 { 1603 $this->set_feed_url($this->data['feed_url']); 1604 return $this->init(); 1605 } 1606 } 1607 } 1608 // Check if the cache has been updated 1609 elseif ($cache->mtime() + $this->cache_duration < time()) 1610 { 1611 // If we have last-modified and/or etag set 1612 if (isset($this->data['headers']['last-modified']) || isset($this->data['headers']['etag'])) 1613 { 1614 $headers = array(); 1615 if (isset($this->data['headers']['last-modified'])) 1616 { 1617 $headers['if-modified-since'] = $this->data['headers']['last-modified']; 1618 } 1619 if (isset($this->data['headers']['etag'])) 1620 { 1621 $headers['if-none-match'] = '"' . $this->data['headers']['etag'] . '"'; 1622 } 1623 $file = new $this->file_class($this->feed_url, $this->timeout/10, 5, $headers, $this->useragent, $this->force_fsockopen); 1624 if ($file->success) 1625 { 1626 if ($file->status_code === 304) 1627 { 1628 $cache->touch(); 1629 return true; 1630 } 1631 else 1632 { 1633 $headers = $file->headers; 1634 } 1635 } 1636 else 1637 { 1638 unset($file); 1639 } 1640 } 1641 } 1642 // If the cache is still valid, just return true 1643 else 1644 { 1645 return true; 1646 } 1647 } 1648 // If the cache is empty, delete it 1649 else 1650 { 1651 $cache->unlink(); 1652 $this->data = array(); 1653 } 1654 } 1655 // If we don't already have the file (it'll only exist if we've opened it to check if the cache has been modified), open it. 1656 if (!isset($file)) 1657 { 1658 if (is_a($this->file, 'SimplePie_File') && $this->file->url === $this->feed_url) 1659 { 1660 $file =& $this->file; 1661 } 1662 else 1663 { 1664 $file = new $this->file_class($this->feed_url, $this->timeout, 5, null, $this->useragent, $this->force_fsockopen); 1665 } 1666 } 1667 // If the file connection has an error, set SimplePie::error to that and quit 1668 if (!$file->success && !($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300))) 1669 { 1670 $this->error = $file->error; 1671 if (!empty($this->data)) 1672 { 1673 return true; 1674 } 1675 else 1676 { 1677 return false; 1678 } 1679 } 1680 1681 if (!$this->force_feed) 1682 { 1683 // Check if the supplied URL is a feed, if it isn't, look for it. 1684 $locate = new $this->locator_class($file, $this->timeout, $this->useragent, $this->file_class, $this->max_checked_feeds, $this->content_type_sniffer_class); 1685 if (!$locate->is_feed($file)) 1686 { 1687 // We need to unset this so that if SimplePie::set_file() has been called that object is untouched 1688 unset($file); 1689 if ($file = $locate->find($this->autodiscovery, $this->all_discovered_feeds)) 1690 { 1691 if ($cache) 1692 { 1693 $this->data = array('url' => $this->feed_url, 'feed_url' => $file->url, 'build' => SIMPLEPIE_BUILD); 1694 if (!$cache->save($this)) 1695 { 1696 trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING); 1697 } 1698 $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, call_user_func($this->cache_name_function, $file->url), 'spc'); 1699 } 1700 $this->feed_url = $file->url; 1701 } 1702 else 1703 { 1704 $this->error = "A feed could not be found at $this->feed_url. A feed with an invalid mime type may fall victim to this error, or " . SIMPLEPIE_NAME . " was unable to auto-discover it.. Use force_feed() if you are certain this URL is a real feed."; 1705 SimplePie_Misc::error($this->error, E_USER_NOTICE, __FILE__, __LINE__); 1706 return false; 1707 } 1708 } 1709 $locate = null; 1710 } 1711 1712 $headers = $file->headers; 1713 $data = $file->body; 1714 $sniffer = new $this->content_type_sniffer_class($file); 1715 $sniffed = $sniffer->get_type(); 1716 } 1717 else 1718 { 1719 $data = $this->raw_data; 1720 } 1721 1722 // Set up array of possible encodings 1723 $encodings = array(); 1724 1725 // First check to see if input has been overridden. 1726 if ($this->input_encoding !== false) 1727 { 1728 $encodings[] = $this->input_encoding; 1729 } 1730 1731 $application_types = array('application/xml', 'application/xml-dtd', 'application/xml-external-parsed-entity'); 1732 $text_types = array('text/xml', 'text/xml-external-parsed-entity'); 1733 1734 // RFC 3023 (only applies to sniffed content) 1735 if (isset($sniffed)) 1736 { 1737 if (in_array($sniffed, $application_types) || substr($sniffed, 0, 12) === 'application/' && substr($sniffed, -4) === '+xml') 1738 { 1739 if (isset($headers['content-type']) && preg_match('/;\x20?charset=([^;]*)/i', $headers['content-type'], $charset)) 1740 { 1741 $encodings[] = strtoupper($charset[1]); 1742 } 1743 $encodings = array_merge($encodings, SimplePie_Misc::xml_encoding($data)); 1744 $encodings[] = 'UTF-8'; 1745 } 1746 elseif (in_array($sniffed, $text_types) || substr($sniffed, 0, 5) === 'text/' && substr($sniffed, -4) === '+xml') 1747 { 1748 if (isset($headers['content-type']) && preg_match('/;\x20?charset=([^;]*)/i', $headers['content-type'], $charset)) 1749 { 1750 $encodings[] = $charset[1]; 1751 } 1752 $encodings[] = 'US-ASCII'; 1753 } 1754 // Text MIME-type default 1755 elseif (substr($sniffed, 0, 5) === 'text/') 1756 { 1757 $encodings[] = 'US-ASCII'; 1758 } 1759 } 1760 1761 // Fallback to XML 1.0 Appendix F.1/UTF-8/ISO-8859-1 1762 $encodings = array_merge($encodings, SimplePie_Misc::xml_encoding($data)); 1763 $encodings[] = 'UTF-8'; 1764 $encodings[] = 'ISO-8859-1'; 1765 1766 // There's no point in trying an encoding twice 1767 $encodings = array_unique($encodings); 1768 1769 // If we want the XML, just output that with the most likely encoding and quit 1770 if ($this->xml_dump) 1771 { 1772 header('Content-type: text/xml; charset=' . $encodings[0]); 1773 echo $data; 1774 exit; 1775 } 1776 1777 // Loop through each possible encoding, till we return something, or run out of possibilities 1778 foreach ($encodings as $encoding) 1779 { 1780 // Change the encoding to UTF-8 (as we always use UTF-8 internally) 1781 if ($utf8_data = SimplePie_Misc::change_encoding($data, $encoding, 'UTF-8')) 1782 { 1783 // Create new parser 1784 $parser = new $this->parser_class(); 1785 1786 // If it's parsed fine 1787 if ($parser->parse($utf8_data, 'UTF-8')) 1788 { 1789 $this->data = $parser->get_data(); 1790 if ($this->get_type() & ~SIMPLEPIE_TYPE_NONE) 1791 { 1792 if (isset($headers)) 1793 { 1794 $this->data['headers'] = $headers; 1795 } 1796 $this->data['build'] = SIMPLEPIE_BUILD; 1797 1798 // Cache the file if caching is enabled 1799 if ($cache && !$cache->save($this)) 1800 { 1801 trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING); 1802 } 1803 return true; 1804 } 1805 else 1806 { 1807 $this->error = "A feed could not be found at $this->feed_url. This does not appear to be a valid RSS or Atom feed."; 1808 SimplePie_Misc::error($this->error, E_USER_NOTICE, __FILE__, __LINE__); 1809 return false; 1810 } 1811 } 1812 } 1813 } 1814 if (isset($parser)) 1815 { 1816 // We have an error, just set SimplePie_Misc::error to it and quit 1817 $this->error = sprintf('This XML document is invalid, likely due to invalid characters. XML error: %s at line %d, column %d', $parser->get_error_string(), $parser->get_current_line(), $parser->get_current_column()); 1818 } 1819 else 1820 { 1821 $this->error = 'The data could not be converted to UTF-8. You MUST have either the iconv or mbstring extension installed. Upgrading to PHP 5.x (which includes iconv) is highly recommended.'; 1822 } 1823 SimplePie_Misc::error($this->error, E_USER_NOTICE, __FILE__, __LINE__); 1824 return false; 1825 } 1826 elseif (!empty($this->multifeed_url)) 1827 { 1828 $i = 0; 1829 $success = 0; 1830 $this->multifeed_objects = array(); 1831 foreach ($this->multifeed_url as $url) 1832 { 1833 if (SIMPLEPIE_PHP5) 1834 { 1835 // This keyword needs to defy coding standards for PHP4 compatibility 1836 $this->multifeed_objects[$i] = clone($this); 1837 } 1838 else 1839 { 1840 $this->multifeed_objects[$i] = $this; 1841 } 1842 $this->multifeed_objects[$i]->set_feed_url($url); 1843 $success |= $this->multifeed_objects[$i]->init(); 1844 $i++; 1845 } 1846 return (bool) $success; 1847 } 1848 else 1849 { 1850 return false; 1851 } 1852 } 1853 1854 /** 1855 * Return the error message for the occured error 1856 * 1857 * @access public 1858 * @return string Error message 1859 */ 1860 function error() 1861 { 1862 return $this->error; 1863 } 1864 1865 function get_encoding() 1866 { 1867 return $this->sanitize->output_encoding; 1868 } 1869 1870 function handle_content_type($mime = 'text/html') 1871 { 1872 if (!headers_sent()) 1873 { 1874 $header = "Content-type: $mime;"; 1875 if ($this->get_encoding()) 1876 { 1877 $header .= ' charset=' . $this->get_encoding(); 1878 } 1879 else 1880 { 1881 $header .= ' charset=UTF-8'; 1882 } 1883 header($header); 1884 } 1885 } 1886 1887 function get_type() 1888 { 1889 if (!isset($this->data['type'])) 1890 { 1891 $this->data['type'] = SIMPLEPIE_TYPE_ALL; 1892 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'])) 1893 { 1894 $this->data['type'] &= SIMPLEPIE_TYPE_ATOM_10; 1895 } 1896 elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'])) 1897 { 1898 $this->data['type'] &= SIMPLEPIE_TYPE_ATOM_03; 1899 } 1900 elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'])) 1901 { 1902 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['channel']) 1903 || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['image']) 1904 || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item']) 1905 || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['textinput'])) 1906 { 1907 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_10; 1908 } 1909 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['channel']) 1910 || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['image']) 1911 || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item']) 1912 || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['textinput'])) 1913 { 1914 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_090; 1915 } 1916 } 1917 elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'])) 1918 { 1919 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_ALL; 1920 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['attribs']['']['version'])) 1921 { 1922 switch (trim($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['attribs']['']['version'])) 1923 { 1924 case '0.91': 1925 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091; 1926 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['skiphours']['hour'][0]['data'])) 1927 { 1928 switch (trim($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['skiphours']['hour'][0]['data'])) 1929 { 1930 case '0': 1931 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091_NETSCAPE; 1932 break; 1933 1934 case '24': 1935 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091_USERLAND; 1936 break; 1937 } 1938 } 1939 break; 1940 1941 case '0.92': 1942 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_092; 1943 break; 1944 1945 case '0.93': 1946 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_093; 1947 break; 1948 1949 case '0.94': 1950 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_094; 1951 break; 1952 1953 case '2.0': 1954 $this->data['type'] &= SIMPLEPIE_TYPE_RSS_20; 1955 break; 1956 } 1957 } 1958 } 1959 else 1960 { 1961 $this->data['type'] = SIMPLEPIE_TYPE_NONE; 1962 } 1963 } 1964 return $this->data['type']; 1965 } 1966 1967 /** 1968 * Returns the URL for the favicon of the feed's website. 1969 * 1970 * @todo Cache atom:icon 1971 * @access public 1972 * @since 1.0 1973 */ 1974 function get_favicon() 1975 { 1976 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon')) 1977 { 1978 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 1979 } 1980 elseif (($url = $this->get_link()) !== null && preg_match('/^http(s)?:\/\//i', $url)) 1981 { 1982 $favicon = SimplePie_Misc::absolutize_url('/favicon.ico', $url); 1983 1984 if ($this->cache && $this->favicon_handler) 1985 { 1986 $favicon_filename = call_user_func($this->cache_name_function, $favicon); 1987 $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, $favicon_filename, 'spi'); 1988 1989 if ($cache->load()) 1990 { 1991 return $this->sanitize($this->favicon_handler . $favicon_filename, SIMPLEPIE_CONSTRUCT_IRI); 1992 } 1993 else 1994 { 1995 $file = new $this->file_class($favicon, $this->timeout / 10, 5, array('X-FORWARDED-FOR' => $_SERVER['REMOTE_ADDR']), $this->useragent, $this->force_fsockopen); 1996 1997 if ($file->success && ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300)) && strlen($file->body) > 0) 1998 { 1999 $sniffer = new $this->content_type_sniffer_class($file); 2000 if (substr($sniffer->get_type(), 0, 6) === 'image/') 2001 { 2002 if ($cache->save(array('headers' => $file->headers, 'body' => $file->body))) 2003 { 2004 return $this->sanitize($this->favicon_handler . $favicon_filename, SIMPLEPIE_CONSTRUCT_IRI); 2005 } 2006 else 2007 { 2008 trigger_error("$cache->name is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING); 2009 return $this->sanitize($favicon, SIMPLEPIE_CONSTRUCT_IRI); 2010 } 2011 } 2012 // not an image 2013 else 2014 { 2015 return false; 2016 } 2017 } 2018 } 2019 } 2020 else 2021 { 2022 return $this->sanitize($favicon, SIMPLEPIE_CONSTRUCT_IRI); 2023 } 2024 } 2025 return false; 2026 } 2027 2028 /** 2029 * @todo If we have a perm redirect we should return the new URL 2030 * @todo When we make the above change, let's support <itunes:new-feed-url> as well 2031 * @todo Also, |atom:link|@rel=self 2032 */ 2033 function subscribe_url() 2034 { 2035 if ($this->feed_url !== null) 2036 { 2037 return $this->sanitize($this->feed_url, SIMPLEPIE_CONSTRUCT_IRI); 2038 } 2039 else 2040 { 2041 return null; 2042 } 2043 } 2044 2045 function subscribe_feed() 2046 { 2047 if ($this->feed_url !== null) 2048 { 2049 return $this->sanitize(SimplePie_Misc::fix_protocol($this->feed_url, 2), SIMPLEPIE_CONSTRUCT_IRI); 2050 } 2051 else 2052 { 2053 return null; 2054 } 2055 } 2056 2057 function subscribe_outlook() 2058 { 2059 if ($this->feed_url !== null) 2060 { 2061 return $this->sanitize('outlook' . SimplePie_Misc::fix_protocol($this->feed_url, 2), SIMPLEPIE_CONSTRUCT_IRI); 2062 } 2063 else 2064 { 2065 return null; 2066 } 2067 } 2068 2069 function subscribe_podcast() 2070 { 2071 if ($this->feed_url !== null) 2072 { 2073 return $this->sanitize(SimplePie_Misc::fix_protocol($this->feed_url, 3), SIMPLEPIE_CONSTRUCT_IRI); 2074 } 2075 else 2076 { 2077 return null; 2078 } 2079 } 2080 2081 function subscribe_itunes() 2082 { 2083 if ($this->feed_url !== null) 2084 { 2085 return $this->sanitize(SimplePie_Misc::fix_protocol($this->feed_url, 4), SIMPLEPIE_CONSTRUCT_IRI); 2086 } 2087 else 2088 { 2089 return null; 2090 } 2091 } 2092 2093 /** 2094 * Creates the subscribe_* methods' return data 2095 * 2096 * @access private 2097 * @param string $feed_url String to prefix to the feed URL 2098 * @param string $site_url String to prefix to the site URL (and 2099 * suffix to the feed URL) 2100 * @return mixed URL if feed exists, false otherwise 2101 */ 2102 function subscribe_service($feed_url, $site_url = null) 2103 { 2104 if ($this->subscribe_url()) 2105 { 2106 $return = $feed_url . rawurlencode($this->feed_url); 2107 if ($site_url !== null && $this->get_link() !== null) 2108 { 2109 $return .= $site_url . rawurlencode($this->get_link()); 2110 } 2111 return $this->sanitize($return, SIMPLEPIE_CONSTRUCT_IRI); 2112 } 2113 else 2114 { 2115 return null; 2116 } 2117 } 2118 2119 function subscribe_aol() 2120 { 2121 return $this->subscribe_service('http://feeds.my.aol.com/add.jsp?url='); 2122 } 2123 2124 function subscribe_bloglines() 2125 { 2126 return $this->subscribe_service('http://www.bloglines.com/sub/'); 2127 } 2128 2129 function subscribe_eskobo() 2130 { 2131 return $this->subscribe_service('http://www.eskobo.com/?AddToMyPage='); 2132 } 2133 2134 function subscribe_feedfeeds() 2135 { 2136 return $this->subscribe_service('http://www.feedfeeds.com/add?feed='); 2137 } 2138 2139 function subscribe_feedster() 2140 { 2141 return $this->subscribe_service('http://www.feedster.com/myfeedster.php?action=addrss&confirm=no&rssurl='); 2142 } 2143 2144 function subscribe_google() 2145 { 2146 return $this->subscribe_service('http://fusion.google.com/add?feedurl='); 2147 } 2148 2149 function subscribe_gritwire() 2150 { 2151 return $this->subscribe_service('http://my.gritwire.com/feeds/addExternalFeed.aspx?FeedUrl='); 2152 } 2153 2154 function subscribe_msn() 2155 { 2156 return $this->subscribe_service('http://my.msn.com/addtomymsn.armx?id=rss&ut=', '&ru='); 2157 } 2158 2159 function subscribe_netvibes() 2160 { 2161 return $this->subscribe_service('http://www.netvibes.com/subscribe.php?url='); 2162 } 2163 2164 function subscribe_newsburst() 2165 { 2166 return $this->subscribe_service('http://www.newsburst.com/Source/?add='); 2167 } 2168 2169 function subscribe_newsgator() 2170 { 2171 return $this->subscribe_service('http://www.newsgator.com/ngs/subscriber/subext.aspx?url='); 2172 } 2173 2174 function subscribe_odeo() 2175 { 2176 return $this->subscribe_service('http://www.odeo.com/listen/subscribe?feed='); 2177 } 2178 2179 function subscribe_podnova() 2180 { 2181 return $this->subscribe_service('http://www.podnova.com/index_your_podcasts.srf?action=add&url='); 2182 } 2183 2184 function subscribe_rojo() 2185 { 2186 return $this->subscribe_service('http://www.rojo.com/add-subscription?resource='); 2187 } 2188 2189 function subscribe_yahoo() 2190 { 2191 return $this->subscribe_service('http://add.my.yahoo.com/rss?url='); 2192 } 2193 2194 function get_feed_tags($namespace, $tag) 2195 { 2196 $type = $this->get_type(); 2197 if ($type & SIMPLEPIE_TYPE_ATOM_10) 2198 { 2199 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['child'][$namespace][$tag])) 2200 { 2201 return $this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['child'][$namespace][$tag]; 2202 } 2203 } 2204 if ($type & SIMPLEPIE_TYPE_ATOM_03) 2205 { 2206 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['child'][$namespace][$tag])) 2207 { 2208 return $this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['child'][$namespace][$tag]; 2209 } 2210 } 2211 if ($type & SIMPLEPIE_TYPE_RSS_RDF) 2212 { 2213 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][$namespace][$tag])) 2214 { 2215 return $this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][$namespace][$tag]; 2216 } 2217 } 2218 if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION) 2219 { 2220 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][$namespace][$tag])) 2221 { 2222 return $this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][$namespace][$tag]; 2223 } 2224 } 2225 return null; 2226 } 2227 2228 function get_channel_tags($namespace, $tag) 2229 { 2230 $type = $this->get_type(); 2231 if ($type & SIMPLEPIE_TYPE_ATOM_ALL) 2232 { 2233 if ($return = $this->get_feed_tags($namespace, $tag)) 2234 { 2235 return $return; 2236 } 2237 } 2238 if ($type & SIMPLEPIE_TYPE_RSS_10) 2239 { 2240 if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'channel')) 2241 { 2242 if (isset($channel[0]['child'][$namespace][$tag])) 2243 { 2244 return $channel[0]['child'][$namespace][$tag]; 2245 } 2246 } 2247 } 2248 if ($type & SIMPLEPIE_TYPE_RSS_090) 2249 { 2250 if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'channel')) 2251 { 2252 if (isset($channel[0]['child'][$namespace][$tag])) 2253 { 2254 return $channel[0]['child'][$namespace][$tag]; 2255 } 2256 } 2257 } 2258 if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION) 2259 { 2260 if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'channel')) 2261 { 2262 if (isset($channel[0]['child'][$namespace][$tag])) 2263 { 2264 return $channel[0]['child'][$namespace][$tag]; 2265 } 2266 } 2267 } 2268 return null; 2269 } 2270 2271 function get_image_tags($namespace, $tag) 2272 { 2273 $type = $this->get_type(); 2274 if ($type & SIMPLEPIE_TYPE_RSS_10) 2275 { 2276 if ($image = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'image')) 2277 { 2278 if (isset($image[0]['child'][$namespace][$tag])) 2279 { 2280 return $image[0]['child'][$namespace][$tag]; 2281 } 2282 } 2283 } 2284 if ($type & SIMPLEPIE_TYPE_RSS_090) 2285 { 2286 if ($image = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'image')) 2287 { 2288 if (isset($image[0]['child'][$namespace][$tag])) 2289 { 2290 return $image[0]['child'][$namespace][$tag]; 2291 } 2292 } 2293 } 2294 if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION) 2295 { 2296 if ($image = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'image')) 2297 { 2298 if (isset($image[0]['child'][$namespace][$tag])) 2299 { 2300 return $image[0]['child'][$namespace][$tag]; 2301 } 2302 } 2303 } 2304 return null; 2305 } 2306 2307 function get_base($element = array()) 2308 { 2309 if (!($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION) && !empty($element['xml_base_explicit']) && isset($element['xml_base'])) 2310 { 2311 return $element['xml_base']; 2312 } 2313 elseif ($this->get_link() !== null) 2314 { 2315 return $this->get_link(); 2316 } 2317 else 2318 { 2319 return $this->subscribe_url(); 2320 } 2321 } 2322 2323 function sanitize($data, $type, $base = '') 2324 { 2325 return $this->sanitize->sanitize($data, $type, $base); 2326 } 2327 2328 function get_title() 2329 { 2330 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title')) 2331 { 2332 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 2333 } 2334 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title')) 2335 { 2336 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 2337 } 2338 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title')) 2339 { 2340 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 2341 } 2342 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title')) 2343 { 2344 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 2345 } 2346 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title')) 2347 { 2348 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 2349 } 2350 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title')) 2351 { 2352 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2353 } 2354 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title')) 2355 { 2356 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2357 } 2358 else 2359 { 2360 return null; 2361 } 2362 } 2363 2364 function get_category($key = 0) 2365 { 2366 $categories = $this->get_categories(); 2367 if (isset($categories[$key])) 2368 { 2369 return $categories[$key]; 2370 } 2371 else 2372 { 2373 return null; 2374 } 2375 } 2376 2377 function get_categories() 2378 { 2379 $categories = array(); 2380 2381 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category) 2382 { 2383 $term = null; 2384 $scheme = null; 2385 $label = null; 2386 if (isset($category['attribs']['']['term'])) 2387 { 2388 $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT); 2389 } 2390 if (isset($category['attribs']['']['scheme'])) 2391 { 2392 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 2393 } 2394 if (isset($category['attribs']['']['label'])) 2395 { 2396 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 2397 } 2398 $categories[] = new $this->category_class($term, $scheme, $label); 2399 } 2400 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category) 2401 { 2402 // This is really the label, but keep this as the term also for BC. 2403 // Label will also work on retrieving because that falls back to term. 2404 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2405 if (isset($category['attribs']['']['domain'])) 2406 { 2407 $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT); 2408 } 2409 else 2410 { 2411 $scheme = null; 2412 } 2413 $categories[] = new $this->category_class($term, $scheme, null); 2414 } 2415 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category) 2416 { 2417 $categories[] = new $this->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 2418 } 2419 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category) 2420 { 2421 $categories[] = new $this->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 2422 } 2423 2424 if (!empty($categories)) 2425 { 2426 return SimplePie_Misc::array_unique($categories); 2427 } 2428 else 2429 { 2430 return null; 2431 } 2432 } 2433 2434 function get_author($key = 0) 2435 { 2436 $authors = $this->get_authors(); 2437 if (isset($authors[$key])) 2438 { 2439 return $authors[$key]; 2440 } 2441 else 2442 { 2443 return null; 2444 } 2445 } 2446 2447 function get_authors() 2448 { 2449 $authors = array(); 2450 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author) 2451 { 2452 $name = null; 2453 $uri = null; 2454 $email = null; 2455 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'])) 2456 { 2457 $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2458 } 2459 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'])) 2460 { 2461 $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0])); 2462 } 2463 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'])) 2464 { 2465 $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2466 } 2467 if ($name !== null || $email !== null || $uri !== null) 2468 { 2469 $authors[] = new $this->author_class($name, $uri, $email); 2470 } 2471 } 2472 if ($author = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author')) 2473 { 2474 $name = null; 2475 $url = null; 2476 $email = null; 2477 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'])) 2478 { 2479 $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2480 } 2481 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'])) 2482 { 2483 $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0])); 2484 } 2485 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'])) 2486 { 2487 $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2488 } 2489 if ($name !== null || $email !== null || $url !== null) 2490 { 2491 $authors[] = new $this->author_class($name, $url, $email); 2492 } 2493 } 2494 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author) 2495 { 2496 $authors[] = new $this->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 2497 } 2498 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author) 2499 { 2500 $authors[] = new $this->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 2501 } 2502 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author) 2503 { 2504 $authors[] = new $this->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 2505 } 2506 2507 if (!empty($authors)) 2508 { 2509 return SimplePie_Misc::array_unique($authors); 2510 } 2511 else 2512 { 2513 return null; 2514 } 2515 } 2516 2517 function get_contributor($key = 0) 2518 { 2519 $contributors = $this->get_contributors(); 2520 if (isset($contributors[$key])) 2521 { 2522 return $contributors[$key]; 2523 } 2524 else 2525 { 2526 return null; 2527 } 2528 } 2529 2530 function get_contributors() 2531 { 2532 $contributors = array(); 2533 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor) 2534 { 2535 $name = null; 2536 $uri = null; 2537 $email = null; 2538 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'])) 2539 { 2540 $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2541 } 2542 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'])) 2543 { 2544 $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0])); 2545 } 2546 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'])) 2547 { 2548 $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2549 } 2550 if ($name !== null || $email !== null || $uri !== null) 2551 { 2552 $contributors[] = new $this->author_class($name, $uri, $email); 2553 } 2554 } 2555 foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor) 2556 { 2557 $name = null; 2558 $url = null; 2559 $email = null; 2560 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'])) 2561 { 2562 $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2563 } 2564 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'])) 2565 { 2566 $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0])); 2567 } 2568 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'])) 2569 { 2570 $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2571 } 2572 if ($name !== null || $email !== null || $url !== null) 2573 { 2574 $contributors[] = new $this->author_class($name, $url, $email); 2575 } 2576 } 2577 2578 if (!empty($contributors)) 2579 { 2580 return SimplePie_Misc::array_unique($contributors); 2581 } 2582 else 2583 { 2584 return null; 2585 } 2586 } 2587 2588 function get_link($key = 0, $rel = 'alternate') 2589 { 2590 $links = $this->get_links($rel); 2591 if (isset($links[$key])) 2592 { 2593 return $links[$key]; 2594 } 2595 else 2596 { 2597 return null; 2598 } 2599 } 2600 2601 /** 2602 * Added for parity between the parent-level and the item/entry-level. 2603 */ 2604 function get_permalink() 2605 { 2606 return $this->get_link(0); 2607 } 2608 2609 function get_links($rel = 'alternate') 2610 { 2611 if (!isset($this->data['links'])) 2612 { 2613 $this->data['links'] = array(); 2614 if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link')) 2615 { 2616 foreach ($links as $link) 2617 { 2618 if (isset($link['attribs']['']['href'])) 2619 { 2620 $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate'; 2621 $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 2622 } 2623 } 2624 } 2625 if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link')) 2626 { 2627 foreach ($links as $link) 2628 { 2629 if (isset($link['attribs']['']['href'])) 2630 { 2631 $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate'; 2632 $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 2633 2634 } 2635 } 2636 } 2637 if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link')) 2638 { 2639 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 2640 } 2641 if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link')) 2642 { 2643 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 2644 } 2645 if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link')) 2646 { 2647 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 2648 } 2649 2650 $keys = array_keys($this->data['links']); 2651 foreach ($keys as $key) 2652 { 2653 if (SimplePie_Misc::is_isegment_nz_nc($key)) 2654 { 2655 if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key])) 2656 { 2657 $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]); 2658 $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]; 2659 } 2660 else 2661 { 2662 $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key]; 2663 } 2664 } 2665 elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY) 2666 { 2667 $this->data['links'][substr($key, 41)] =& $this->data['links'][$key]; 2668 } 2669 $this->data['links'][$key] = array_unique($this->data['links'][$key]); 2670 } 2671 } 2672 2673 if (isset($this->data['links'][$rel])) 2674 { 2675 return $this->data['links'][$rel]; 2676 } 2677 else 2678 { 2679 return null; 2680 } 2681 } 2682 2683 function get_all_discovered_feeds() 2684 { 2685 return $this->all_discovered_feeds; 2686 } 2687 2688 function get_description() 2689 { 2690 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'subtitle')) 2691 { 2692 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 2693 } 2694 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'tagline')) 2695 { 2696 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 2697 } 2698 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description')) 2699 { 2700 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 2701 } 2702 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description')) 2703 { 2704 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 2705 } 2706 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description')) 2707 { 2708 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 2709 } 2710 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description')) 2711 { 2712 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2713 } 2714 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description')) 2715 { 2716 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2717 } 2718 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary')) 2719 { 2720 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 2721 } 2722 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle')) 2723 { 2724 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 2725 } 2726 else 2727 { 2728 return null; 2729 } 2730 } 2731 2732 function get_copyright() 2733 { 2734 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights')) 2735 { 2736 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 2737 } 2738 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'copyright')) 2739 { 2740 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 2741 } 2742 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'copyright')) 2743 { 2744 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2745 } 2746 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights')) 2747 { 2748 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2749 } 2750 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights')) 2751 { 2752 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2753 } 2754 else 2755 { 2756 return null; 2757 } 2758 } 2759 2760 function get_language() 2761 { 2762 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'language')) 2763 { 2764 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2765 } 2766 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'language')) 2767 { 2768 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2769 } 2770 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'language')) 2771 { 2772 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2773 } 2774 elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['xml_lang'])) 2775 { 2776 return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT); 2777 } 2778 elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['xml_lang'])) 2779 { 2780 return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT); 2781 } 2782 elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['xml_lang'])) 2783 { 2784 return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT); 2785 } 2786 elseif (isset($this->data['headers']['content-language'])) 2787 { 2788 return $this->sanitize($this->data['headers']['content-language'], SIMPLEPIE_CONSTRUCT_TEXT); 2789 } 2790 else 2791 { 2792 return null; 2793 } 2794 } 2795 2796 function get_latitude() 2797 { 2798 2799 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat')) 2800 { 2801 return (float) $return[0]['data']; 2802 } 2803 elseif (($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match)) 2804 { 2805 return (float) $match[1]; 2806 } 2807 else 2808 { 2809 return null; 2810 } 2811 } 2812 2813 function get_longitude() 2814 { 2815 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long')) 2816 { 2817 return (float) $return[0]['data']; 2818 } 2819 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon')) 2820 { 2821 return (float) $return[0]['data']; 2822 } 2823 elseif (($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match)) 2824 { 2825 return (float) $match[2]; 2826 } 2827 else 2828 { 2829 return null; 2830 } 2831 } 2832 2833 function get_image_title() 2834 { 2835 if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title')) 2836 { 2837 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2838 } 2839 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title')) 2840 { 2841 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2842 } 2843 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title')) 2844 { 2845 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2846 } 2847 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title')) 2848 { 2849 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2850 } 2851 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title')) 2852 { 2853 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 2854 } 2855 else 2856 { 2857 return null; 2858 } 2859 } 2860 2861 function get_image_url() 2862 { 2863 if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'image')) 2864 { 2865 return $this->sanitize($return[0]['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI); 2866 } 2867 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'logo')) 2868 { 2869 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2870 } 2871 elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon')) 2872 { 2873 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2874 } 2875 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'url')) 2876 { 2877 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2878 } 2879 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'url')) 2880 { 2881 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2882 } 2883 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url')) 2884 { 2885 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2886 } 2887 else 2888 { 2889 return null; 2890 } 2891 } 2892 2893 function get_image_link() 2894 { 2895 if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link')) 2896 { 2897 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2898 } 2899 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link')) 2900 { 2901 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2902 } 2903 elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link')) 2904 { 2905 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 2906 } 2907 else 2908 { 2909 return null; 2910 } 2911 } 2912 2913 function get_image_width() 2914 { 2915 if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'width')) 2916 { 2917 return round($return[0]['data']); 2918 } 2919 elseif ($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION && $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url')) 2920 { 2921 return 88.0; 2922 } 2923 else 2924 { 2925 return null; 2926 } 2927 } 2928 2929 function get_image_height() 2930 { 2931 if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'height')) 2932 { 2933 return round($return[0]['data']); 2934 } 2935 elseif ($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION && $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url')) 2936 { 2937 return 31.0; 2938 } 2939 else 2940 { 2941 return null; 2942 } 2943 } 2944 2945 function get_item_quantity($max = 0) 2946 { 2947 $max = (int) $max; 2948 $qty = count($this->get_items()); 2949 if ($max === 0) 2950 { 2951 return $qty; 2952 } 2953 else 2954 { 2955 return ($qty > $max) ? $max : $qty; 2956 } 2957 } 2958 2959 function get_item($key = 0) 2960 { 2961 $items = $this->get_items(); 2962 if (isset($items[$key])) 2963 { 2964 return $items[$key]; 2965 } 2966 else 2967 { 2968 return null; 2969 } 2970 } 2971 2972 function get_items($start = 0, $end = 0) 2973 { 2974 if (!isset($this->data['items'])) 2975 { 2976 if (!empty($this->multifeed_objects)) 2977 { 2978 $this->data['items'] = SimplePie::merge_items($this->multifeed_objects, $start, $end, $this->item_limit); 2979 } 2980 else 2981 { 2982 $this->data['items'] = array(); 2983 if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'entry')) 2984 { 2985 $keys = array_keys($items); 2986 foreach ($keys as $key) 2987 { 2988 $this->data['items'][] = new $this->item_class($this, $items[$key]); 2989 } 2990 } 2991 if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'entry')) 2992 { 2993 $keys = array_keys($items); 2994 foreach ($keys as $key) 2995 { 2996 $this->data['items'][] = new $this->item_class($this, $items[$key]); 2997 } 2998 } 2999 if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'item')) 3000 { 3001 $keys = array_keys($items); 3002 foreach ($keys as $key) 3003 { 3004 $this->data['items'][] = new $this->item_class($this, $items[$key]); 3005 } 3006 } 3007 if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'item')) 3008 { 3009 $keys = array_keys($items); 3010 foreach ($keys as $key) 3011 { 3012 $this->data['items'][] = new $this->item_class($this, $items[$key]); 3013 } 3014 } 3015 if ($items = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'item')) 3016 { 3017 $keys = array_keys($items); 3018 foreach ($keys as $key) 3019 { 3020 $this->data['items'][] = new $this->item_class($this, $items[$key]); 3021 } 3022 } 3023 } 3024 } 3025 3026 if (!empty($this->data['items'])) 3027 { 3028 // If we want to order it by date, check if all items have a date, and then sort it 3029 if ($this->order_by_date && empty($this->multifeed_objects)) 3030 { 3031 if (!isset($this->data['ordered_items'])) 3032 { 3033 $do_sort = true; 3034 foreach ($this->data['items'] as $item) 3035 { 3036 if (!$item->get_date('U')) 3037 { 3038 $do_sort = false; 3039 break; 3040 } 3041 } 3042 $item = null; 3043 $this->data['ordered_items'] = $this->data['items']; 3044 if ($do_sort) 3045 { 3046 usort($this->data['ordered_items'], array(&$this, 'sort_items')); 3047 } 3048 } 3049 $items = $this->data['ordered_items']; 3050 } 3051 else 3052 { 3053 $items = $this->data['items']; 3054 } 3055 3056 // Slice the data as desired 3057 if ($end === 0) 3058 { 3059 return array_slice($items, $start); 3060 } 3061 else 3062 { 3063 return array_slice($items, $start, $end); 3064 } 3065 } 3066 else 3067 { 3068 return array(); 3069 } 3070 } 3071 3072 /** 3073 * @static 3074 */ 3075 function sort_items($a, $b) 3076 { 3077 return $a->get_date('U') <= $b->get_date('U'); 3078 } 3079 3080 /** 3081 * @static 3082 */ 3083 function merge_items($urls, $start = 0, $end = 0, $limit = 0) 3084 { 3085 if (is_array($urls) && sizeof($urls) > 0) 3086 { 3087 $items = array(); 3088 foreach ($urls as $arg) 3089 { 3090 if (is_a($arg, 'SimplePie')) 3091 { 3092 $items = array_merge($items, $arg->get_items(0, $limit)); 3093 } 3094 else 3095 { 3096 trigger_error('Arguments must be SimplePie objects', E_USER_WARNING); 3097 } 3098 } 3099 3100 $do_sort = true; 3101 foreach ($items as $item) 3102 { 3103 if (!$item->get_date('U')) 3104 { 3105 $do_sort = false; 3106 break; 3107 } 3108 } 3109 $item = null; 3110 if ($do_sort) 3111 { 3112 usort($items, array('SimplePie', 'sort_items')); 3113 } 3114 3115 if ($end === 0) 3116 { 3117 return array_slice($items, $start); 3118 } 3119 else 3120 { 3121 return array_slice($items, $start, $end); 3122 } 3123 } 3124 else 3125 { 3126 trigger_error('Cannot merge zero SimplePie objects', E_USER_WARNING); 3127 return array(); 3128 } 3129 } 3130 } 3131 3132 class SimplePie_Item 3133 { 3134 var $feed; 3135 var $data = array(); 3136 3137 function SimplePie_Item($feed, $data) 3138 { 3139 $this->feed = $feed; 3140 $this->data = $data; 3141 } 3142 3143 function __toString() 3144 { 3145 return md5(serialize($this->data)); 3146 } 3147 3148 /** 3149 * Remove items that link back to this before destroying this object 3150 */ 3151 function __destruct() 3152 { 3153 if ((version_compare(PHP_VERSION, '5.3', '<') || !gc_enabled()) && !ini_get('zend.ze1_compatibility_mode')) 3154 { 3155 unset($this->feed); 3156 } 3157 } 3158 3159 function get_item_tags($namespace, $tag) 3160 { 3161 if (isset($this->data['child'][$namespace][$tag])) 3162 { 3163 return $this->data['child'][$namespace][$tag]; 3164 } 3165 else 3166 { 3167 return null; 3168 } 3169 } 3170 3171 function get_base($element = array()) 3172 { 3173 return $this->feed->get_base($element); 3174 } 3175 3176 function sanitize($data, $type, $base = '') 3177 { 3178 return $this->feed->sanitize($data, $type, $base); 3179 } 3180 3181 function get_feed() 3182 { 3183 return $this->feed; 3184 } 3185 3186 function get_id($hash = false) 3187 { 3188 if (!$hash) 3189 { 3190 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'id')) 3191 { 3192 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3193 } 3194 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'id')) 3195 { 3196 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3197 } 3198 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'guid')) 3199 { 3200 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3201 } 3202 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'identifier')) 3203 { 3204 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3205 } 3206 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'identifier')) 3207 { 3208 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3209 } 3210 elseif (($return = $this->get_permalink()) !== null) 3211 { 3212 return $return; 3213 } 3214 elseif (($return = $this->get_title()) !== null) 3215 { 3216 return $return; 3217 } 3218 } 3219 if ($this->get_permalink() !== null || $this->get_title() !== null) 3220 { 3221 return md5($this->get_permalink() . $this->get_title()); 3222 } 3223 else 3224 { 3225 return md5(serialize($this->data)); 3226 } 3227 } 3228 3229 function get_title() 3230 { 3231 if (!isset($this->data['title'])) 3232 { 3233 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title')) 3234 { 3235 $this->data['title'] = $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 3236 } 3237 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title')) 3238 { 3239 $this->data['title'] = $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 3240 } 3241 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title')) 3242 { 3243 $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 3244 } 3245 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title')) 3246 { 3247 $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 3248 } 3249 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title')) 3250 { 3251 $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 3252 } 3253 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title')) 3254 { 3255 $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3256 } 3257 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title')) 3258 { 3259 $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3260 } 3261 else 3262 { 3263 $this->data['title'] = null; 3264 } 3265 } 3266 return $this->data['title']; 3267 } 3268 3269 function get_description($description_only = false) 3270 { 3271 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'summary')) 3272 { 3273 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 3274 } 3275 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'summary')) 3276 { 3277 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 3278 } 3279 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description')) 3280 { 3281 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 3282 } 3283 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description')) 3284 { 3285 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 3286 } 3287 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description')) 3288 { 3289 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3290 } 3291 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description')) 3292 { 3293 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3294 } 3295 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary')) 3296 { 3297 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 3298 } 3299 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle')) 3300 { 3301 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3302 } 3303 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description')) 3304 { 3305 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML); 3306 } 3307 3308 elseif (!$description_only) 3309 { 3310 return $this->get_content(true); 3311 } 3312 else 3313 { 3314 return null; 3315 } 3316 } 3317 3318 function get_content($content_only = false) 3319 { 3320 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'content')) 3321 { 3322 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_content_construct_type($return[0]['attribs']), $this->get_base($return[0])); 3323 } 3324 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'content')) 3325 { 3326 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 3327 } 3328 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10_MODULES_CONTENT, 'encoded')) 3329 { 3330 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 3331 } 3332 elseif (!$content_only) 3333 { 3334 return $this->get_description(true); 3335 } 3336 else 3337 { 3338 return null; 3339 } 3340 } 3341 3342 function get_category($key = 0) 3343 { 3344 $categories = $this->get_categories(); 3345 if (isset($categories[$key])) 3346 { 3347 return $categories[$key]; 3348 } 3349 else 3350 { 3351 return null; 3352 } 3353 } 3354 3355 function get_categories() 3356 { 3357 $categories = array(); 3358 3359 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category) 3360 { 3361 $term = null; 3362 $scheme = null; 3363 $label = null; 3364 if (isset($category['attribs']['']['term'])) 3365 { 3366 $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT); 3367 } 3368 if (isset($category['attribs']['']['scheme'])) 3369 { 3370 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 3371 } 3372 if (isset($category['attribs']['']['label'])) 3373 { 3374 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 3375 } 3376 $categories[] = new $this->feed->category_class($term, $scheme, $label); 3377 } 3378 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category) 3379 { 3380 // This is really the label, but keep this as the term also for BC. 3381 // Label will also work on retrieving because that falls back to term. 3382 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3383 if (isset($category['attribs']['']['domain'])) 3384 { 3385 $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT); 3386 } 3387 else 3388 { 3389 $scheme = null; 3390 } 3391 $categories[] = new $this->feed->category_class($term, $scheme, null); 3392 } 3393 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category) 3394 { 3395 $categories[] = new $this->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 3396 } 3397 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category) 3398 { 3399 $categories[] = new $this->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 3400 } 3401 3402 if (!empty($categories)) 3403 { 3404 return SimplePie_Misc::array_unique($categories); 3405 } 3406 else 3407 { 3408 return null; 3409 } 3410 } 3411 3412 function get_author($key = 0) 3413 { 3414 $authors = $this->get_authors(); 3415 if (isset($authors[$key])) 3416 { 3417 return $authors[$key]; 3418 } 3419 else 3420 { 3421 return null; 3422 } 3423 } 3424 3425 function get_contributor($key = 0) 3426 { 3427 $contributors = $this->get_contributors(); 3428 if (isset($contributors[$key])) 3429 { 3430 return $contributors[$key]; 3431 } 3432 else 3433 { 3434 return null; 3435 } 3436 } 3437 3438 function get_contributors() 3439 { 3440 $contributors = array(); 3441 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor) 3442 { 3443 $name = null; 3444 $uri = null; 3445 $email = null; 3446 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'])) 3447 { 3448 $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3449 } 3450 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'])) 3451 { 3452 $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0])); 3453 } 3454 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'])) 3455 { 3456 $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3457 } 3458 if ($name !== null || $email !== null || $uri !== null) 3459 { 3460 $contributors[] = new $this->feed->author_class($name, $uri, $email); 3461 } 3462 } 3463 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor) 3464 { 3465 $name = null; 3466 $url = null; 3467 $email = null; 3468 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'])) 3469 { 3470 $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3471 } 3472 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'])) 3473 { 3474 $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0])); 3475 } 3476 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'])) 3477 { 3478 $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3479 } 3480 if ($name !== null || $email !== null || $url !== null) 3481 { 3482 $contributors[] = new $this->feed->author_class($name, $url, $email); 3483 } 3484 } 3485 3486 if (!empty($contributors)) 3487 { 3488 return SimplePie_Misc::array_unique($contributors); 3489 } 3490 else 3491 { 3492 return null; 3493 } 3494 } 3495 3496 function get_authors() 3497 { 3498 $authors = array(); 3499 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author) 3500 { 3501 $name = null; 3502 $uri = null; 3503 $email = null; 3504 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'])) 3505 { 3506 $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3507 } 3508 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'])) 3509 { 3510 $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0])); 3511 } 3512 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'])) 3513 { 3514 $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3515 } 3516 if ($name !== null || $email !== null || $uri !== null) 3517 { 3518 $authors[] = new $this->feed->author_class($name, $uri, $email); 3519 } 3520 } 3521 if ($author = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author')) 3522 { 3523 $name = null; 3524 $url = null; 3525 $email = null; 3526 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'])) 3527 { 3528 $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3529 } 3530 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'])) 3531 { 3532 $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0])); 3533 } 3534 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'])) 3535 { 3536 $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3537 } 3538 if ($name !== null || $email !== null || $url !== null) 3539 { 3540 $authors[] = new $this->feed->author_class($name, $url, $email); 3541 } 3542 } 3543 if ($author = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'author')) 3544 { 3545 $authors[] = new $this->feed->author_class(null, null, $this->sanitize($author[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 3546 } 3547 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author) 3548 { 3549 $authors[] = new $this->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 3550 } 3551 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author) 3552 { 3553 $authors[] = new $this->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 3554 } 3555 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author) 3556 { 3557 $authors[] = new $this->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 3558 } 3559 3560 if (!empty($authors)) 3561 { 3562 return SimplePie_Misc::array_unique($authors); 3563 } 3564 elseif (($source = $this->get_source()) && ($authors = $source->get_authors())) 3565 { 3566 return $authors; 3567 } 3568 elseif ($authors = $this->feed->get_authors()) 3569 { 3570 return $authors; 3571 } 3572 else 3573 { 3574 return null; 3575 } 3576 } 3577 3578 function get_copyright() 3579 { 3580 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights')) 3581 { 3582 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 3583 } 3584 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights')) 3585 { 3586 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3587 } 3588 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights')) 3589 { 3590 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3591 } 3592 else 3593 { 3594 return null; 3595 } 3596 } 3597 3598 function get_date($date_format = 'j F Y, g:i a') 3599 { 3600 if (!isset($this->data['date'])) 3601 { 3602 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'published')) 3603 { 3604 $this->data['date']['raw'] = $return[0]['data']; 3605 } 3606 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'updated')) 3607 { 3608 $this->data['date']['raw'] = $return[0]['data']; 3609 } 3610 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'issued')) 3611 { 3612 $this->data['date']['raw'] = $return[0]['data']; 3613 } 3614 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'created')) 3615 { 3616 $this->data['date']['raw'] = $return[0]['data']; 3617 } 3618 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'modified')) 3619 { 3620 $this->data['date']['raw'] = $return[0]['data']; 3621 } 3622 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'pubDate')) 3623 { 3624 $this->data['date']['raw'] = $return[0]['data']; 3625 } 3626 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'date')) 3627 { 3628 $this->data['date']['raw'] = $return[0]['data']; 3629 } 3630 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'date')) 3631 { 3632 $this->data['date']['raw'] = $return[0]['data']; 3633 } 3634 3635 if (!empty($this->data['date']['raw'])) 3636 { 3637 $parser = SimplePie_Parse_Date::get(); 3638 $this->data['date']['parsed'] = $parser->parse($this->data['date']['raw']); 3639 } 3640 else 3641 { 3642 $this->data['date'] = null; 3643 } 3644 } 3645 if ($this->data['date']) 3646 { 3647 $date_format = (string) $date_format; 3648 switch ($date_format) 3649 { 3650 case '': 3651 return $this->sanitize($this->data['date']['raw'], SIMPLEPIE_CONSTRUCT_TEXT); 3652 3653 case 'U': 3654 return $this->data['date']['parsed']; 3655 3656 default: 3657 return date($date_format, $this->data['date']['parsed']); 3658 } 3659 } 3660 else 3661 { 3662 return null; 3663 } 3664 } 3665 3666 function get_local_date($date_format = '%c') 3667 { 3668 if (!$date_format) 3669 { 3670 return $this->sanitize($this->get_date(''), SIMPLEPIE_CONSTRUCT_TEXT); 3671 } 3672 elseif (($date = $this->get_date('U')) !== null && $date !== false) 3673 { 3674 return strftime($date_format, $date); 3675 } 3676 else 3677 { 3678 return null; 3679 } 3680 } 3681 3682 function get_permalink() 3683 { 3684 $link = $this->get_link(); 3685 $enclosure = $this->get_enclosure(0); 3686 if ($link !== null) 3687 { 3688 return $link; 3689 } 3690 elseif ($enclosure !== null) 3691 { 3692 return $enclosure->get_link(); 3693 } 3694 else 3695 { 3696 return null; 3697 } 3698 } 3699 3700 function get_link($key = 0, $rel = 'alternate') 3701 { 3702 $links = $this->get_links($rel); 3703 if ($links[$key] !== null) 3704 { 3705 return $links[$key]; 3706 } 3707 else 3708 { 3709 return null; 3710 } 3711 } 3712 3713 function get_links($rel = 'alternate') 3714 { 3715 if (!isset($this->data['links'])) 3716 { 3717 $this->data['links'] = array(); 3718 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link') as $link) 3719 { 3720 if (isset($link['attribs']['']['href'])) 3721 { 3722 $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate'; 3723 $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 3724 3725 } 3726 } 3727 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link') as $link) 3728 { 3729 if (isset($link['attribs']['']['href'])) 3730 { 3731 $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate'; 3732 $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 3733 } 3734 } 3735 if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link')) 3736 { 3737 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 3738 } 3739 if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link')) 3740 { 3741 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 3742 } 3743 if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link')) 3744 { 3745 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 3746 } 3747 if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'guid')) 3748 { 3749 if (!isset($links[0]['attribs']['']['isPermaLink']) || strtolower(trim($links[0]['attribs']['']['isPermaLink'])) === 'true') 3750 { 3751 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 3752 } 3753 } 3754 3755 $keys = array_keys($this->data['links']); 3756 foreach ($keys as $key) 3757 { 3758 if (SimplePie_Misc::is_isegment_nz_nc($key)) 3759 { 3760 if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key])) 3761 { 3762 $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]); 3763 $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]; 3764 } 3765 else 3766 { 3767 $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key]; 3768 } 3769 } 3770 elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY) 3771 { 3772 $this->data['links'][substr($key, 41)] =& $this->data['links'][$key]; 3773 } 3774 $this->data['links'][$key] = array_unique($this->data['links'][$key]); 3775 } 3776 } 3777 if (isset($this->data['links'][$rel])) 3778 { 3779 return $this->data['links'][$rel]; 3780 } 3781 else 3782 { 3783 return null; 3784 } 3785 } 3786 3787 /** 3788 * @todo Add ability to prefer one type of content over another (in a media group). 3789 */ 3790 function get_enclosure($key = 0, $prefer = null) 3791 { 3792 $enclosures = $this->get_enclosures(); 3793 if (isset($enclosures[$key])) 3794 { 3795 return $enclosures[$key]; 3796 } 3797 else 3798 { 3799 return null; 3800 } 3801 } 3802 3803 /** 3804 * Grabs all available enclosures (podcasts, etc.) 3805 * 3806 * Supports the <enclosure> RSS tag, as well as Media RSS and iTunes RSS. 3807 * 3808 * At this point, we're pretty much assuming that all enclosures for an item are the same content. Anything else is too complicated to properly support. 3809 * 3810 * @todo Add support for end-user defined sorting of enclosures by type/handler (so we can prefer the faster-loading FLV over MP4). 3811 * @todo If an element exists at a level, but it's value is empty, we should fall back to the value from the parent (if it exists). 3812 */ 3813 function get_enclosures() 3814 { 3815 if (!isset($this->data['enclosures'])) 3816 { 3817 $this->data['enclosures'] = array(); 3818 3819 // Elements 3820 $captions_parent = null; 3821 $categories_parent = null; 3822 $copyrights_parent = null; 3823 $credits_parent = null; 3824 $description_parent = null; 3825 $duration_parent = null; 3826 $hashes_parent = null; 3827 $keywords_parent = null; 3828 $player_parent = null; 3829 $ratings_parent = null; 3830 $restrictions_parent = null; 3831 $thumbnails_parent = null; 3832 $title_parent = null; 3833 3834 // Let's do the channel and item-level ones first, and just re-use them if we need to. 3835 $parent = $this->get_feed(); 3836 3837 // CAPTIONS 3838 if ($captions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'text')) 3839 { 3840 foreach ($captions as $caption) 3841 { 3842 $caption_type = null; 3843 $caption_lang = null; 3844 $caption_startTime = null; 3845 $caption_endTime = null; 3846 $caption_text = null; 3847 if (isset($caption['attribs']['']['type'])) 3848 { 3849 $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 3850 } 3851 if (isset($caption['attribs']['']['lang'])) 3852 { 3853 $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT); 3854 } 3855 if (isset($caption['attribs']['']['start'])) 3856 { 3857 $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT); 3858 } 3859 if (isset($caption['attribs']['']['end'])) 3860 { 3861 $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT); 3862 } 3863 if (isset($caption['data'])) 3864 { 3865 $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3866 } 3867 $captions_parent[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text); 3868 } 3869 } 3870 elseif ($captions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'text')) 3871 { 3872 foreach ($captions as $caption) 3873 { 3874 $caption_type = null; 3875 $caption_lang = null; 3876 $caption_startTime = null; 3877 $caption_endTime = null; 3878 $caption_text = null; 3879 if (isset($caption['attribs']['']['type'])) 3880 { 3881 $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 3882 } 3883 if (isset($caption['attribs']['']['lang'])) 3884 { 3885 $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT); 3886 } 3887 if (isset($caption['attribs']['']['start'])) 3888 { 3889 $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT); 3890 } 3891 if (isset($caption['attribs']['']['end'])) 3892 { 3893 $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT); 3894 } 3895 if (isset($caption['data'])) 3896 { 3897 $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3898 } 3899 $captions_parent[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text); 3900 } 3901 } 3902 if (is_array($captions_parent)) 3903 { 3904 $captions_parent = array_values(SimplePie_Misc::array_unique($captions_parent)); 3905 } 3906 3907 // CATEGORIES 3908 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'category') as $category) 3909 { 3910 $term = null; 3911 $scheme = null; 3912 $label = null; 3913 if (isset($category['data'])) 3914 { 3915 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3916 } 3917 if (isset($category['attribs']['']['scheme'])) 3918 { 3919 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 3920 } 3921 else 3922 { 3923 $scheme = 'http://search.yahoo.com/mrss/category_schema'; 3924 } 3925 if (isset($category['attribs']['']['label'])) 3926 { 3927 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 3928 } 3929 $categories_parent[] = new $this->feed->category_class($term, $scheme, $label); 3930 } 3931 foreach ((array) $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'category') as $category) 3932 { 3933 $term = null; 3934 $scheme = null; 3935 $label = null; 3936 if (isset($category['data'])) 3937 { 3938 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3939 } 3940 if (isset($category['attribs']['']['scheme'])) 3941 { 3942 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 3943 } 3944 else 3945 { 3946 $scheme = 'http://search.yahoo.com/mrss/category_schema'; 3947 } 3948 if (isset($category['attribs']['']['label'])) 3949 { 3950 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 3951 } 3952 $categories_parent[] = new $this->feed->category_class($term, $scheme, $label); 3953 } 3954 foreach ((array) $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'category') as $category) 3955 { 3956 $term = null; 3957 $scheme = 'http://www.itunes.com/dtds/podcast-1.0.dtd'; 3958 $label = null; 3959 if (isset($category['attribs']['']['text'])) 3960 { 3961 $label = $this->sanitize($category['attribs']['']['text'], SIMPLEPIE_CONSTRUCT_TEXT); 3962 } 3963 $categories_parent[] = new $this->feed->category_class($term, $scheme, $label); 3964 3965 if (isset($category['child'][SIMPLEPIE_NAMESPACE_ITUNES]['category'])) 3966 { 3967 foreach ((array) $category['child'][SIMPLEPIE_NAMESPACE_ITUNES]['category'] as $subcategory) 3968 { 3969 if (isset($subcategory['attribs']['']['text'])) 3970 { 3971 $label = $this->sanitize($subcategory['attribs']['']['text'], SIMPLEPIE_CONSTRUCT_TEXT); 3972 } 3973 $categories_parent[] = new $this->feed->category_class($term, $scheme, $label); 3974 } 3975 } 3976 } 3977 if (is_array($categories_parent)) 3978 { 3979 $categories_parent = array_values(SimplePie_Misc::array_unique($categories_parent)); 3980 } 3981 3982 // COPYRIGHT 3983 if ($copyright = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'copyright')) 3984 { 3985 $copyright_url = null; 3986 $copyright_label = null; 3987 if (isset($copyright[0]['attribs']['']['url'])) 3988 { 3989 $copyright_url = $this->sanitize($copyright[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT); 3990 } 3991 if (isset($copyright[0]['data'])) 3992 { 3993 $copyright_label = $this->sanitize($copyright[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 3994 } 3995 $copyrights_parent = new $this->feed->copyright_class($copyright_url, $copyright_label); 3996 } 3997 elseif ($copyright = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'copyright')) 3998 { 3999 $copyright_url = null; 4000 $copyright_label = null; 4001 if (isset($copyright[0]['attribs']['']['url'])) 4002 { 4003 $copyright_url = $this->sanitize($copyright[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT); 4004 } 4005 if (isset($copyright[0]['data'])) 4006 { 4007 $copyright_label = $this->sanitize($copyright[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4008 } 4009 $copyrights_parent = new $this->feed->copyright_class($copyright_url, $copyright_label); 4010 } 4011 4012 // CREDITS 4013 if ($credits = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'credit')) 4014 { 4015 foreach ($credits as $credit) 4016 { 4017 $credit_role = null; 4018 $credit_scheme = null; 4019 $credit_name = null; 4020 if (isset($credit['attribs']['']['role'])) 4021 { 4022 $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT); 4023 } 4024 if (isset($credit['attribs']['']['scheme'])) 4025 { 4026 $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4027 } 4028 else 4029 { 4030 $credit_scheme = 'urn:ebu'; 4031 } 4032 if (isset($credit['data'])) 4033 { 4034 $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4035 } 4036 $credits_parent[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name); 4037 } 4038 } 4039 elseif ($credits = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'credit')) 4040 { 4041 foreach ($credits as $credit) 4042 { 4043 $credit_role = null; 4044 $credit_scheme = null; 4045 $credit_name = null; 4046 if (isset($credit['attribs']['']['role'])) 4047 { 4048 $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT); 4049 } 4050 if (isset($credit['attribs']['']['scheme'])) 4051 { 4052 $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4053 } 4054 else 4055 { 4056 $credit_scheme = 'urn:ebu'; 4057 } 4058 if (isset($credit['data'])) 4059 { 4060 $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4061 } 4062 $credits_parent[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name); 4063 } 4064 } 4065 if (is_array($credits_parent)) 4066 { 4067 $credits_parent = array_values(SimplePie_Misc::array_unique($credits_parent)); 4068 } 4069 4070 // DESCRIPTION 4071 if ($description_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'description')) 4072 { 4073 if (isset($description_parent[0]['data'])) 4074 { 4075 $description_parent = $this->sanitize($description_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4076 } 4077 } 4078 elseif ($description_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'description')) 4079 { 4080 if (isset($description_parent[0]['data'])) 4081 { 4082 $description_parent = $this->sanitize($description_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4083 } 4084 } 4085 4086 // DURATION 4087 if ($duration_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'duration')) 4088 { 4089 $seconds = null; 4090 $minutes = null; 4091 $hours = null; 4092 if (isset($duration_parent[0]['data'])) 4093 { 4094 $temp = explode(':', $this->sanitize($duration_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 4095 if (sizeof($temp) > 0) 4096 { 4097 $seconds = (int) array_pop($temp); 4098 } 4099 if (sizeof($temp) > 0) 4100 { 4101 $minutes = (int) array_pop($temp); 4102 $seconds += $minutes * 60; 4103 } 4104 if (sizeof($temp) > 0) 4105 { 4106 $hours = (int) array_pop($temp); 4107 $seconds += $hours * 3600; 4108 } 4109 unset($temp); 4110 $duration_parent = $seconds; 4111 } 4112 } 4113 4114 // HASHES 4115 if ($hashes_iterator = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'hash')) 4116 { 4117 foreach ($hashes_iterator as $hash) 4118 { 4119 $value = null; 4120 $algo = null; 4121 if (isset($hash['data'])) 4122 { 4123 $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4124 } 4125 if (isset($hash['attribs']['']['algo'])) 4126 { 4127 $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT); 4128 } 4129 else 4130 { 4131 $algo = 'md5'; 4132 } 4133 $hashes_parent[] = $algo.':'.$value; 4134 } 4135 } 4136 elseif ($hashes_iterator = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'hash')) 4137 { 4138 foreach ($hashes_iterator as $hash) 4139 { 4140 $value = null; 4141 $algo = null; 4142 if (isset($hash['data'])) 4143 { 4144 $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4145 } 4146 if (isset($hash['attribs']['']['algo'])) 4147 { 4148 $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT); 4149 } 4150 else 4151 { 4152 $algo = 'md5'; 4153 } 4154 $hashes_parent[] = $algo.':'.$value; 4155 } 4156 } 4157 if (is_array($hashes_parent)) 4158 { 4159 $hashes_parent = array_values(SimplePie_Misc::array_unique($hashes_parent)); 4160 } 4161 4162 // KEYWORDS 4163 if ($keywords = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'keywords')) 4164 { 4165 if (isset($keywords[0]['data'])) 4166 { 4167 $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 4168 foreach ($temp as $word) 4169 { 4170 $keywords_parent[] = trim($word); 4171 } 4172 } 4173 unset($temp); 4174 } 4175 elseif ($keywords = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'keywords')) 4176 { 4177 if (isset($keywords[0]['data'])) 4178 { 4179 $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 4180 foreach ($temp as $word) 4181 { 4182 $keywords_parent[] = trim($word); 4183 } 4184 } 4185 unset($temp); 4186 } 4187 elseif ($keywords = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'keywords')) 4188 { 4189 if (isset($keywords[0]['data'])) 4190 { 4191 $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 4192 foreach ($temp as $word) 4193 { 4194 $keywords_parent[] = trim($word); 4195 } 4196 } 4197 unset($temp); 4198 } 4199 elseif ($keywords = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'keywords')) 4200 { 4201 if (isset($keywords[0]['data'])) 4202 { 4203 $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 4204 foreach ($temp as $word) 4205 { 4206 $keywords_parent[] = trim($word); 4207 } 4208 } 4209 unset($temp); 4210 } 4211 if (is_array($keywords_parent)) 4212 { 4213 $keywords_parent = array_values(SimplePie_Misc::array_unique($keywords_parent)); 4214 } 4215 4216 // PLAYER 4217 if ($player_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'player')) 4218 { 4219 if (isset($player_parent[0]['attribs']['']['url'])) 4220 { 4221 $player_parent = $this->sanitize($player_parent[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 4222 } 4223 } 4224 elseif ($player_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'player')) 4225 { 4226 if (isset($player_parent[0]['attribs']['']['url'])) 4227 { 4228 $player_parent = $this->sanitize($player_parent[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 4229 } 4230 } 4231 4232 // RATINGS 4233 if ($ratings = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'rating')) 4234 { 4235 foreach ($ratings as $rating) 4236 { 4237 $rating_scheme = null; 4238 $rating_value = null; 4239 if (isset($rating['attribs']['']['scheme'])) 4240 { 4241 $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4242 } 4243 else 4244 { 4245 $rating_scheme = 'urn:simple'; 4246 } 4247 if (isset($rating['data'])) 4248 { 4249 $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4250 } 4251 $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value); 4252 } 4253 } 4254 elseif ($ratings = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'explicit')) 4255 { 4256 foreach ($ratings as $rating) 4257 { 4258 $rating_scheme = 'urn:itunes'; 4259 $rating_value = null; 4260 if (isset($rating['data'])) 4261 { 4262 $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4263 } 4264 $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value); 4265 } 4266 } 4267 elseif ($ratings = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'rating')) 4268 { 4269 foreach ($ratings as $rating) 4270 { 4271 $rating_scheme = null; 4272 $rating_value = null; 4273 if (isset($rating['attribs']['']['scheme'])) 4274 { 4275 $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4276 } 4277 else 4278 { 4279 $rating_scheme = 'urn:simple'; 4280 } 4281 if (isset($rating['data'])) 4282 { 4283 $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4284 } 4285 $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value); 4286 } 4287 } 4288 elseif ($ratings = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'explicit')) 4289 { 4290 foreach ($ratings as $rating) 4291 { 4292 $rating_scheme = 'urn:itunes'; 4293 $rating_value = null; 4294 if (isset($rating['data'])) 4295 { 4296 $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4297 } 4298 $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value); 4299 } 4300 } 4301 if (is_array($ratings_parent)) 4302 { 4303 $ratings_parent = array_values(SimplePie_Misc::array_unique($ratings_parent)); 4304 } 4305 4306 // RESTRICTIONS 4307 if ($restrictions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'restriction')) 4308 { 4309 foreach ($restrictions as $restriction) 4310 { 4311 $restriction_relationship = null; 4312 $restriction_type = null; 4313 $restriction_value = null; 4314 if (isset($restriction['attribs']['']['relationship'])) 4315 { 4316 $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT); 4317 } 4318 if (isset($restriction['attribs']['']['type'])) 4319 { 4320 $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 4321 } 4322 if (isset($restriction['data'])) 4323 { 4324 $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4325 } 4326 $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value); 4327 } 4328 } 4329 elseif ($restrictions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'block')) 4330 { 4331 foreach ($restrictions as $restriction) 4332 { 4333 $restriction_relationship = 'allow'; 4334 $restriction_type = null; 4335 $restriction_value = 'itunes'; 4336 if (isset($restriction['data']) && strtolower($restriction['data']) === 'yes') 4337 { 4338 $restriction_relationship = 'deny'; 4339 } 4340 $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value); 4341 } 4342 } 4343 elseif ($restrictions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'restriction')) 4344 { 4345 foreach ($restrictions as $restriction) 4346 { 4347 $restriction_relationship = null; 4348 $restriction_type = null; 4349 $restriction_value = null; 4350 if (isset($restriction['attribs']['']['relationship'])) 4351 { 4352 $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT); 4353 } 4354 if (isset($restriction['attribs']['']['type'])) 4355 { 4356 $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 4357 } 4358 if (isset($restriction['data'])) 4359 { 4360 $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4361 } 4362 $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value); 4363 } 4364 } 4365 elseif ($restrictions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'block')) 4366 { 4367 foreach ($restrictions as $restriction) 4368 { 4369 $restriction_relationship = 'allow'; 4370 $restriction_type = null; 4371 $restriction_value = 'itunes'; 4372 if (isset($restriction['data']) && strtolower($restriction['data']) === 'yes') 4373 { 4374 $restriction_relationship = 'deny'; 4375 } 4376 $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value); 4377 } 4378 } 4379 if (is_array($restrictions_parent)) 4380 { 4381 $restrictions_parent = array_values(SimplePie_Misc::array_unique($restrictions_parent)); 4382 } 4383 4384 // THUMBNAILS 4385 if ($thumbnails = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'thumbnail')) 4386 { 4387 foreach ($thumbnails as $thumbnail) 4388 { 4389 if (isset($thumbnail['attribs']['']['url'])) 4390 { 4391 $thumbnails_parent[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 4392 } 4393 } 4394 } 4395 elseif ($thumbnails = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'thumbnail')) 4396 { 4397 foreach ($thumbnails as $thumbnail) 4398 { 4399 if (isset($thumbnail['attribs']['']['url'])) 4400 { 4401 $thumbnails_parent[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 4402 } 4403 } 4404 } 4405 4406 // TITLES 4407 if ($title_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'title')) 4408 { 4409 if (isset($title_parent[0]['data'])) 4410 { 4411 $title_parent = $this->sanitize($title_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4412 } 4413 } 4414 elseif ($title_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'title')) 4415 { 4416 if (isset($title_parent[0]['data'])) 4417 { 4418 $title_parent = $this->sanitize($title_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4419 } 4420 } 4421 4422 // Clear the memory 4423 unset($parent); 4424 4425 // Attributes 4426 $bitrate = null; 4427 $channels = null; 4428 $duration = null; 4429 $expression = null; 4430 $framerate = null; 4431 $height = null; 4432 $javascript = null; 4433 $lang = null; 4434 $length = null; 4435 $medium = null; 4436 $samplingrate = null; 4437 $type = null; 4438 $url = null; 4439 $width = null; 4440 4441 // Elements 4442 $captions = null; 4443 $categories = null; 4444 $copyrights = null; 4445 $credits = null; 4446 $description = null; 4447 $hashes = null; 4448 $keywords = null; 4449 $player = null; 4450 $ratings = null; 4451 $restrictions = null; 4452 $thumbnails = null; 4453 $title = null; 4454 4455 // If we have media:group tags, loop through them. 4456 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'group') as $group) 4457 { 4458 if(isset($group['child']) && isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'])) 4459 { 4460 // If we have media:content tags, loop through them. 4461 foreach ((array) $group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'] as $content) 4462 { 4463 if (isset($content['attribs']['']['url'])) 4464 { 4465 // Attributes 4466 $bitrate = null; 4467 $channels = null; 4468 $duration = null; 4469 $expression = null; 4470 $framerate = null; 4471 $height = null; 4472 $javascript = null; 4473 $lang = null; 4474 $length = null; 4475 $medium = null; 4476 $samplingrate = null; 4477 $type = null; 4478 $url = null; 4479 $width = null; 4480 4481 // Elements 4482 $captions = null; 4483 $categories = null; 4484 $copyrights = null; 4485 $credits = null; 4486 $description = null; 4487 $hashes = null; 4488 $keywords = null; 4489 $player = null; 4490 $ratings = null; 4491 $restrictions = null; 4492 $thumbnails = null; 4493 $title = null; 4494 4495 // Start checking the attributes of media:content 4496 if (isset($content['attribs']['']['bitrate'])) 4497 { 4498 $bitrate = $this->sanitize($content['attribs']['']['bitrate'], SIMPLEPIE_CONSTRUCT_TEXT); 4499 } 4500 if (isset($content['attribs']['']['channels'])) 4501 { 4502 $channels = $this->sanitize($content['attribs']['']['channels'], SIMPLEPIE_CONSTRUCT_TEXT); 4503 } 4504 if (isset($content['attribs']['']['duration'])) 4505 { 4506 $duration = $this->sanitize($content['attribs']['']['duration'], SIMPLEPIE_CONSTRUCT_TEXT); 4507 } 4508 else 4509 { 4510 $duration = $duration_parent; 4511 } 4512 if (isset($content['attribs']['']['expression'])) 4513 { 4514 $expression = $this->sanitize($content['attribs']['']['expression'], SIMPLEPIE_CONSTRUCT_TEXT); 4515 } 4516 if (isset($content['attribs']['']['framerate'])) 4517 { 4518 $framerate = $this->sanitize($content['attribs']['']['framerate'], SIMPLEPIE_CONSTRUCT_TEXT); 4519 } 4520 if (isset($content['attribs']['']['height'])) 4521 { 4522 $height = $this->sanitize($content['attribs']['']['height'], SIMPLEPIE_CONSTRUCT_TEXT); 4523 } 4524 if (isset($content['attribs']['']['lang'])) 4525 { 4526 $lang = $this->sanitize($content['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT); 4527 } 4528 if (isset($content['attribs']['']['fileSize'])) 4529 { 4530 $length = ceil($content['attribs']['']['fileSize']); 4531 } 4532 if (isset($content['attribs']['']['medium'])) 4533 { 4534 $medium = $this->sanitize($content['attribs']['']['medium'], SIMPLEPIE_CONSTRUCT_TEXT); 4535 } 4536 if (isset($content['attribs']['']['samplingrate'])) 4537 { 4538 $samplingrate = $this->sanitize($content['attribs']['']['samplingrate'], SIMPLEPIE_CONSTRUCT_TEXT); 4539 } 4540 if (isset($content['attribs']['']['type'])) 4541 { 4542 $type = $this->sanitize($content['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 4543 } 4544 if (isset($content['attribs']['']['width'])) 4545 { 4546 $width = $this->sanitize($content['attribs']['']['width'], SIMPLEPIE_CONSTRUCT_TEXT); 4547 } 4548 $url = $this->sanitize($content['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 4549 4550 // Checking the other optional media: elements. Priority: media:content, media:group, item, channel 4551 4552 // CAPTIONS 4553 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'])) 4554 { 4555 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption) 4556 { 4557 $caption_type = null; 4558 $caption_lang = null; 4559 $caption_startTime = null; 4560 $caption_endTime = null; 4561 $caption_text = null; 4562 if (isset($caption['attribs']['']['type'])) 4563 { 4564 $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 4565 } 4566 if (isset($caption['attribs']['']['lang'])) 4567 { 4568 $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT); 4569 } 4570 if (isset($caption['attribs']['']['start'])) 4571 { 4572 $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT); 4573 } 4574 if (isset($caption['attribs']['']['end'])) 4575 { 4576 $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT); 4577 } 4578 if (isset($caption['data'])) 4579 { 4580 $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4581 } 4582 $captions[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text); 4583 } 4584 if (is_array($captions)) 4585 { 4586 $captions = array_values(SimplePie_Misc::array_unique($captions)); 4587 } 4588 } 4589 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'])) 4590 { 4591 foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption) 4592 { 4593 $caption_type = null; 4594 $caption_lang = null; 4595 $caption_startTime = null; 4596 $caption_endTime = null; 4597 $caption_text = null; 4598 if (isset($caption['attribs']['']['type'])) 4599 { 4600 $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 4601 } 4602 if (isset($caption['attribs']['']['lang'])) 4603 { 4604 $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT); 4605 } 4606 if (isset($caption['attribs']['']['start'])) 4607 { 4608 $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT); 4609 } 4610 if (isset($caption['attribs']['']['end'])) 4611 { 4612 $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT); 4613 } 4614 if (isset($caption['data'])) 4615 { 4616 $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4617 } 4618 $captions[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text); 4619 } 4620 if (is_array($captions)) 4621 { 4622 $captions = array_values(SimplePie_Misc::array_unique($captions)); 4623 } 4624 } 4625 else 4626 { 4627 $captions = $captions_parent; 4628 } 4629 4630 // CATEGORIES 4631 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'])) 4632 { 4633 foreach ((array) $content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category) 4634 { 4635 $term = null; 4636 $scheme = null; 4637 $label = null; 4638 if (isset($category['data'])) 4639 { 4640 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4641 } 4642 if (isset($category['attribs']['']['scheme'])) 4643 { 4644 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4645 } 4646 else 4647 { 4648 $scheme = 'http://search.yahoo.com/mrss/category_schema'; 4649 } 4650 if (isset($category['attribs']['']['label'])) 4651 { 4652 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 4653 } 4654 $categories[] = new $this->feed->category_class($term, $scheme, $label); 4655 } 4656 } 4657 if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'])) 4658 { 4659 foreach ((array) $group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category) 4660 { 4661 $term = null; 4662 $scheme = null; 4663 $label = null; 4664 if (isset($category['data'])) 4665 { 4666 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4667 } 4668 if (isset($category['attribs']['']['scheme'])) 4669 { 4670 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4671 } 4672 else 4673 { 4674 $scheme = 'http://search.yahoo.com/mrss/category_schema'; 4675 } 4676 if (isset($category['attribs']['']['label'])) 4677 { 4678 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 4679 } 4680 $categories[] = new $this->feed->category_class($term, $scheme, $label); 4681 } 4682 } 4683 if (is_array($categories) && is_array($categories_parent)) 4684 { 4685 $categories = array_values(SimplePie_Misc::array_unique(array_merge($categories, $categories_parent))); 4686 } 4687 elseif (is_array($categories)) 4688 { 4689 $categories = array_values(SimplePie_Misc::array_unique($categories)); 4690 } 4691 elseif (is_array($categories_parent)) 4692 { 4693 $categories = array_values(SimplePie_Misc::array_unique($categories_parent)); 4694 } 4695 4696 // COPYRIGHTS 4697 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'])) 4698 { 4699 $copyright_url = null; 4700 $copyright_label = null; 4701 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'])) 4702 { 4703 $copyright_url = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT); 4704 } 4705 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'])) 4706 { 4707 $copyright_label = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4708 } 4709 $copyrights = new $this->feed->copyright_class($copyright_url, $copyright_label); 4710 } 4711 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'])) 4712 { 4713 $copyright_url = null; 4714 $copyright_label = null; 4715 if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'])) 4716 { 4717 $copyright_url = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT); 4718 } 4719 if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'])) 4720 { 4721 $copyright_label = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4722 } 4723 $copyrights = new $this->feed->copyright_class($copyright_url, $copyright_label); 4724 } 4725 else 4726 { 4727 $copyrights = $copyrights_parent; 4728 } 4729 4730 // CREDITS 4731 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'])) 4732 { 4733 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit) 4734 { 4735 $credit_role = null; 4736 $credit_scheme = null; 4737 $credit_name = null; 4738 if (isset($credit['attribs']['']['role'])) 4739 { 4740 $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT); 4741 } 4742 if (isset($credit['attribs']['']['scheme'])) 4743 { 4744 $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4745 } 4746 else 4747 { 4748 $credit_scheme = 'urn:ebu'; 4749 } 4750 if (isset($credit['data'])) 4751 { 4752 $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4753 } 4754 $credits[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name); 4755 } 4756 if (is_array($credits)) 4757 { 4758 $credits = array_values(SimplePie_Misc::array_unique($credits)); 4759 } 4760 } 4761 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'])) 4762 { 4763 foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit) 4764 { 4765 $credit_role = null; 4766 $credit_scheme = null; 4767 $credit_name = null; 4768 if (isset($credit['attribs']['']['role'])) 4769 { 4770 $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT); 4771 } 4772 if (isset($credit['attribs']['']['scheme'])) 4773 { 4774 $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4775 } 4776 else 4777 { 4778 $credit_scheme = 'urn:ebu'; 4779 } 4780 if (isset($credit['data'])) 4781 { 4782 $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4783 } 4784 $credits[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name); 4785 } 4786 if (is_array($credits)) 4787 { 4788 $credits = array_values(SimplePie_Misc::array_unique($credits)); 4789 } 4790 } 4791 else 4792 { 4793 $credits = $credits_parent; 4794 } 4795 4796 // DESCRIPTION 4797 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'])) 4798 { 4799 $description = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4800 } 4801 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'])) 4802 { 4803 $description = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4804 } 4805 else 4806 { 4807 $description = $description_parent; 4808 } 4809 4810 // HASHES 4811 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'])) 4812 { 4813 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash) 4814 { 4815 $value = null; 4816 $algo = null; 4817 if (isset($hash['data'])) 4818 { 4819 $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4820 } 4821 if (isset($hash['attribs']['']['algo'])) 4822 { 4823 $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT); 4824 } 4825 else 4826 { 4827 $algo = 'md5'; 4828 } 4829 $hashes[] = $algo.':'.$value; 4830 } 4831 if (is_array($hashes)) 4832 { 4833 $hashes = array_values(SimplePie_Misc::array_unique($hashes)); 4834 } 4835 } 4836 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'])) 4837 { 4838 foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash) 4839 { 4840 $value = null; 4841 $algo = null; 4842 if (isset($hash['data'])) 4843 { 4844 $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4845 } 4846 if (isset($hash['attribs']['']['algo'])) 4847 { 4848 $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT); 4849 } 4850 else 4851 { 4852 $algo = 'md5'; 4853 } 4854 $hashes[] = $algo.':'.$value; 4855 } 4856 if (is_array($hashes)) 4857 { 4858 $hashes = array_values(SimplePie_Misc::array_unique($hashes)); 4859 } 4860 } 4861 else 4862 { 4863 $hashes = $hashes_parent; 4864 } 4865 4866 // KEYWORDS 4867 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'])) 4868 { 4869 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'])) 4870 { 4871 $temp = explode(',', $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 4872 foreach ($temp as $word) 4873 { 4874 $keywords[] = trim($word); 4875 } 4876 unset($temp); 4877 } 4878 if (is_array($keywords)) 4879 { 4880 $keywords = array_values(SimplePie_Misc::array_unique($keywords)); 4881 } 4882 } 4883 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'])) 4884 { 4885 if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'])) 4886 { 4887 $temp = explode(',', $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 4888 foreach ($temp as $word) 4889 { 4890 $keywords[] = trim($word); 4891 } 4892 unset($temp); 4893 } 4894 if (is_array($keywords)) 4895 { 4896 $keywords = array_values(SimplePie_Misc::array_unique($keywords)); 4897 } 4898 } 4899 else 4900 { 4901 $keywords = $keywords_parent; 4902 } 4903 4904 // PLAYER 4905 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'])) 4906 { 4907 $player = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 4908 } 4909 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'])) 4910 { 4911 $player = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 4912 } 4913 else 4914 { 4915 $player = $player_parent; 4916 } 4917 4918 // RATINGS 4919 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'])) 4920 { 4921 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating) 4922 { 4923 $rating_scheme = null; 4924 $rating_value = null; 4925 if (isset($rating['attribs']['']['scheme'])) 4926 { 4927 $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4928 } 4929 else 4930 { 4931 $rating_scheme = 'urn:simple'; 4932 } 4933 if (isset($rating['data'])) 4934 { 4935 $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4936 } 4937 $ratings[] = new $this->feed->rating_class($rating_scheme, $rating_value); 4938 } 4939 if (is_array($ratings)) 4940 { 4941 $ratings = array_values(SimplePie_Misc::array_unique($ratings)); 4942 } 4943 } 4944 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'])) 4945 { 4946 foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating) 4947 { 4948 $rating_scheme = null; 4949 $rating_value = null; 4950 if (isset($rating['attribs']['']['scheme'])) 4951 { 4952 $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 4953 } 4954 else 4955 { 4956 $rating_scheme = 'urn:simple'; 4957 } 4958 if (isset($rating['data'])) 4959 { 4960 $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4961 } 4962 $ratings[] = new $this->feed->rating_class($rating_scheme, $rating_value); 4963 } 4964 if (is_array($ratings)) 4965 { 4966 $ratings = array_values(SimplePie_Misc::array_unique($ratings)); 4967 } 4968 } 4969 else 4970 { 4971 $ratings = $ratings_parent; 4972 } 4973 4974 // RESTRICTIONS 4975 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'])) 4976 { 4977 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction) 4978 { 4979 $restriction_relationship = null; 4980 $restriction_type = null; 4981 $restriction_value = null; 4982 if (isset($restriction['attribs']['']['relationship'])) 4983 { 4984 $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT); 4985 } 4986 if (isset($restriction['attribs']['']['type'])) 4987 { 4988 $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 4989 } 4990 if (isset($restriction['data'])) 4991 { 4992 $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT); 4993 } 4994 $restrictions[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value); 4995 } 4996 if (is_array($restrictions)) 4997 { 4998 $restrictions = array_values(SimplePie_Misc::array_unique($restrictions)); 4999 } 5000 } 5001 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'])) 5002 { 5003 foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction) 5004 { 5005 $restriction_relationship = null; 5006 $restriction_type = null; 5007 $restriction_value = null; 5008 if (isset($restriction['attribs']['']['relationship'])) 5009 { 5010 $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT); 5011 } 5012 if (isset($restriction['attribs']['']['type'])) 5013 { 5014 $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 5015 } 5016 if (isset($restriction['data'])) 5017 { 5018 $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5019 } 5020 $restrictions[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value); 5021 } 5022 if (is_array($restrictions)) 5023 { 5024 $restrictions = array_values(SimplePie_Misc::array_unique($restrictions)); 5025 } 5026 } 5027 else 5028 { 5029 $restrictions = $restrictions_parent; 5030 } 5031 5032 // THUMBNAILS 5033 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'])) 5034 { 5035 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail) 5036 { 5037 $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 5038 } 5039 if (is_array($thumbnails)) 5040 { 5041 $thumbnails = array_values(SimplePie_Misc::array_unique($thumbnails)); 5042 } 5043 } 5044 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'])) 5045 { 5046 foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail) 5047 { 5048 $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 5049 } 5050 if (is_array($thumbnails)) 5051 { 5052 $thumbnails = array_values(SimplePie_Misc::array_unique($thumbnails)); 5053 } 5054 } 5055 else 5056 { 5057 $thumbnails = $thumbnails_parent; 5058 } 5059 5060 // TITLES 5061 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'])) 5062 { 5063 $title = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5064 } 5065 elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'])) 5066 { 5067 $title = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5068 } 5069 else 5070 { 5071 $title = $title_parent; 5072 } 5073 5074 $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions, $categories, $channels, $copyrights, $credits, $description, $duration, $expression, $framerate, $hashes, $height, $keywords, $lang, $medium, $player, $ratings, $restrictions, $samplingrate, $thumbnails, $title, $width); 5075 } 5076 } 5077 } 5078 } 5079 5080 // If we have standalone media:content tags, loop through them. 5081 if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'])) 5082 { 5083 foreach ((array) $this->data['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'] as $content) 5084 { 5085 if (isset($content['attribs']['']['url']) || isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'])) 5086 { 5087 // Attributes 5088 $bitrate = null; 5089 $channels = null; 5090 $duration = null; 5091 $expression = null; 5092 $framerate = null; 5093 $height = null; 5094 $javascript = null; 5095 $lang = null; 5096 $length = null; 5097 $medium = null; 5098 $samplingrate = null; 5099 $type = null; 5100 $url = null; 5101 $width = null; 5102 5103 // Elements 5104 $captions = null; 5105 $categories = null; 5106 $copyrights = null; 5107 $credits = null; 5108 $description = null; 5109 $hashes = null; 5110 $keywords = null; 5111 $player = null; 5112 $ratings = null; 5113 $restrictions = null; 5114 $thumbnails = null; 5115 $title = null; 5116 5117 // Start checking the attributes of media:content 5118 if (isset($content['attribs']['']['bitrate'])) 5119 { 5120 $bitrate = $this->sanitize($content['attribs']['']['bitrate'], SIMPLEPIE_CONSTRUCT_TEXT); 5121 } 5122 if (isset($content['attribs']['']['channels'])) 5123 { 5124 $channels = $this->sanitize($content['attribs']['']['channels'], SIMPLEPIE_CONSTRUCT_TEXT); 5125 } 5126 if (isset($content['attribs']['']['duration'])) 5127 { 5128 $duration = $this->sanitize($content['attribs']['']['duration'], SIMPLEPIE_CONSTRUCT_TEXT); 5129 } 5130 else 5131 { 5132 $duration = $duration_parent; 5133 } 5134 if (isset($content['attribs']['']['expression'])) 5135 { 5136 $expression = $this->sanitize($content['attribs']['']['expression'], SIMPLEPIE_CONSTRUCT_TEXT); 5137 } 5138 if (isset($content['attribs']['']['framerate'])) 5139 { 5140 $framerate = $this->sanitize($content['attribs']['']['framerate'], SIMPLEPIE_CONSTRUCT_TEXT); 5141 } 5142 if (isset($content['attribs']['']['height'])) 5143 { 5144 $height = $this->sanitize($content['attribs']['']['height'], SIMPLEPIE_CONSTRUCT_TEXT); 5145 } 5146 if (isset($content['attribs']['']['lang'])) 5147 { 5148 $lang = $this->sanitize($content['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT); 5149 } 5150 if (isset($content['attribs']['']['fileSize'])) 5151 { 5152 $length = ceil($content['attribs']['']['fileSize']); 5153 } 5154 if (isset($content['attribs']['']['medium'])) 5155 { 5156 $medium = $this->sanitize($content['attribs']['']['medium'], SIMPLEPIE_CONSTRUCT_TEXT); 5157 } 5158 if (isset($content['attribs']['']['samplingrate'])) 5159 { 5160 $samplingrate = $this->sanitize($content['attribs']['']['samplingrate'], SIMPLEPIE_CONSTRUCT_TEXT); 5161 } 5162 if (isset($content['attribs']['']['type'])) 5163 { 5164 $type = $this->sanitize($content['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 5165 } 5166 if (isset($content['attribs']['']['width'])) 5167 { 5168 $width = $this->sanitize($content['attribs']['']['width'], SIMPLEPIE_CONSTRUCT_TEXT); 5169 } 5170 if (isset($content['attribs']['']['url'])) 5171 { 5172 $url = $this->sanitize($content['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 5173 } 5174 // Checking the other optional media: elements. Priority: media:content, media:group, item, channel 5175 5176 // CAPTIONS 5177 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'])) 5178 { 5179 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption) 5180 { 5181 $caption_type = null; 5182 $caption_lang = null; 5183 $caption_startTime = null; 5184 $caption_endTime = null; 5185 $caption_text = null; 5186 if (isset($caption['attribs']['']['type'])) 5187 { 5188 $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 5189 } 5190 if (isset($caption['attribs']['']['lang'])) 5191 { 5192 $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT); 5193 } 5194 if (isset($caption['attribs']['']['start'])) 5195 { 5196 $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT); 5197 } 5198 if (isset($caption['attribs']['']['end'])) 5199 { 5200 $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT); 5201 } 5202 if (isset($caption['data'])) 5203 { 5204 $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5205 } 5206 $captions[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text); 5207 } 5208 if (is_array($captions)) 5209 { 5210 $captions = array_values(SimplePie_Misc::array_unique($captions)); 5211 } 5212 } 5213 else 5214 { 5215 $captions = $captions_parent; 5216 } 5217 5218 // CATEGORIES 5219 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'])) 5220 { 5221 foreach ((array) $content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category) 5222 { 5223 $term = null; 5224 $scheme = null; 5225 $label = null; 5226 if (isset($category['data'])) 5227 { 5228 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5229 } 5230 if (isset($category['attribs']['']['scheme'])) 5231 { 5232 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 5233 } 5234 else 5235 { 5236 $scheme = 'http://search.yahoo.com/mrss/category_schema'; 5237 } 5238 if (isset($category['attribs']['']['label'])) 5239 { 5240 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 5241 } 5242 $categories[] = new $this->feed->category_class($term, $scheme, $label); 5243 } 5244 } 5245 if (is_array($categories) && is_array($categories_parent)) 5246 { 5247 $categories = array_values(SimplePie_Misc::array_unique(array_merge($categories, $categories_parent))); 5248 } 5249 elseif (is_array($categories)) 5250 { 5251 $categories = array_values(SimplePie_Misc::array_unique($categories)); 5252 } 5253 elseif (is_array($categories_parent)) 5254 { 5255 $categories = array_values(SimplePie_Misc::array_unique($categories_parent)); 5256 } 5257 else 5258 { 5259 $categories = null; 5260 } 5261 5262 // COPYRIGHTS 5263 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'])) 5264 { 5265 $copyright_url = null; 5266 $copyright_label = null; 5267 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'])) 5268 { 5269 $copyright_url = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT); 5270 } 5271 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'])) 5272 { 5273 $copyright_label = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5274 } 5275 $copyrights = new $this->feed->copyright_class($copyright_url, $copyright_label); 5276 } 5277 else 5278 { 5279 $copyrights = $copyrights_parent; 5280 } 5281 5282 // CREDITS 5283 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'])) 5284 { 5285 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit) 5286 { 5287 $credit_role = null; 5288 $credit_scheme = null; 5289 $credit_name = null; 5290 if (isset($credit['attribs']['']['role'])) 5291 { 5292 $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT); 5293 } 5294 if (isset($credit['attribs']['']['scheme'])) 5295 { 5296 $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 5297 } 5298 else 5299 { 5300 $credit_scheme = 'urn:ebu'; 5301 } 5302 if (isset($credit['data'])) 5303 { 5304 $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5305 } 5306 $credits[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name); 5307 } 5308 if (is_array($credits)) 5309 { 5310 $credits = array_values(SimplePie_Misc::array_unique($credits)); 5311 } 5312 } 5313 else 5314 { 5315 $credits = $credits_parent; 5316 } 5317 5318 // DESCRIPTION 5319 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'])) 5320 { 5321 $description = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5322 } 5323 else 5324 { 5325 $description = $description_parent; 5326 } 5327 5328 // HASHES 5329 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'])) 5330 { 5331 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash) 5332 { 5333 $value = null; 5334 $algo = null; 5335 if (isset($hash['data'])) 5336 { 5337 $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5338 } 5339 if (isset($hash['attribs']['']['algo'])) 5340 { 5341 $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT); 5342 } 5343 else 5344 { 5345 $algo = 'md5'; 5346 } 5347 $hashes[] = $algo.':'.$value; 5348 } 5349 if (is_array($hashes)) 5350 { 5351 $hashes = array_values(SimplePie_Misc::array_unique($hashes)); 5352 } 5353 } 5354 else 5355 { 5356 $hashes = $hashes_parent; 5357 } 5358 5359 // KEYWORDS 5360 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'])) 5361 { 5362 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'])) 5363 { 5364 $temp = explode(',', $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)); 5365 foreach ($temp as $word) 5366 { 5367 $keywords[] = trim($word); 5368 } 5369 unset($temp); 5370 } 5371 if (is_array($keywords)) 5372 { 5373 $keywords = array_values(SimplePie_Misc::array_unique($keywords)); 5374 } 5375 } 5376 else 5377 { 5378 $keywords = $keywords_parent; 5379 } 5380 5381 // PLAYER 5382 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'])) 5383 { 5384 $player = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 5385 } 5386 else 5387 { 5388 $player = $player_parent; 5389 } 5390 5391 // RATINGS 5392 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'])) 5393 { 5394 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating) 5395 { 5396 $rating_scheme = null; 5397 $rating_value = null; 5398 if (isset($rating['attribs']['']['scheme'])) 5399 { 5400 $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 5401 } 5402 else 5403 { 5404 $rating_scheme = 'urn:simple'; 5405 } 5406 if (isset($rating['data'])) 5407 { 5408 $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5409 } 5410 $ratings[] = new $this->feed->rating_class($rating_scheme, $rating_value); 5411 } 5412 if (is_array($ratings)) 5413 { 5414 $ratings = array_values(SimplePie_Misc::array_unique($ratings)); 5415 } 5416 } 5417 else 5418 { 5419 $ratings = $ratings_parent; 5420 } 5421 5422 // RESTRICTIONS 5423 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'])) 5424 { 5425 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction) 5426 { 5427 $restriction_relationship = null; 5428 $restriction_type = null; 5429 $restriction_value = null; 5430 if (isset($restriction['attribs']['']['relationship'])) 5431 { 5432 $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT); 5433 } 5434 if (isset($restriction['attribs']['']['type'])) 5435 { 5436 $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 5437 } 5438 if (isset($restriction['data'])) 5439 { 5440 $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5441 } 5442 $restrictions[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value); 5443 } 5444 if (is_array($restrictions)) 5445 { 5446 $restrictions = array_values(SimplePie_Misc::array_unique($restrictions)); 5447 } 5448 } 5449 else 5450 { 5451 $restrictions = $restrictions_parent; 5452 } 5453 5454 // THUMBNAILS 5455 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'])) 5456 { 5457 foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail) 5458 { 5459 $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI); 5460 } 5461 if (is_array($thumbnails)) 5462 { 5463 $thumbnails = array_values(SimplePie_Misc::array_unique($thumbnails)); 5464 } 5465 } 5466 else 5467 { 5468 $thumbnails = $thumbnails_parent; 5469 } 5470 5471 // TITLES 5472 if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'])) 5473 { 5474 $title = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5475 } 5476 else 5477 { 5478 $title = $title_parent; 5479 } 5480 5481 $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions, $categories, $channels, $copyrights, $credits, $description, $duration, $expression, $framerate, $hashes, $height, $keywords, $lang, $medium, $player, $ratings, $restrictions, $samplingrate, $thumbnails, $title, $width); 5482 } 5483 } 5484 } 5485 5486 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link') as $link) 5487 { 5488 if (isset($link['attribs']['']['href']) && !empty($link['attribs']['']['rel']) && $link['attribs']['']['rel'] === 'enclosure') 5489 { 5490 // Attributes 5491 $bitrate = null; 5492 $channels = null; 5493 $duration = null; 5494 $expression = null; 5495 $framerate = null; 5496 $height = null; 5497 $javascript = null; 5498 $lang = null; 5499 $length = null; 5500 $medium = null; 5501 $samplingrate = null; 5502 $type = null; 5503 $url = null; 5504 $width = null; 5505 5506 $url = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 5507 if (isset($link['attribs']['']['type'])) 5508 { 5509 $type = $this->sanitize($link['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 5510 } 5511 if (isset($link['attribs']['']['length'])) 5512 { 5513 $length = ceil($link['attribs']['']['length']); 5514 } 5515 5516 // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor 5517 $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width); 5518 } 5519 } 5520 5521 foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link') as $link) 5522 { 5523 if (isset($link['attribs']['']['href']) && !empty($link['attribs']['']['rel']) && $link['attribs']['']['rel'] === 'enclosure') 5524 { 5525 // Attributes 5526 $bitrate = null; 5527 $channels = null; 5528 $duration = null; 5529 $expression = null; 5530 $framerate = null; 5531 $height = null; 5532 $javascript = null; 5533 $lang = null; 5534 $length = null; 5535 $medium = null; 5536 $samplingrate = null; 5537 $type = null; 5538 $url = null; 5539 $width = null; 5540 5541 $url = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 5542 if (isset($link['attribs']['']['type'])) 5543 { 5544 $type = $this->sanitize($link['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 5545 } 5546 if (isset($link['attribs']['']['length'])) 5547 { 5548 $length = ceil($link['attribs']['']['length']); 5549 } 5550 5551 // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor 5552 $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width); 5553 } 5554 } 5555 5556 if ($enclosure = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'enclosure')) 5557 { 5558 if (isset($enclosure[0]['attribs']['']['url'])) 5559 { 5560 // Attributes 5561 $bitrate = null; 5562 $channels = null; 5563 $duration = null; 5564 $expression = null; 5565 $framerate = null; 5566 $height = null; 5567 $javascript = null; 5568 $lang = null; 5569 $length = null; 5570 $medium = null; 5571 $samplingrate = null; 5572 $type = null; 5573 $url = null; 5574 $width = null; 5575 5576 $url = $this->sanitize($enclosure[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($enclosure[0])); 5577 if (isset($enclosure[0]['attribs']['']['type'])) 5578 { 5579 $type = $this->sanitize($enclosure[0]['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT); 5580 } 5581 if (isset($enclosure[0]['attribs']['']['length'])) 5582 { 5583 $length = ceil($enclosure[0]['attribs']['']['length']); 5584 } 5585 5586 // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor 5587 $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width); 5588 } 5589 } 5590 5591 if (sizeof($this->data['enclosures']) === 0 && ($url || $type || $length || $bitrate || $captions_parent || $categories_parent || $channels || $copyrights_parent || $credits_parent || $description_parent || $duration_parent || $expression || $framerate || $hashes_parent || $height || $keywords_parent || $lang || $medium || $player_parent || $ratings_parent || $restrictions_parent || $samplingrate || $thumbnails_parent || $title_parent || $width)) 5592 { 5593 // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor 5594 $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width); 5595 } 5596 5597 $this->data['enclosures'] = array_values(SimplePie_Misc::array_unique($this->data['enclosures'])); 5598 } 5599 if (!empty($this->data['enclosures'])) 5600 { 5601 return $this->data['enclosures']; 5602 } 5603 else 5604 { 5605 return null; 5606 } 5607 } 5608 5609 function get_latitude() 5610 { 5611 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat')) 5612 { 5613 return (float) $return[0]['data']; 5614 } 5615 elseif (($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match)) 5616 { 5617 return (float) $match[1]; 5618 } 5619 else 5620 { 5621 return null; 5622 } 5623 } 5624 5625 function get_longitude() 5626 { 5627 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long')) 5628 { 5629 return (float) $return[0]['data']; 5630 } 5631 elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon')) 5632 { 5633 return (float) $return[0]['data']; 5634 } 5635 elseif (($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match)) 5636 { 5637 return (float) $match[2]; 5638 } 5639 else 5640 { 5641 return null; 5642 } 5643 } 5644 5645 function get_source() 5646 { 5647 if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'source')) 5648 { 5649 return new $this->feed->source_class($this, $return[0]); 5650 } 5651 else 5652 { 5653 return null; 5654 } 5655 } 5656 5657 /** 5658 * Creates the add_to_* methods' return data 5659 * 5660 * @access private 5661 * @param string $item_url String to prefix to the item permalink 5662 * @param string $title_url String to prefix to the item title 5663 * (and suffix to the item permalink) 5664 * @return mixed URL if feed exists, false otherwise 5665 */ 5666 function add_to_service($item_url, $title_url = null, $summary_url = null) 5667 { 5668 if ($this->get_permalink() !== null) 5669 { 5670 $return = $item_url . rawurlencode($this->get_permalink()); 5671 if ($title_url !== null && $this->get_title() !== null) 5672 { 5673 $return .= $title_url . rawurlencode($this->get_title()); 5674 } 5675 if ($summary_url !== null && $this->get_description() !== null) 5676 { 5677 $return .= $summary_url . rawurlencode($this->get_description()); 5678 } 5679 return $this->sanitize($return, SIMPLEPIE_CONSTRUCT_IRI); 5680 } 5681 else 5682 { 5683 return null; 5684 } 5685 } 5686 5687 function add_to_blinklist() 5688 { 5689 return $this->add_to_service('http://www.blinklist.com/index.php?Action=Blink/addblink.php&Description=&Url=', '&Title='); 5690 } 5691 5692 function add_to_blogmarks() 5693 { 5694 return $this->add_to_service('http://blogmarks.net/my/new.php?mini=1&simple=1&url=', '&title='); 5695 } 5696 5697 function add_to_delicious() 5698 { 5699 return $this->add_to_service('http://del.icio.us/post/?v=4&url=', '&title='); 5700 } 5701 5702 function add_to_digg() 5703 { 5704 return $this->add_to_service('http://digg.com/submit?url=', '&title=', '&bodytext='); 5705 } 5706 5707 function add_to_furl() 5708 { 5709 return $this->add_to_service('http://www.furl.net/storeIt.jsp?u=', '&t='); 5710 } 5711 5712 function add_to_magnolia() 5713 { 5714 return $this->add_to_service('http://ma.gnolia.com/bookmarklet/add?url=', '&title='); 5715 } 5716 5717 function add_to_myweb20() 5718 { 5719 return $this->add_to_service('http://myweb2.search.yahoo.com/myresults/bookmarklet?u=', '&t='); 5720 } 5721 5722 function add_to_newsvine() 5723 { 5724 return $this->add_to_service('http://www.newsvine.com/_wine/save?u=', '&h='); 5725 } 5726 5727 function add_to_reddit() 5728 { 5729 return $this->add_to_service('http://reddit.com/submit?url=', '&title='); 5730 } 5731 5732 function add_to_segnalo() 5733 { 5734 return $this->add_to_service('http://segnalo.com/post.html.php?url=', '&title='); 5735 } 5736 5737 function add_to_simpy() 5738 { 5739 return $this->add_to_service('http://www.simpy.com/simpy/LinkAdd.do?href=', '&title='); 5740 } 5741 5742 function add_to_spurl() 5743 { 5744 return $this->add_to_service('http://www.spurl.net/spurl.php?v=3&url=', '&title='); 5745 } 5746 5747 function add_to_wists() 5748 { 5749 return $this->add_to_service('http://wists.com/r.php?c=&r=', '&title='); 5750 } 5751 5752 function search_technorati() 5753 { 5754 return $this->add_to_service('http://www.technorati.com/search/'); 5755 } 5756 } 5757 5758 class SimplePie_Source 5759 { 5760 var $item; 5761 var $data = array(); 5762 5763 function SimplePie_Source($item, $data) 5764 { 5765 $this->item = $item; 5766 $this->data = $data; 5767 } 5768 5769 function __toString() 5770 { 5771 return md5(serialize($this->data)); 5772 } 5773 5774 function get_source_tags($namespace, $tag) 5775 { 5776 if (isset($this->data['child'][$namespace][$tag])) 5777 { 5778 return $this->data['child'][$namespace][$tag]; 5779 } 5780 else 5781 { 5782 return null; 5783 } 5784 } 5785 5786 function get_base($element = array()) 5787 { 5788 return $this->item->get_base($element); 5789 } 5790 5791 function sanitize($data, $type, $base = '') 5792 { 5793 return $this->item->sanitize($data, $type, $base); 5794 } 5795 5796 function get_item() 5797 { 5798 return $this->item; 5799 } 5800 5801 function get_title() 5802 { 5803 if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title')) 5804 { 5805 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 5806 } 5807 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title')) 5808 { 5809 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 5810 } 5811 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title')) 5812 { 5813 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 5814 } 5815 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title')) 5816 { 5817 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 5818 } 5819 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title')) 5820 { 5821 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 5822 } 5823 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title')) 5824 { 5825 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5826 } 5827 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title')) 5828 { 5829 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5830 } 5831 else 5832 { 5833 return null; 5834 } 5835 } 5836 5837 function get_category($key = 0) 5838 { 5839 $categories = $this->get_categories(); 5840 if (isset($categories[$key])) 5841 { 5842 return $categories[$key]; 5843 } 5844 else 5845 { 5846 return null; 5847 } 5848 } 5849 5850 function get_categories() 5851 { 5852 $categories = array(); 5853 5854 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category) 5855 { 5856 $term = null; 5857 $scheme = null; 5858 $label = null; 5859 if (isset($category['attribs']['']['term'])) 5860 { 5861 $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT); 5862 } 5863 if (isset($category['attribs']['']['scheme'])) 5864 { 5865 $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT); 5866 } 5867 if (isset($category['attribs']['']['label'])) 5868 { 5869 $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT); 5870 } 5871 $categories[] = new $this->item->feed->category_class($term, $scheme, $label); 5872 } 5873 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category) 5874 { 5875 // This is really the label, but keep this as the term also for BC. 5876 // Label will also work on retrieving because that falls back to term. 5877 $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5878 if (isset($category['attribs']['']['domain'])) 5879 { 5880 $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT); 5881 } 5882 else 5883 { 5884 $scheme = null; 5885 } 5886 $categories[] = new $this->item->feed->category_class($term, $scheme, null); 5887 } 5888 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category) 5889 { 5890 $categories[] = new $this->item->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 5891 } 5892 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category) 5893 { 5894 $categories[] = new $this->item->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 5895 } 5896 5897 if (!empty($categories)) 5898 { 5899 return SimplePie_Misc::array_unique($categories); 5900 } 5901 else 5902 { 5903 return null; 5904 } 5905 } 5906 5907 function get_author($key = 0) 5908 { 5909 $authors = $this->get_authors(); 5910 if (isset($authors[$key])) 5911 { 5912 return $authors[$key]; 5913 } 5914 else 5915 { 5916 return null; 5917 } 5918 } 5919 5920 function get_authors() 5921 { 5922 $authors = array(); 5923 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author) 5924 { 5925 $name = null; 5926 $uri = null; 5927 $email = null; 5928 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'])) 5929 { 5930 $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5931 } 5932 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'])) 5933 { 5934 $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0])); 5935 } 5936 if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'])) 5937 { 5938 $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5939 } 5940 if ($name !== null || $email !== null || $uri !== null) 5941 { 5942 $authors[] = new $this->item->feed->author_class($name, $uri, $email); 5943 } 5944 } 5945 if ($author = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author')) 5946 { 5947 $name = null; 5948 $url = null; 5949 $email = null; 5950 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'])) 5951 { 5952 $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5953 } 5954 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'])) 5955 { 5956 $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0])); 5957 } 5958 if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'])) 5959 { 5960 $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 5961 } 5962 if ($name !== null || $email !== null || $url !== null) 5963 { 5964 $authors[] = new $this->item->feed->author_class($name, $url, $email); 5965 } 5966 } 5967 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author) 5968 { 5969 $authors[] = new $this->item->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 5970 } 5971 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author) 5972 { 5973 $authors[] = new $this->item->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 5974 } 5975 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author) 5976 { 5977 $authors[] = new $this->item->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null); 5978 } 5979 5980 if (!empty($authors)) 5981 { 5982 return SimplePie_Misc::array_unique($authors); 5983 } 5984 else 5985 { 5986 return null; 5987 } 5988 } 5989 5990 function get_contributor($key = 0) 5991 { 5992 $contributors = $this->get_contributors(); 5993 if (isset($contributors[$key])) 5994 { 5995 return $contributors[$key]; 5996 } 5997 else 5998 { 5999 return null; 6000 } 6001 } 6002 6003 function get_contributors() 6004 { 6005 $contributors = array(); 6006 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor) 6007 { 6008 $name = null; 6009 $uri = null; 6010 $email = null; 6011 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'])) 6012 { 6013 $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6014 } 6015 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'])) 6016 { 6017 $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0])); 6018 } 6019 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'])) 6020 { 6021 $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6022 } 6023 if ($name !== null || $email !== null || $uri !== null) 6024 { 6025 $contributors[] = new $this->item->feed->author_class($name, $uri, $email); 6026 } 6027 } 6028 foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor) 6029 { 6030 $name = null; 6031 $url = null; 6032 $email = null; 6033 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'])) 6034 { 6035 $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6036 } 6037 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'])) 6038 { 6039 $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0])); 6040 } 6041 if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'])) 6042 { 6043 $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6044 } 6045 if ($name !== null || $email !== null || $url !== null) 6046 { 6047 $contributors[] = new $this->item->feed->author_class($name, $url, $email); 6048 } 6049 } 6050 6051 if (!empty($contributors)) 6052 { 6053 return SimplePie_Misc::array_unique($contributors); 6054 } 6055 else 6056 { 6057 return null; 6058 } 6059 } 6060 6061 function get_link($key = 0, $rel = 'alternate') 6062 { 6063 $links = $this->get_links($rel); 6064 if (isset($links[$key])) 6065 { 6066 return $links[$key]; 6067 } 6068 else 6069 { 6070 return null; 6071 } 6072 } 6073 6074 /** 6075 * Added for parity between the parent-level and the item/entry-level. 6076 */ 6077 function get_permalink() 6078 { 6079 return $this->get_link(0); 6080 } 6081 6082 function get_links($rel = 'alternate') 6083 { 6084 if (!isset($this->data['links'])) 6085 { 6086 $this->data['links'] = array(); 6087 if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link')) 6088 { 6089 foreach ($links as $link) 6090 { 6091 if (isset($link['attribs']['']['href'])) 6092 { 6093 $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate'; 6094 $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 6095 } 6096 } 6097 } 6098 if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link')) 6099 { 6100 foreach ($links as $link) 6101 { 6102 if (isset($link['attribs']['']['href'])) 6103 { 6104 $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate'; 6105 $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link)); 6106 6107 } 6108 } 6109 } 6110 if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link')) 6111 { 6112 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 6113 } 6114 if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link')) 6115 { 6116 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 6117 } 6118 if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link')) 6119 { 6120 $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0])); 6121 } 6122 6123 $keys = array_keys($this->data['links']); 6124 foreach ($keys as $key) 6125 { 6126 if (SimplePie_Misc::is_isegment_nz_nc($key)) 6127 { 6128 if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key])) 6129 { 6130 $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]); 6131 $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]; 6132 } 6133 else 6134 { 6135 $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key]; 6136 } 6137 } 6138 elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY) 6139 { 6140 $this->data['links'][substr($key, 41)] =& $this->data['links'][$key]; 6141 } 6142 $this->data['links'][$key] = array_unique($this->data['links'][$key]); 6143 } 6144 } 6145 6146 if (isset($this->data['links'][$rel])) 6147 { 6148 return $this->data['links'][$rel]; 6149 } 6150 else 6151 { 6152 return null; 6153 } 6154 } 6155 6156 function get_description() 6157 { 6158 if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'subtitle')) 6159 { 6160 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 6161 } 6162 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'tagline')) 6163 { 6164 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 6165 } 6166 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description')) 6167 { 6168 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 6169 } 6170 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description')) 6171 { 6172 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 6173 } 6174 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description')) 6175 { 6176 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0])); 6177 } 6178 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description')) 6179 { 6180 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6181 } 6182 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description')) 6183 { 6184 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6185 } 6186 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary')) 6187 { 6188 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 6189 } 6190 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle')) 6191 { 6192 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0])); 6193 } 6194 else 6195 { 6196 return null; 6197 } 6198 } 6199 6200 function get_copyright() 6201 { 6202 if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights')) 6203 { 6204 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0])); 6205 } 6206 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'copyright')) 6207 { 6208 return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0])); 6209 } 6210 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'copyright')) 6211 { 6212 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6213 } 6214 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights')) 6215 { 6216 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6217 } 6218 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights')) 6219 { 6220 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6221 } 6222 else 6223 { 6224 return null; 6225 } 6226 } 6227 6228 function get_language() 6229 { 6230 if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'language')) 6231 { 6232 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6233 } 6234 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'language')) 6235 { 6236 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6237 } 6238 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'language')) 6239 { 6240 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT); 6241 } 6242 elseif (isset($this->data['xml_lang'])) 6243 { 6244 return $this->sanitize($this->data['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT); 6245 } 6246 else 6247 { 6248 return null; 6249 } 6250 } 6251 6252 function get_latitude() 6253 { 6254 if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat')) 6255 { 6256 return (float) $return[0]['data']; 6257 } 6258 elseif (($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match)) 6259 { 6260 return (float) $match[1]; 6261 } 6262 else 6263 { 6264 return null; 6265 } 6266 } 6267 6268 function get_longitude() 6269 { 6270 if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long')) 6271 { 6272 return (float) $return[0]['data']; 6273 } 6274 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon')) 6275 { 6276 return (float) $return[0]['data']; 6277 } 6278 elseif (($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match)) 6279 { 6280 return (float) $match[2]; 6281 } 6282 else 6283 { 6284 return null; 6285 } 6286 } 6287 6288 function get_image_url() 6289 { 6290 if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'image')) 6291 { 6292 return $this->sanitize($return[0]['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI); 6293 } 6294 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'logo')) 6295 { 6296 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 6297 } 6298 elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon')) 6299 { 6300 return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0])); 6301 } 6302 else 6303 { 6304 return null; 6305 } 6306 } 6307 } 6308 6309 class SimplePie_Author 6310 { 6311 var $name; 6312 var $link; 6313 var $email; 6314 6315 // Constructor, used to input the data 6316 function SimplePie_Author($name = null, $link = null, $email = null) 6317 { 6318 $this->name = $name; 6319 $this->link = $link; 6320 $this->email = $email; 6321 } 6322 6323 function __toString() 6324 { 6325 // There is no $this->data here 6326 return md5(serialize($this)); 6327 } 6328 6329 function get_name() 6330 { 6331 if ($this->name !== null) 6332 { 6333 return $this->name; 6334 } 6335 else 6336 { 6337 return null; 6338 } 6339 } 6340 6341 function get_link() 6342 { 6343 if ($this->link !== null) 6344 { 6345 return $this->link; 6346 } 6347 else 6348 { 6349 return null; 6350 } 6351 } 6352 6353 function get_email() 6354 { 6355 if ($this->email !== null) 6356 { 6357 return $this->email; 6358 } 6359 else 6360 { 6361 return null; 6362 } 6363 } 6364 } 6365 6366 class SimplePie_Category 6367 { 6368 var $term; 6369 var $scheme; 6370 var $label; 6371 6372 // Constructor, used to input the data 6373 function SimplePie_Category($term = null, $scheme = null, $label = null) 6374 { 6375 $this->term = $term; 6376 $this->scheme = $scheme; 6377 $this->label = $label; 6378 } 6379 6380 function __toString() 6381 { 6382 // There is no $this->data here 6383 return md5(serialize($this)); 6384 } 6385 6386 function get_term() 6387 { 6388 if ($this->term !== null) 6389 { 6390 return $this->term; 6391 } 6392 else 6393 { 6394 return null; 6395 } 6396 } 6397 6398 function get_scheme() 6399 { 6400 if ($this->scheme !== null) 6401 { 6402 return $this->scheme; 6403 } 6404 else 6405 { 6406 return null; 6407 } 6408 } 6409 6410 function get_label() 6411 { 6412 if ($this->label !== null) 6413 { 6414 return $this->label; 6415 } 6416 else 6417 { 6418 return $this->get_term(); 6419 } 6420 } 6421 } 6422 6423 class SimplePie_Enclosure 6424 { 6425 var $bitrate; 6426 var $captions; 6427 var $categories; 6428 var $channels; 6429 var $copyright; 6430 var $credits; 6431 var $description; 6432 var $duration; 6433 var $expression; 6434 var $framerate; 6435 var $handler; 6436 var $hashes; 6437 var $height; 6438 var $javascript; 6439 var $keywords; 6440 var $lang; 6441 var $length; 6442 var $link; 6443 var $medium; 6444 var $player; 6445 var $ratings; 6446 var $restrictions; 6447 var $samplingrate; 6448 var $thumbnails; 6449 var $title; 6450 var $type; 6451 var $width; 6452 6453 // Constructor, used to input the data 6454 function SimplePie_Enclosure($link = null, $type = null, $length = null, $javascript = null, $bitrate = null, $captions = null, $categories = null, $channels = null, $copyright = null, $credits = null, $description = null, $duration = null, $expression = null, $framerate = null, $hashes = null, $height = null, $keywords = null, $lang = null, $medium = null, $player = null, $ratings = null, $restrictions = null, $samplingrate = null, $thumbnails = null, $title = null, $width = null) 6455 { 6456 $this->bitrate = $bitrate; 6457 $this->captions = $captions; 6458 $this->categories = $categories; 6459 $this->channels = $channels; 6460 $this->copyright = $copyright; 6461 $this->credits = $credits; 6462 $this->description = $description; 6463 $this->duration = $duration; 6464 $this->expression = $expression; 6465 $this->framerate = $framerate; 6466 $this->hashes = $hashes; 6467 $this->height = $height; 6468 $this->javascript = $javascript; 6469 $this->keywords = $keywords; 6470 $this->lang = $lang; 6471 $this->length = $length; 6472 $this->link = $link; 6473 $this->medium = $medium; 6474 $this->player = $player; 6475 $this->ratings = $ratings; 6476 $this->restrictions = $restrictions; 6477 $this->samplingrate = $samplingrate; 6478 $this->thumbnails = $thumbnails; 6479 $this->title = $title; 6480 $this->type = $type; 6481 $this->width = $width; 6482 if (class_exists('idna_convert')) 6483 { 6484 $idn = new idna_convert(); 6485 $parsed = SimplePie_Misc::parse_url($link); 6486 $this->link = SimplePie_Misc::compress_parse_url($parsed['scheme'], $idn->encode($parsed['authority']), $parsed['path'], $parsed['query'], $parsed['fragment']); 6487 } 6488 $this->handler = $this->get_handler(); // Needs to load last 6489 } 6490 6491 function __toString() 6492 { 6493 // There is no $this->data here 6494 return md5(serialize($this)); 6495 } 6496 6497 function get_bitrate() 6498 { 6499 if ($this->bitrate !== null) 6500 { 6501 return $this->bitrate; 6502 } 6503 else 6504 { 6505 return null; 6506 } 6507 } 6508 6509 function get_caption($key = 0) 6510 { 6511 $captions = $this->get_captions(); 6512 if (isset($captions[$key])) 6513 { 6514 return $captions[$key]; 6515 } 6516 else 6517 { 6518 return null; 6519 } 6520 } 6521 6522 function get_captions() 6523 { 6524 if ($this->captions !== null) 6525 { 6526 return $this->captions; 6527 } 6528 else 6529 { 6530 return null; 6531 } 6532 } 6533 6534 function get_category($key = 0) 6535 { 6536 $categories = $this->get_categories(); 6537 if (isset($categories[$key])) 6538 { 6539 return $categories[$key]; 6540 } 6541 else 6542 { 6543 return null; 6544 } 6545 } 6546 6547 function get_categories() 6548 { 6549 if ($this->categories !== null) 6550 { 6551 return $this->categories; 6552 } 6553 else 6554 { 6555 return null; 6556 } 6557 } 6558 6559 function get_channels() 6560 { 6561 if ($this->channels !== null) 6562 { 6563 return $this->channels; 6564 } 6565 else 6566 { 6567 return null; 6568 } 6569 } 6570 6571 function get_copyright() 6572 { 6573 if ($this->copyright !== null) 6574 { 6575 return $this->copyright; 6576 } 6577 else 6578 { 6579 return null; 6580 } 6581 } 6582 6583 function get_credit($key = 0) 6584 { 6585 $credits = $this->get_credits(); 6586 if (isset($credits[$key])) 6587 { 6588 return $credits[$key]; 6589 } 6590 else 6591 { 6592 return null; 6593 } 6594 } 6595 6596 function get_credits() 6597 { 6598 if ($this->credits !== null) 6599 { 6600 return $this->credits; 6601 } 6602 else 6603 { 6604 return null; 6605 } 6606 } 6607 6608 function get_description() 6609 { 6610 if ($this->description !== null) 6611 { 6612 return $this->description; 6613 } 6614 else 6615 { 6616 return null; 6617 } 6618 } 6619 6620 function get_duration($convert = false) 6621 { 6622 if ($this->duration !== null) 6623 { 6624 if ($convert) 6625 { 6626 $time = SimplePie_Misc::time_hms($this->duration); 6627 return $time; 6628 } 6629 else 6630 { 6631 return $this->duration; 6632 } 6633 } 6634 else 6635 { 6636 return null; 6637 } 6638 } 6639 6640 function get_expression() 6641 { 6642 if ($this->expression !== null) 6643 { 6644 return $this->expression; 6645 } 6646 else 6647 { 6648 return 'full'; 6649 } 6650 } 6651 6652 function get_extension() 6653 { 6654 if ($this->link !== null) 6655 { 6656 $url = SimplePie_Misc::parse_url($this->link); 6657 if ($url['path'] !== '') 6658 { 6659 return pathinfo($url['path'], PATHINFO_EXTENSION); 6660 } 6661 } 6662 return null; 6663 } 6664 6665 function get_framerate() 6666 { 6667 if ($this->framerate !== null) 6668 { 6669 return $this->framerate; 6670 } 6671 else 6672 { 6673 return null; 6674 } 6675 } 6676 6677 function get_handler() 6678 { 6679 return $this->get_real_type(true); 6680 } 6681 6682 function get_hash($key = 0) 6683 { 6684 $hashes = $this->get_hashes(); 6685 if (isset($hashes[$key])) 6686 { 6687 return $hashes[$key]; 6688 } 6689 else 6690 { 6691 return null; 6692 } 6693 } 6694 6695 function get_hashes() 6696 { 6697 if ($this->hashes !== null) 6698 { 6699 return $this->hashes; 6700 } 6701 else 6702 { 6703 return null; 6704 } 6705 } 6706 6707 function get_height() 6708 { 6709 if ($this->height !== null) 6710 { 6711 return $this->height; 6712 } 6713 else 6714 { 6715 return null; 6716 } 6717 } 6718 6719 function get_language() 6720 { 6721 if ($this->lang !== null) 6722 { 6723 return $this->lang; 6724 } 6725 else 6726 { 6727 return null; 6728 } 6729 } 6730 6731 function get_keyword($key = 0) 6732 { 6733 $keywords = $this->get_keywords(); 6734 if (isset($keywords[$key])) 6735 { 6736 return $keywords[$key]; 6737 } 6738 else 6739 { 6740 return null; 6741 } 6742 } 6743 6744 function get_keywords() 6745 { 6746 if ($this->keywords !== null) 6747 { 6748 return $this->keywords; 6749 } 6750 else 6751 { 6752 return null; 6753 } 6754 } 6755 6756 function get_length() 6757 { 6758 if ($this->length !== null) 6759 { 6760 return $this->length; 6761 } 6762 else 6763 { 6764 return null; 6765 } 6766 } 6767 6768 function get_link() 6769 { 6770 if ($this->link !== null) 6771 { 6772 return urldecode($this->link); 6773 } 6774 else 6775 { 6776 return null; 6777 } 6778 } 6779 6780 function get_medium() 6781 { 6782 if ($this->medium !== null) 6783 { 6784 return $this->medium; 6785 } 6786 else 6787 { 6788 return null; 6789 } 6790 } 6791 6792 function get_player() 6793 { 6794 if ($this->player !== null) 6795 { 6796 return $this->player; 6797 } 6798 else 6799 { 6800 return null; 6801 } 6802 } 6803 6804 function get_rating($key = 0) 6805 { 6806 $ratings = $this->get_ratings(); 6807 if (isset($ratings[$key])) 6808 { 6809 return $ratings[$key]; 6810 } 6811 else 6812 { 6813 return null; 6814 } 6815 } 6816 6817 function get_ratings() 6818 { 6819 if ($this->ratings !== null) 6820 { 6821 return $this->ratings; 6822 } 6823 else 6824 { 6825 return null; 6826 } 6827 } 6828 6829 function get_restriction($key = 0) 6830 { 6831 $restrictions = $this->get_restrictions(); 6832 if (isset($restrictions[$key])) 6833 { 6834 return $restrictions[$key]; 6835 } 6836 else 6837 { 6838 return null; 6839 } 6840 } 6841 6842 function get_restrictions() 6843 { 6844 if ($this->restrictions !== null) 6845 { 6846 return $this->restrictions; 6847 } 6848 else 6849 { 6850 return null; 6851 } 6852 } 6853 6854 function get_sampling_rate() 6855 { 6856 if ($this->samplingrate !== null) 6857 { 6858 return $this->samplingrate; 6859 } 6860 else 6861 { 6862 return null; 6863 } 6864 } 6865 6866 function get_size() 6867 { 6868 $length = $this->get_length(); 6869 if ($length !== null) 6870 { 6871 return round($length/1048576, 2); 6872 } 6873 else 6874 { 6875 return null; 6876 } 6877 } 6878 6879 function get_thumbnail($key = 0) 6880 { 6881 $thumbnails = $this->get_thumbnails(); 6882 if (isset($thumbnails[$key])) 6883 { 6884 return $thumbnails[$key]; 6885 } 6886 else 6887 { 6888 return null; 6889 } 6890 } 6891 6892 function get_thumbnails() 6893 { 6894 if ($this->thumbnails !== null) 6895 { 6896 return $this->thumbnails; 6897 } 6898 else 6899 { 6900 return null; 6901 } 6902 } 6903 6904 function get_title() 6905 { 6906 if ($this->title !== null) 6907 { 6908 return $this->title; 6909 } 6910 else 6911 { 6912 return null; 6913 } 6914 } 6915 6916 function get_type() 6917 { 6918 if ($this->type !== null) 6919 { 6920 return $this->type; 6921 } 6922 else 6923 { 6924 return null; 6925 } 6926 } 6927 6928 function get_width() 6929 { 6930 if ($this->width !== null) 6931 { 6932 return $this->width; 6933 } 6934 else 6935 { 6936 return null; 6937 } 6938 } 6939 6940 function native_embed($options='') 6941 { 6942 return $this->embed($options, true); 6943 } 6944 6945 /** 6946 * @todo If the dimensions for media:content are defined, use them when width/height are set to 'auto'. 6947 */ 6948 function embed($options = '', $native = false) 6949 { 6950 // Set up defaults 6951 $audio = ''; 6952 $video = ''; 6953 $alt = ''; 6954 $altclass = ''; 6955 $loop = 'false'; 6956 $width = 'auto'; 6957 $height = 'auto'; 6958 $bgcolor = '#ffffff'; 6959 $mediaplayer = ''; 6960 $widescreen = false; 6961 $handler = $this->get_handler(); 6962 $type = $this->get_real_type(); 6963 6964 // Process options and reassign values as necessary 6965 if (is_array($options)) 6966 { 6967 extract($options); 6968 } 6969 else 6970 { 6971 $options = explode(',', $options); 6972 foreach($options as $option) 6973 { 6974 $opt = explode(':', $option, 2); 6975 if (isset($opt[0], $opt[1])) 6976 { 6977 $opt[0] = trim($opt[0]); 6978 $opt[1] = trim($opt[1]); 6979 switch ($opt[0]) 6980 { 6981 case 'audio': 6982 $audio = $opt[1]; 6983 break; 6984 6985 case 'video': 6986 $video = $opt[1]; 6987 break; 6988 6989 case 'alt': 6990 $alt = $opt[1]; 6991 break; 6992 6993 case 'altclass': 6994 $altclass = $opt[1]; 6995 break; 6996 6997 case 'loop': 6998 $loop = $opt[1]; 6999 break; 7000 7001 case 'width': 7002 $width = $opt[1]; 7003 break; 7004 7005 case 'height': 7006 $height = $opt[1]; 7007 break; 7008 7009 case 'bgcolor': 7010 $bgcolor = $opt[1]; 7011 break; 7012 7013 case 'mediaplayer': 7014 $mediaplayer = $opt[1]; 7015 break; 7016 7017 case 'widescreen': 7018 $widescreen = $opt[1]; 7019 break; 7020 } 7021 } 7022 } 7023 } 7024 7025 $mime = explode('/', $type, 2); 7026 $mime = $mime[0]; 7027 7028 // Process values for 'auto' 7029 if ($width === 'auto') 7030 { 7031 if ($mime === 'video') 7032 { 7033 if ($height === 'auto') 7034 { 7035 $width = 480; 7036 } 7037 elseif ($widescreen) 7038 { 7039 $width = round((intval($height)/9)*16); 7040 } 7041 else 7042 { 7043 $width = round((intval($height)/3)*4); 7044 } 7045 } 7046 else 7047 { 7048 $width = '100%'; 7049 } 7050 } 7051 7052 if ($height === 'auto') 7053 { 7054 if ($mime === 'audio') 7055 { 7056 $height = 0; 7057 } 7058 elseif ($mime === 'video') 7059 { 7060 if ($width === 'auto') 7061 { 7062 if ($widescreen) 7063 { 7064 $height = 270; 7065 } 7066 else 7067 { 7068 $height = 360; 7069 } 7070 } 7071 elseif ($widescreen) 7072 { 7073 $height = round((intval($width)/16)*9); 7074 } 7075 else 7076 { 7077 $height = round((intval($width)/4)*3); 7078 } 7079 } 7080 else 7081 { 7082 $height = 376; 7083 } 7084 } 7085 elseif ($mime === 'audio') 7086 { 7087 $height = 0; 7088 } 7089 7090 // Set proper placeholder value 7091 if ($mime === 'audio') 7092 { 7093 $placeholder = $audio; 7094 } 7095 elseif ($mime === 'video') 7096 { 7097 $placeholder = $video; 7098 } 7099 7100 $embed = ''; 7101 7102 // Make sure the JS library is included 7103 if (!$native) 7104 { 7105 static $javascript_outputted = null; 7106 if (!$javascript_outputted && $this->javascript) 7107 { 7108 $embed .= '<script type="text/javascript" src="?' . htmlspecialchars($this->javascript) . '"></script>'; 7109 $javascript_outputted = true; 7110 } 7111 } 7112 7113 // Odeo Feed MP3's 7114 if ($handler === 'odeo') 7115 { 7116 if ($native) 7117 { 7118 $embed .= '<embed src="http://odeo.com/flash/audio_player_fullsize.swf" pluginspage="http://adobe.com/go/getflashplayer" type="application/x-shockwave-flash" quality="high" width="440" height="80" wmode="transparent" allowScriptAccess="any" flashvars="valid_sample_rate=true&external_url=' . $this->get_link() . '"></embed>'; 7119 } 7120 else 7121 { 7122 $embed .= '<script type="text/javascript">embed_odeo("' . $this->get_link() . '");</script>'; 7123 } 7124 } 7125 7126 // Flash 7127 elseif ($handler === 'flash') 7128 { 7129 if ($native) 7130 { 7131 $embed .= "<embed src=\"" . $this->get_link() . "\" pluginspage=\"http://adobe.com/go/getflashplayer\" type=\"$type\" quality=\"high\" width=\"$width\" height=\"$height\" bgcolor=\"$bgcolor\" loop=\"$loop\"></embed>"; 7132 } 7133 else 7134 { 7135 $embed .= "<script type='text/javascript'>embed_flash('$bgcolor', '$width', '$height', '" . $this->get_link() . "', '$loop', '$type');</script>"; 7136 } 7137 } 7138 7139 // Flash Media Player file types. 7140 // Preferred handler for MP3 file types. 7141 elseif ($handler === 'fmedia' || ($handler === 'mp3' && $mediaplayer !== '')) 7142 { 7143 $height += 20; 7144 if ($native) 7145 { 7146 $embed .= "<embed src=\"$mediaplayer\" pluginspage=\"http://adobe.com/go/getflashplayer\" type=\"application/x-shockwave-flash\" quality=\"high\" width=\"$width\" height=\"$height\" wmode=\"transparent\" flashvars=\"file=" . rawurlencode($this->get_link().'?file_extension=.'.$this->get_extension()) . "&autostart=false&repeat=$loop&showdigits=true&showfsbutton=false\"></embed>"; 7147 } 7148 else 7149 { 7150 $embed .= "<script type='text/javascript'>embed_flv('$width', '$height', '" . rawurlencode($this->get_link().'?file_extension=.'.$this->get_extension()) . "', '$placeholder', '$loop', '$mediaplayer');</script>"; 7151 } 7152 } 7153 7154 // QuickTime 7 file types. Need to test with QuickTime 6. 7155 // Only handle MP3's if the Flash Media Player is not present. 7156 elseif ($handler === 'quicktime' || ($handler === 'mp3' && $mediaplayer === '')) 7157 { 7158 $height += 16; 7159 if ($native) 7160 { 7161 if ($placeholder !== '') 7162 { 7163 $embed .= "<embed type=\"$type\" style=\"cursor:hand; cursor:pointer;\" href=\"" . $this->get_link() . "\" src=\"$placeholder\" width=\"$width\" height=\"$height\" autoplay=\"false\" target=\"myself\" controller=\"false\" loop=\"$loop\" scale=\"aspect\" bgcolor=\"$bgcolor\" pluginspage=\"http://apple.com/quicktime/download/\"></embed>"; 7164 } 7165 else 7166 { 7167 $embed .= "<embed type=\"$type\" style=\"cursor:hand; cursor:pointer;\" src=\"" . $this->get_link() . "\" width=\"$width\" height=\"$height\" autoplay=\"false\" target=\"myself\" controller=\"true\" loop=\"$loop\" scale=\"aspect\" bgcolor=\"$bgcolor\" pluginspage=\"http://apple.com/quicktime/download/\"></embed>"; 7168 } 7169 } 7170 else 7171 { 7172 $embed .= "<script type='text/javascript'>embed_quicktime('$type', '$bgcolor', '$width', '$height', '" . $this->get_link() . "', '$placeholder', '$loop');</script>"; 7173 } 7174 } 7175 7176 // Windows Media 7177 elseif ($handler === 'wmedia') 7178 { 7179 $height += 45; 7180 if ($native) 7181 { 7182 $embed .= "<embed type=\"application/x-mplayer2\" src=\"" . $this->get_link() . "\" autosize=\"1\" width=\"$width\" height=\"$height\" showcontrols=\"1\" showstatusbar=\"0\" showdisplay=\"0\" autostart=\"0\"></embed>"; 7183 } 7184 else 7185 { 7186 $embed .= "<script type='text/javascript'>embed_wmedia('$width', '$height', '" . $this->get_link() . "');</script>"; 7187 } 7188 } 7189 7190 // Everything else 7191 else $embed .= '<a href="' . $this->get_link() . '" class="' . $altclass . '">' . $alt . '</a>'; 7192 7193 return $embed; 7194 } 7195 7196 function get_real_type($find_handler = false) 7197 { 7198 // If it's Odeo, let's get it out of the way. 7199 if (substr(strtolower($this->get_link()), 0, 15) === 'http://odeo.com') 7200 { 7201 return 'odeo'; 7202 } 7203 7204 // Mime-types by handler. 7205 $types_flash = array('application/x-shockwave-flash', 'application/futuresplash'); // Flash 7206 $types_fmedia = array('video/flv', 'video/x-flv','flv-application/octet-stream'); // Flash Media Player 7207 $types_quicktime = array('audio/3gpp', 'audio/3gpp2', 'audio/aac', 'audio/x-aac', 'audio/aiff', 'audio/x-aiff', 'audio/mid', 'audio/midi', 'audio/x-midi', 'audio/mp4', 'audio/m4a', 'audio/x-m4a', 'audio/wav', 'audio/x-wav', 'video/3gpp', 'video/3gpp2', 'video/m4v', 'video/x-m4v', 'video/mp4', 'video/mpeg', 'video/x-mpeg', 'video/quicktime', 'video/sd-video'); // QuickTime 7208 $types_wmedia = array('application/asx', 'application/x-mplayer2', 'audio/x-ms-wma', 'audio/x-ms-wax', 'video/x-ms-asf-plugin', 'video/x-ms-asf', 'video/x-ms-wm', 'video/x-ms-wmv', 'video/x-ms-wvx'); // Windows Media 7209 $types_mp3 = array('audio/mp3', 'audio/x-mp3', 'audio/mpeg', 'audio/x-mpeg'); // MP3 7210 7211 if ($this->get_type() !== null) 7212 { 7213 $type = strtolower($this->type); 7214 } 7215 else 7216 { 7217 $type = null; 7218 } 7219 7220 // If we encounter an unsupported mime-type, check the file extension and guess intelligently. 7221 if (!in_array($type, array_merge($types_flash, $types_fmedia, $types_quicktime, $types_wmedia, $types_mp3))) 7222 { 7223 switch (strtolower($this->get_extension())) 7224 { 7225 // Audio mime-types 7226 case 'aac': 7227 case 'adts': 7228 $type = 'audio/acc'; 7229 break; 7230 7231 case 'aif': 7232 case 'aifc': 7233 case 'aiff': 7234 case 'cdda': 7235 $type = 'audio/aiff'; 7236 break; 7237 7238 case 'bwf': 7239 $type = 'audio/wav'; 7240 break; 7241 7242 case 'kar': 7243 case 'mid': 7244 case 'midi': 7245 case 'smf': 7246 $type = 'audio/midi'; 7247 break; 7248 7249 case 'm4a': 7250 $type = 'audio/x-m4a'; 7251 break; 7252 7253 case 'mp3': 7254 case 'swa': 7255 $type = 'audio/mp3'; 7256 break; 7257 7258 case 'wav': 7259 $type = 'audio/wav'; 7260 break; 7261 7262 case 'wax': 7263 $type = 'audio/x-ms-wax'; 7264 break; 7265 7266 case 'wma': 7267 $type = 'audio/x-ms-wma'; 7268 break; 7269 7270 // Video mime-types 7271 case '3gp': 7272 case '3gpp': 7273 $type = 'video/3gpp'; 7274 break; 7275 7276 case '3g2': 7277 case '3gp2': 7278 $type = 'video/3gpp2'; 7279 break; 7280 7281 case 'asf': 7282 $type = 'video/x-ms-asf'; 7283 break; 7284 7285 case 'flv': 7286 $type = 'video/x-flv'; 7287 break; 7288 7289 case 'm1a': 7290 case 'm1s': 7291 case 'm1v': 7292 case 'm15': 7293 case 'm75': 7294 case 'mp2': 7295 case 'mpa': 7296 case 'mpeg': 7297 case 'mpg': 7298 case 'mpm': 7299 case 'mpv': 7300 $type = 'video/mpeg'; 7301 break; 7302 7303 case 'm4v': 7304 $type = 'video/x-m4v'; 7305 break; 7306 7307 case 'mov': 7308 case 'qt': 7309 $type = 'video/quicktime'; 7310 break; 7311 7312 case 'mp4': 7313 case 'mpg4': 7314 $type = 'video/mp4'; 7315 break; 7316 7317 case 'sdv': 7318 $type = 'video/sd-video'; 7319 break; 7320 7321 case 'wm': 7322 $type = 'video/x-ms-wm'; 7323 break; 7324 7325 case 'wmv': 7326 $type = 'video/x-ms-wmv'; 7327 break; 7328 7329 case 'wvx': 7330 $type = 'video/x-ms-wvx'; 7331 break; 7332 7333 // Flash mime-types 7334 case 'spl': 7335 $type = 'application/futuresplash'; 7336 break; 7337 7338 case 'swf': 7339 $type = 'application/x-shockwave-flash'; 7340 break; 7341 } 7342 } 7343 7344 if ($find_handler) 7345 { 7346 if (in_array($type, $types_flash)) 7347 { 7348 return 'flash'; 7349 } 7350 elseif (in_array($type, $types_fmedia)) 7351 { 7352 return 'fmedia'; 7353 } 7354 elseif (in_array($type, $types_quicktime)) 7355 { 7356 return 'quicktime'; 7357 } 7358 elseif (in_array($type, $types_wmedia)) 7359 { 7360 return 'wmedia'; 7361 } 7362 elseif (in_array($type, $types_mp3)) 7363 { 7364 return 'mp3'; 7365 } 7366 else 7367 { 7368 return null; 7369 } 7370 } 7371 else 7372 { 7373 return $type; 7374 } 7375 } 7376 } 7377 7378 class SimplePie_Caption 7379 { 7380 var $type; 7381 var $lang; 7382 var $startTime; 7383 var $endTime; 7384 var $text; 7385 7386 // Constructor, used to input the data 7387 function SimplePie_Caption($type = null, $lang = null, $startTime = null, $endTime = null, $text = null) 7388 { 7389 $this->type = $type; 7390 $this->lang = $lang; 7391 $this->startTime = $startTime; 7392 $this->endTime = $endTime; 7393 $this->text = $text; 7394 } 7395 7396 function __toString() 7397 { 7398 // There is no $this->data here 7399 return md5(serialize($this)); 7400 } 7401 7402 function get_endtime() 7403 { 7404 if ($this->endTime !== null) 7405 { 7406 return $this->endTime; 7407 } 7408 else 7409 { 7410 return null; 7411 } 7412 } 7413 7414 function get_language() 7415 { 7416 if ($this->lang !== null) 7417 { 7418 return $this->lang; 7419 } 7420 else 7421 { 7422 return null; 7423 } 7424 } 7425 7426 function get_starttime() 7427 { 7428 if ($this->startTime !== null) 7429 { 7430 return $this->startTime; 7431 } 7432 else 7433 { 7434 return null; 7435 } 7436 } 7437 7438 function get_text() 7439 { 7440 if ($this->text !== null) 7441 { 7442 return $this->text; 7443 } 7444 else 7445 { 7446 return null; 7447 } 7448 } 7449 7450 function get_type() 7451 { 7452 if ($this->type !== null) 7453 { 7454 return $this->type; 7455 } 7456 else 7457 { 7458 return null; 7459 } 7460 } 7461 } 7462 7463 class SimplePie_Credit 7464 { 7465 var $role; 7466 var $scheme; 7467 var $name; 7468 7469 // Constructor, used to input the data 7470 function SimplePie_Credit($role = null, $scheme = null, $name = null) 7471 { 7472 $this->role = $role; 7473 $this->scheme = $scheme; 7474 $this->name = $name; 7475 } 7476 7477 function __toString() 7478 { 7479 // There is no $this->data here 7480 return md5(serialize($this)); 7481 } 7482 7483 function get_role() 7484 { 7485 if ($this->role !== null) 7486 { 7487 return $this->role; 7488 } 7489 else 7490 { 7491 return null; 7492 } 7493 } 7494 7495 function get_scheme() 7496 { 7497 if ($this->scheme !== null) 7498 { 7499 return $this->scheme; 7500 } 7501 else 7502 { 7503 return null; 7504 } 7505 } 7506 7507 function get_name() 7508 { 7509 if ($this->name !== null) 7510 { 7511 return $this->name; 7512 } 7513 else 7514 { 7515 return null; 7516 } 7517 } 7518 } 7519 7520 class SimplePie_Copyright 7521 { 7522 var $url; 7523 var $label; 7524 7525 // Constructor, used to input the data 7526 function SimplePie_Copyright($url = null, $label = null) 7527 { 7528 $this->url = $url; 7529 $this->label = $label; 7530 } 7531 7532 function __toString() 7533 { 7534 // There is no $this->data here 7535 return md5(serialize($this)); 7536 } 7537 7538 function get_url() 7539 { 7540 if ($this->url !== null) 7541 { 7542 return $this->url; 7543 } 7544 else 7545 { 7546 return null; 7547 } 7548 } 7549 7550 function get_attribution() 7551 { 7552 if ($this->label !== null) 7553 { 7554 return $this->label; 7555 } 7556 else 7557 { 7558 return null; 7559 } 7560 } 7561 } 7562 7563 class SimplePie_Rating 7564 { 7565 var $scheme; 7566 var $value; 7567 7568 // Constructor, used to input the data 7569 function SimplePie_Rating($scheme = null, $value = null) 7570 { 7571 $this->scheme = $scheme; 7572 $this->value = $value; 7573 } 7574 7575 function __toString() 7576 { 7577 // There is no $this->data here 7578 return md5(serialize($this)); 7579 } 7580 7581 function get_scheme() 7582 { 7583 if ($this->scheme !== null) 7584 { 7585 return $this->scheme; 7586 } 7587 else 7588 { 7589 return null; 7590 } 7591 } 7592 7593 function get_value() 7594 { 7595 if ($this->value !== null) 7596 { 7597 return $this->value; 7598 } 7599 else 7600 { 7601 return null; 7602 } 7603 } 7604 } 7605 7606 class SimplePie_Restriction 7607 { 7608 var $relationship; 7609 var $type; 7610 var $value; 7611 7612 // Constructor, used to input the data 7613 function SimplePie_Restriction($relationship = null, $type = null, $value = null) 7614 { 7615 $this->relationship = $relationship; 7616 $this->type = $type; 7617 $this->value = $value; 7618 } 7619 7620 function __toString() 7621 { 7622 // There is no $this->data here 7623 return md5(serialize($this)); 7624 } 7625 7626 function get_relationship() 7627 { 7628 if ($this->relationship !== null) 7629 { 7630 return $this->relationship; 7631 } 7632 else 7633 { 7634 return null; 7635 } 7636 } 7637 7638 function get_type() 7639 { 7640 if ($this->type !== null) 7641 { 7642 return $this->type; 7643 } 7644 else 7645 { 7646 return null; 7647 } 7648 } 7649 7650 function get_value() 7651 { 7652 if ($this->value !== null) 7653 { 7654 return $this->value; 7655 } 7656 else 7657 { 7658 return null; 7659 } 7660 } 7661 } 7662 7663 /** 7664 * @todo Move to properly supporting RFC2616 (HTTP/1.1) 7665 */ 7666 class SimplePie_File 7667 { 7668 var $url; 7669 var $useragent; 7670 var $success = true; 7671 var $headers = array(); 7672 var $body; 7673 var $status_code; 7674 var $redirects = 0; 7675 var $error; 7676 var $method = SIMPLEPIE_FILE_SOURCE_NONE; 7677 7678 function SimplePie_File($url, $timeout = 10, $redirects = 5, $headers = null, $useragent = null, $force_fsockopen = false) 7679 { 7680 if (class_exists('idna_convert')) 7681 { 7682 $idn = new idna_convert(); 7683 $parsed = SimplePie_Misc::parse_url($url); 7684 $url = SimplePie_Misc::compress_parse_url($parsed['scheme'], $idn->encode($parsed['authority']), $parsed['path'], $parsed['query'], $parsed['fragment']); 7685 } 7686 $this->url = $url; 7687 $this->useragent = $useragent; 7688 if (preg_match('/^http(s)?:\/\//i', $url)) 7689 { 7690 if ($useragent === null) 7691 { 7692 $useragent = ini_get('user_agent'); 7693 $this->useragent = $useragent; 7694 } 7695 if (!is_array($headers)) 7696 { 7697 $headers = array(); 7698 } 7699 if (!$force_fsockopen && function_exists('curl_exec')) 7700 { 7701 $this->method = SIMPLEPIE_FILE_SOURCE_REMOTE | SIMPLEPIE_FILE_SOURCE_CURL; 7702 $fp = curl_init(); 7703 $headers2 = array(); 7704 foreach ($headers as $key => $value) 7705 { 7706 $headers2[] = "$key: $value"; 7707 } 7708 if (version_compare(SimplePie_Misc::get_curl_version(), '7.10.5', '>=')) 7709 { 7710 curl_setopt($fp, CURLOPT_ENCODING, ''); 7711 } 7712 curl_setopt($fp, CURLOPT_URL, $url); 7713 curl_setopt($fp, CURLOPT_HEADER, 1); 7714 curl_setopt($fp, CURLOPT_RETURNTRANSFER, 1); 7715 curl_setopt($fp, CURLOPT_TIMEOUT, $timeout); 7716 curl_setopt($fp, CURLOPT_CONNECTTIMEOUT, $timeout); 7717 curl_setopt($fp, CURLOPT_REFERER, $url); 7718 curl_setopt($fp, CURLOPT_USERAGENT, $useragent); 7719 curl_setopt($fp, CURLOPT_HTTPHEADER, $headers2); 7720 if (!ini_get('open_basedir') && !ini_get('safe_mode') && version_compare(SimplePie_Misc::get_curl_version(), '7.15.2', '>=')) 7721 { 7722 curl_setopt($fp, CURLOPT_FOLLOWLOCATION, 1); 7723 curl_setopt($fp, CURLOPT_MAXREDIRS, $redirects); 7724 } 7725 7726 $this->headers = curl_exec($fp); 7727 if (curl_errno($fp) === 23 || curl_errno($fp) === 61) 7728 { 7729 curl_setopt($fp, CURLOPT_ENCODING, 'none'); 7730 $this->headers = curl_exec($fp); 7731 } 7732 if (curl_errno($fp)) 7733 { 7734 $this->error = 'cURL error ' . curl_errno($fp) . ': ' . curl_error($fp); 7735 $this->success = false; 7736 } 7737 else 7738 { 7739 $info = curl_getinfo($fp); 7740 curl_close($fp); 7741 $this->headers = explode("\r\n\r\n", $this->headers, $info['redirect_count'] + 1); 7742 $this->headers = array_pop($this->headers); 7743 $parser = new SimplePie_HTTP_Parser($this->headers); 7744 if ($parser->parse()) 7745 { 7746 $this->headers = $parser->headers; 7747 $this->body = $parser->body; 7748 $this->status_code = $parser->status_code; 7749 if ((in_array($this->status_code, array(300, 301, 302, 303, 307)) || $this->status_code > 307 && $this->status_code < 400) && isset($this->headers['location']) && $this->redirects < $redirects) 7750 { 7751 $this->redirects++; 7752 $location = SimplePie_Misc::absolutize_url($this->headers['location'], $url); 7753 return $this->SimplePie_File($location, $timeout, $redirects, $headers, $useragent, $force_fsockopen); 7754 } 7755 } 7756 } 7757 } 7758 else 7759 { 7760 $this->method = SIMPLEPIE_FILE_SOURCE_REMOTE | SIMPLEPIE_FILE_SOURCE_FSOCKOPEN; 7761 $url_parts = parse_url($url); 7762 if (isset($url_parts['scheme']) && strtolower($url_parts['scheme']) === 'https') 7763 { 7764 $url_parts['host'] = 'ssl://'.$url_parts['host']; 7765 $url_parts['port'] = 443; 7766 } 7767 if (!isset($url_parts['port'])) 7768 { 7769 $url_parts['port'] = 80; 7770 } 7771 $fp = @fsockopen($url_parts['host'], $url_parts['port'], $errno, $errstr, $timeout); 7772 if (!$fp) 7773 { 7774 $this->error = 'fsockopen error: ' . $errstr; 7775 $this->success = false; 7776 } 7777 else 7778 { 7779 stream_set_timeout($fp, $timeout); 7780 if (isset($url_parts['path'])) 7781 { 7782 if (isset($url_parts['query'])) 7783 { 7784 $get = $url_parts['path'].'?'.$url_parts['query']; 7785 } 7786 else 7787 { 7788 $get = $url_parts['path']; 7789 } 7790 } 7791 else 7792 { 7793 $get = '/'; 7794 } 7795 $out = "GET $get HTTP/1.0\r\n"; 7796 $out .= "Host: $url_parts[host]\r\n"; 7797 $out .= "User-Agent: $useragent\r\n"; 7798 if (extension_loaded('zlib')) 7799 { 7800 $out .= "Accept-Encoding: x-gzip,gzip,deflate\r\n"; 7801 } 7802 7803 if (isset($url_parts['user']) && isset($url_parts['pass'])) 7804 { 7805 $out .= "Authorization: Basic " . base64_encode($url_parts['user'].':'.$url_parts['pass']) . "\r\n"; 7806 } 7807 foreach ($headers as $key => $value) 7808 { 7809 $out .= "$key: $value\r\n"; 7810 } 7811 $out .= "Connection: Close\r\n\r\n"; 7812 fwrite($fp, $out); 7813 7814 $info = stream_get_meta_data($fp); 7815 7816 $this->headers = ''; 7817 while (!$info['eof'] && !$info['timed_out']) 7818 { 7819 $this->headers .= fread($fp, 1160); 7820 $info = stream_get_meta_data($fp); 7821 } 7822 if (!$info['timed_out']) 7823 { 7824 $parser = new SimplePie_HTTP_Parser($this->headers); 7825 if ($parser->parse()) 7826 { 7827 $this->headers = $parser->headers; 7828 $this->body = $parser->body; 7829 $this->status_code = $parser->status_code; 7830 if ((in_array($this->status_code, array(300, 301, 302, 303, 307)) || $this->status_code > 307 && $this->status_code < 400) && isset($this->headers['location']) && $this->redirects < $redirects) 7831 { 7832 $this->redirects++; 7833 $location = SimplePie_Misc::absolutize_url($this->headers['location'], $url); 7834 return $this->SimplePie_File($location, $timeout, $redirects, $headers, $useragent, $force_fsockopen); 7835 } 7836 if (isset($this->headers['content-encoding'])) 7837 { 7838 // Hey, we act dumb elsewhere, so let's do that here too 7839 switch (strtolower(trim($this->headers['content-encoding'], "\x09\x0A\x0D\x20"))) 7840 { 7841 case 'gzip': 7842 case 'x-gzip': 7843 $decoder = new SimplePie_gzdecode($this->body); 7844 if (!$decoder->parse()) 7845 { 7846 $this->error = 'Unable to decode HTTP "gzip" stream'; 7847 $this->success = false; 7848 } 7849 else 7850 { 7851 $this->body = $decoder->data; 7852 } 7853 break; 7854 7855 case 'deflate': 7856 if (($body = gzuncompress($this->body)) === false) 7857 { 7858 if (($body = gzinflate($this->body)) === false) 7859 { 7860 $this->error = 'Unable to decode HTTP "deflate" stream'; 7861 $this->success = false; 7862 } 7863 } 7864 $this->body = $body; 7865 break; 7866 7867 default: 7868 $this->error = 'Unknown content coding'; 7869 $this->success = false; 7870 } 7871 } 7872 } 7873 } 7874 else 7875 { 7876 $this->error = 'fsocket timed out'; 7877 $this->success = false; 7878 } 7879 fclose($fp); 7880 } 7881 } 7882 } 7883 else 7884 { 7885 $this->method = SIMPLEPIE_FILE_SOURCE_LOCAL | SIMPLEPIE_FILE_SOURCE_FILE_GET_CONTENTS; 7886 if (!$this->body = file_get_contents($url)) 7887 { 7888 $this->error = 'file_get_contents could not read the file'; 7889 $this->success = false; 7890 } 7891 } 7892 } 7893 } 7894 7895 /** 7896 * HTTP Response Parser 7897 * 7898 * @package SimplePie 7899 */ 7900 class SimplePie_HTTP_Parser 7901 { 7902 /** 7903 * HTTP Version 7904 * 7905 * @access public 7906 * @var float 7907 */ 7908 var $http_version = 0.0; 7909 7910 /** 7911 * Status code 7912 * 7913 * @access public 7914 * @var int 7915 */ 7916 var $status_code = 0; 7917 7918 /** 7919 * Reason phrase 7920 * 7921 * @access public 7922 * @var string 7923 */ 7924 var $reason = ''; 7925 7926 /** 7927 * Key/value pairs of the headers 7928 * 7929 * @access public 7930 * @var array 7931 */ 7932 var $headers = array(); 7933 7934 /** 7935 * Body of the response 7936 * 7937 * @access public 7938 * @var string 7939 */ 7940 var $body = ''; 7941 7942 /** 7943 * Current state of the state machine 7944 * 7945 * @access private 7946 * @var string 7947 */ 7948 var $state = 'http_version'; 7949 7950 /** 7951 * Input data 7952 * 7953 * @access private 7954 * @var string 7955 */ 7956 var $data = ''; 7957 7958 /** 7959 * Input data length (to avoid calling strlen() everytime this is needed) 7960 * 7961 * @access private 7962 * @var int 7963 */ 7964 var $data_length = 0; 7965 7966 /** 7967 * Current position of the pointer 7968 * 7969 * @var int 7970 * @access private 7971 */ 7972 var $position = 0; 7973 7974 /** 7975 * Name of the hedaer currently being parsed 7976 * 7977 * @access private 7978 * @var string 7979 */ 7980 var $name = ''; 7981 7982 /** 7983 * Value of the hedaer currently being parsed 7984 * 7985 * @access private 7986 * @var string 7987 */ 7988 var $value = ''; 7989 7990 /** 7991 * Create an instance of the class with the input data 7992 * 7993 * @access public 7994 * @param string $data Input data 7995 */ 7996 function SimplePie_HTTP_Parser($data) 7997 { 7998 $this->data = $data; 7999 $this->data_length = strlen($this->data); 8000 } 8001 8002 /** 8003 * Parse the input data 8004 * 8005 * @access public 8006 * @return bool true on success, false on failure 8007 */ 8008 function parse() 8009 { 8010 while ($this->state && $this->state !== 'emit' && $this->has_data()) 8011 { 8012 $state = $this->state; 8013 $this->$state(); 8014 } 8015 $this->data = ''; 8016 if ($this->state === 'emit' || $this->state === 'body') 8017 { 8018 return true; 8019 } 8020 else 8021 { 8022 $this->http_version = ''; 8023 $this->status_code = ''; 8024 $this->reason = ''; 8025 $this->headers = array(); 8026 $this->body = ''; 8027 return false; 8028 } 8029 } 8030 8031 /** 8032 * Check whether there is data beyond the pointer 8033 * 8034 * @access private 8035 * @return bool true if there is further data, false if not 8036 */ 8037 function has_data() 8038 { 8039 return (bool) ($this->position < $this->data_length); 8040 } 8041 8042 /** 8043 * See if the next character is LWS 8044 * 8045 * @access private 8046 * @return bool true if the next character is LWS, false if not 8047 */ 8048 function is_linear_whitespace() 8049 { 8050 return (bool) ($this->data[$this->position] === "\x09" 8051 || $this->data[$this->position] === "\x20" 8052 || ($this->data[$this->position] === "\x0A" 8053 && isset($this->data[$this->position + 1]) 8054 && ($this->data[$this->position + 1] === "\x09" || $this->data[$this->position + 1] === "\x20"))); 8055 } 8056 8057 /** 8058 * Parse the HTTP version 8059 * 8060 * @access private 8061 */ 8062 function http_version() 8063 { 8064 if (strpos($this->data, "\x0A") !== false && strtoupper(substr($this->data, 0, 5)) === 'HTTP/') 8065 { 8066 $len = strspn($this->data, '0123456789.', 5); 8067 $this->http_version = substr($this->data, 5, $len); 8068 $this->position += 5 + $len; 8069 if (substr_count($this->http_version, '.') <= 1) 8070 { 8071 $this->http_version = (float) $this->http_version; 8072 $this->position += strspn($this->data, "\x09\x20", $this->position); 8073 $this->state = 'status'; 8074 } 8075 else 8076 { 8077 $this->state = false; 8078 } 8079 } 8080 else 8081 { 8082 $this->state = false; 8083 } 8084 } 8085 8086 /** 8087 * Parse the status code 8088 * 8089 * @access private 8090 */ 8091 function status() 8092 { 8093 if ($len = strspn($this->data, '0123456789', $this->position)) 8094 { 8095 $this->status_code = (int) substr($this->data, $this->position, $len); 8096 $this->position += $len; 8097 $this->state = 'reason'; 8098 } 8099 else 8100 { 8101 $this->state = false; 8102 } 8103 } 8104 8105 /** 8106 * Parse the reason phrase 8107 * 8108 * @access private 8109 */ 8110 function reason() 8111 { 8112 $len = strcspn($this->data, "\x0A", $this->position); 8113 $this->reason = trim(substr($this->data, $this->position, $len), "\x09\x0D\x20"); 8114 $this->position += $len + 1; 8115 $this->state = 'new_line'; 8116 } 8117 8118 /** 8119 * Deal with a new line, shifting data around as needed 8120 * 8121 * @access private 8122 */ 8123 function new_line() 8124 { 8125 $this->value = trim($this->value, "\x0D\x20"); 8126 if ($this->name !== '' && $this->value !== '') 8127 { 8128 $this->name = strtolower($this->name); 8129 if (isset($this->headers[$this->name])) 8130 { 8131 $this->headers[$this->name] .= ', ' . $this->value; 8132 } 8133 else 8134 { 8135 $this->headers[$this->name] = $this->value; 8136 } 8137 } 8138 $this->name = ''; 8139 $this->value = ''; 8140 if (substr($this->data[$this->position], 0, 2) === "\x0D\x0A") 8141 { 8142 $this->position += 2; 8143 $this->state = 'body'; 8144 } 8145 elseif ($this->data[$this->position] === "\x0A") 8146 { 8147 $this->position++; 8148 $this->state = 'body'; 8149 } 8150 else 8151 { 8152 $this->state = 'name'; 8153 } 8154 } 8155 8156 /** 8157 * Parse a header name 8158 * 8159 * @access private 8160 */ 8161 function name() 8162 { 8163 $len = strcspn($this->data, "\x0A:", $this->position); 8164 if (isset($this->data[$this->position + $len])) 8165 { 8166 if ($this->data[$this->position + $len] === "\x0A") 8167 { 8168 $this->position += $len; 8169 $this->state = 'new_line'; 8170 } 8171 else 8172 { 8173 $this->name = substr($this->data, $this->position, $len); 8174 $this->position += $len + 1; 8175 $this->state = 'value'; 8176 } 8177 } 8178 else 8179 { 8180 $this->state = false; 8181 } 8182 } 8183 8184 /** 8185 * Parse LWS, replacing consecutive LWS characters with a single space 8186 * 8187 * @access private 8188 */ 8189 function linear_whitespace() 8190 { 8191 do 8192 { 8193 if (substr($this->data, $this->position, 2) === "\x0D\x0A") 8194 { 8195 $this->position += 2; 8196 } 8197 elseif ($this->data[$this->position] === "\x0A") 8198 { 8199 $this->position++; 8200 } 8201 $this->position += strspn($this->data, "\x09\x20", $this->position); 8202 } while ($this->has_data() && $this->is_linear_whitespace()); 8203 $this->value .= "\x20"; 8204 } 8205 8206 /** 8207 * See what state to move to while within non-quoted header values 8208 * 8209 * @access private 8210 */ 8211 function value() 8212 { 8213 if ($this->is_linear_whitespace()) 8214 { 8215 $this->linear_whitespace(); 8216 } 8217 else 8218 { 8219 switch ($this->data[$this->position]) 8220 { 8221 case '"': 8222 $this->position++; 8223 $this->state = 'quote'; 8224 break; 8225 8226 case "\x0A": 8227 $this->position++; 8228 $this->state = 'new_line'; 8229 break; 8230 8231 default: 8232 $this->state = 'value_char'; 8233 break; 8234 } 8235 } 8236 } 8237 8238 /** 8239 * Parse a header value while outside quotes 8240 * 8241 * @access private 8242 */ 8243 function value_char() 8244 { 8245 $len = strcspn($this->data, "\x09\x20\x0A\"", $this->position); 8246 $this->value .= substr($this->data, $this->position, $len); 8247 $this->position += $len; 8248 $this->state = 'value'; 8249 } 8250 8251 /** 8252 * See what state to move to while within quoted header values 8253 * 8254 * @access private 8255 */ 8256 function quote() 8257 { 8258 if ($this->is_linear_whitespace()) 8259 { 8260 $this->linear_whitespace(); 8261 } 8262 else 8263 { 8264 switch ($this->data[$this->position]) 8265 { 8266 case '"': 8267 $this->position++; 8268 $this->state = 'value'; 8269 break; 8270 8271 case "\x0A": 8272 $this->position++; 8273 $this->state = 'new_line'; 8274 break; 8275 8276 case '\\': 8277 $this->position++; 8278 $this->state = 'quote_escaped'; 8279 break; 8280 8281 default: 8282 $this->state = 'quote_char'; 8283 break; 8284 } 8285 } 8286 } 8287 8288 /** 8289 * Parse a header value while within quotes 8290 * 8291 * @access private 8292 */ 8293 function quote_char() 8294 { 8295 $len = strcspn($this->data, "\x09\x20\x0A\"\\", $this->position); 8296 $this->value .= substr($this->data, $this->position, $len); 8297 $this->position += $len; 8298 $this->state = 'value'; 8299 } 8300 8301 /** 8302 * Parse an escaped character within quotes 8303 * 8304 * @access private 8305 */ 8306 function quote_escaped() 8307 { 8308 $this->value .= $this->data[$this->position]; 8309 $this->position++; 8310 $this->state = 'quote'; 8311 } 8312 8313 /** 8314 * Parse the body 8315 * 8316 * @access private 8317 */ 8318 function body() 8319 { 8320 $this->body = substr($this->data, $this->position); 8321 $this->state = 'emit'; 8322 } 8323 } 8324 8325 /** 8326 * gzdecode 8327 * 8328 * @package SimplePie 8329 */ 8330 class SimplePie_gzdecode 8331 { 8332 /** 8333 * Compressed data 8334 * 8335 * @access private 8336 * @see gzdecode::$data 8337 */ 8338 var $compressed_data; 8339 8340 /** 8341 * Size of compressed data 8342 * 8343 * @access private 8344 */ 8345 var $compressed_size; 8346 8347 /** 8348 * Minimum size of a valid gzip string 8349 * 8350 * @access private 8351 */ 8352 var $min_compressed_size = 18; 8353 8354 /** 8355 * Current position of pointer 8356 * 8357 * @access private 8358 */ 8359 var $position = 0; 8360 8361 /** 8362 * Flags (FLG) 8363 * 8364 * @access private 8365 */ 8366 var $flags; 8367 8368 /** 8369 * Uncompressed data 8370 * 8371 * @access public 8372 * @see gzdecode::$compressed_data 8373 */ 8374 var $data; 8375 8376 /** 8377 * Modified time 8378 * 8379 * @access public 8380 */ 8381 var $MTIME; 8382 8383 /** 8384 * Extra Flags 8385 * 8386 * @access public 8387 */ 8388 var $XFL; 8389 8390 /** 8391 * Operating System 8392 * 8393 * @access public 8394 */ 8395 var $OS; 8396 8397 /** 8398 * Subfield ID 1 8399 * 8400 * @access public 8401 * @see gzdecode::$extra_field 8402 * @see gzdecode::$SI2 8403 */ 8404 var $SI1; 8405 8406 /** 8407 * Subfield ID 2 8408 * 8409 * @access public 8410 * @see gzdecode::$extra_field 8411 * @see gzdecode::$SI1 8412 */ 8413 var $SI2; 8414 8415 /** 8416 * Extra field content 8417 * 8418 * @access public 8419 * @see gzdecode::$SI1 8420 * @see gzdecode::$SI2 8421 */ 8422 var $extra_field; 8423 8424 /** 8425 * Original filename 8426 * 8427 * @access public 8428 */ 8429 var $filename; 8430 8431 /** 8432 * Human readable comment 8433 * 8434 * @access public 8435 */ 8436 var $comment; 8437 8438 /** 8439 * Don't allow anything to be set 8440 * 8441 * @access public 8442 */ 8443 function __set($name, $value) 8444 { 8445 trigger_error("Cannot write property $name", E_USER_ERROR); 8446 } 8447 8448 /** 8449 * Set the compressed string and related properties 8450 * 8451 * @access public 8452 */ 8453 function SimplePie_gzdecode($data) 8454 { 8455 $this->compressed_data = $data; 8456 $this->compressed_size = strlen($data); 8457 } 8458 8459 /** 8460 * Decode the GZIP stream 8461 * 8462 * @access public 8463 */ 8464 function parse() 8465 { 8466 if ($this->compressed_size >= $this->min_compressed_size) 8467 { 8468 // Check ID1, ID2, and CM 8469 if (substr($this->compressed_data, 0, 3) !== "\x1F\x8B\x08") 8470 { 8471 return false; 8472 } 8473 8474 // Get the FLG (FLaGs) 8475 $this->flags = ord($this->compressed_data[3]); 8476 8477 // FLG bits above (1 << 4) are reserved 8478 if ($this->flags > 0x1F) 8479 { 8480 return false; 8481 } 8482 8483 // Advance the pointer after the above 8484 $this->position += 4; 8485 8486 // MTIME 8487 $mtime = substr($this->compressed_data, $this->position, 4); 8488 // Reverse the string if we're on a big-endian arch because l is the only signed long and is machine endianness 8489 if (current(unpack('S', "\x00\x01")) === 1) 8490 { 8491 $mtime = strrev($mtime); 8492 } 8493 $this->MTIME = current(unpack('l', $mtime)); 8494 $this->position += 4; 8495 8496 // Get the XFL (eXtra FLags) 8497 $this->XFL = ord($this->compressed_data[$this->position++]); 8498 8499 // Get the OS (Operating System) 8500 $this->OS = ord($this->compressed_data[$this->position++]); 8501 8502 // Parse the FEXTRA 8503 if ($this->flags & 4) 8504 { 8505 // Read subfield IDs 8506 $this->SI1 = $this->compressed_data[$this->position++]; 8507 $this->SI2 = $this->compressed_data[$this->position++]; 8508 8509 // SI2 set to zero is reserved for future use 8510 if ($this->SI2 === "\x00") 8511 { 8512 return false; 8513 } 8514 8515 // Get the length of the extra field 8516 $len = current(unpack('v', substr($this->compressed_data, $this->position, 2))); 8517 $this->position += 2; 8518 8519 // Check the length of the string is still valid 8520 $this->min_compressed_size += $len + 4; 8521 if ($this->compressed_size >= $this->min_compressed_size) 8522 { 8523 // Set the extra field to the given data 8524 $this->extra_field = substr($this->compressed_data, $this->position, $len); 8525 $this->position += $len; 8526 } 8527 else 8528 { 8529 return false; 8530 } 8531 } 8532 8533 // Parse the FNAME 8534 if ($this->flags & 8) 8535 { 8536 // Get the length of the filename 8537 $len = strcspn($this->compressed_data, "\x00", $this->position); 8538 8539 // Check the length of the string is still valid 8540 $this->min_compressed_size += $len + 1; 8541 if ($this->compressed_size >= $this->min_compressed_size) 8542 { 8543 // Set the original filename to the given string 8544 $this->filename = substr($this->compressed_data, $this->position, $len); 8545 $this->position += $len + 1; 8546 } 8547 else 8548 { 8549 return false; 8550 } 8551 } 8552 8553 // Parse the FCOMMENT 8554 if ($this->flags & 16) 8555 { 8556 // Get the length of the comment 8557 $len = strcspn($this->compressed_data, "\x00", $this->position); 8558 8559 // Check the length of the string is still valid 8560 $this->min_compressed_size += $len + 1; 8561 if ($this->compressed_size >= $this->min_compressed_size) 8562 { 8563 // Set the original comment to the given string 8564 $this->comment = substr($this->compressed_data, $this->position, $len); 8565 $this->position += $len + 1; 8566 } 8567 else 8568 { 8569 return false; 8570 } 8571 } 8572 8573 // Parse the FHCRC 8574 if ($this->flags & 2) 8575 { 8576 // Check the length of the string is still valid 8577 $this->min_compressed_size += $len + 2; 8578 if ($this->compressed_size >= $this->min_compressed_size) 8579 { 8580 // Read the CRC 8581 $crc = current(unpack('v', substr($this->compressed_data, $this->position, 2))); 8582 8583 // Check the CRC matches 8584 if ((crc32(substr($this->compressed_data, 0, $this->position)) & 0xFFFF) === $crc) 8585 { 8586 $this->position += 2; 8587 } 8588 else 8589 { 8590 return false; 8591 } 8592 } 8593 else 8594 { 8595 return false; 8596 } 8597 } 8598 8599 // Decompress the actual data 8600 if (($this->data = gzinflate(substr($this->compressed_data, $this->position, -8))) === false) 8601 { 8602 return false; 8603 } 8604 else 8605 { 8606 $this->position = $this->compressed_size - 8; 8607 } 8608 8609 // Check CRC of data 8610 $crc = current(unpack('V', substr($this->compressed_data, $this->position, 4))); 8611 $this->position += 4; 8612 /*if (extension_loaded('hash') && sprintf('%u', current(unpack('V', hash('crc32b', $this->data)))) !== sprintf('%u', $crc)) 8613 { 8614 return false; 8615 }*/ 8616 8617 // Check ISIZE of data 8618 $isize = current(unpack('V', substr($this->compressed_data, $this->position, 4))); 8619 $this->position += 4; 8620 if (sprintf('%u', strlen($this->data) & 0xFFFFFFFF) !== sprintf('%u', $isize)) 8621 { 8622 return false; 8623 } 8624 8625 // Wow, against all odds, we've actually got a valid gzip string 8626 return true; 8627 } 8628 else 8629 { 8630 return false; 8631 } 8632 } 8633 } 8634 8635 class SimplePie_Cache 8636 { 8637 /** 8638 * Don't call the constructor. Please. 8639 * 8640 * @access private 8641 */ 8642 function SimplePie_Cache() 8643 { 8644 trigger_error('Please call SimplePie_Cache::create() instead of the constructor', E_USER_ERROR); 8645 } 8646 8647 /** 8648 * Create a new SimplePie_Cache object 8649 * 8650 * @static 8651 * @access public 8652 */ 8653 function create($location, $filename, $extension) 8654 { 8655 $location_iri = new SimplePie_IRI($location); 8656 switch ($location_iri->get_scheme()) 8657 { 8658 case 'mysql': 8659 if (extension_loaded('mysql')) 8660 { 8661 return new SimplePie_Cache_MySQL($location_iri, $filename, $extension); 8662 } 8663 break; 8664 8665 default: 8666 return new SimplePie_Cache_File($location, $filename, $extension); 8667 } 8668 } 8669 } 8670 8671 class SimplePie_Cache_File 8672 { 8673 var $location; 8674 var $filename; 8675 var $extension; 8676 var $name; 8677 8678 function SimplePie_Cache_File($location, $filename, $extension) 8679 { 8680 $this->location = $location; 8681 $this->filename = $filename; 8682 $this->extension = $extension; 8683 $this->name = "$this->location/$this->filename.$this->extension"; 8684 } 8685 8686 function save($data) 8687 { 8688 if (file_exists($this->name) && is_writeable($this->name) || file_exists($this->location) && is_writeable($this->location)) 8689 { 8690 if (is_a($data, 'SimplePie')) 8691 { 8692 $data = $data->data; 8693 } 8694 8695 $data = serialize($data); 8696 8697 if (function_exists('file_put_contents')) 8698 { 8699 return (bool) file_put_contents($this->name, $data); 8700 } 8701 else 8702 { 8703 $fp = fopen($this->name, 'wb'); 8704 if ($fp) 8705 { 8706 fwrite($fp, $data); 8707 fclose($fp); 8708 return true; 8709 } 8710 } 8711 } 8712 return false; 8713 } 8714 8715 function load() 8716 { 8717 if (file_exists($this->name) && is_readable($this->name)) 8718 { 8719 return unserialize(file_get_contents($this->name)); 8720 } 8721 return false; 8722 } 8723 8724 function mtime() 8725 { 8726 if (file_exists($this->name)) 8727 { 8728 return filemtime($this->name); 8729 } 8730 return false; 8731 } 8732 8733 function touch() 8734 { 8735 if (file_exists($this->name)) 8736 { 8737 return touch($this->name); 8738 } 8739 return false; 8740 } 8741 8742 function unlink() 8743 { 8744 if (file_exists($this->name)) 8745 { 8746 return unlink($this->name); 8747 } 8748 return false; 8749 } 8750 } 8751 8752 class SimplePie_Cache_DB 8753 { 8754 function prepare_simplepie_object_for_cache($data) 8755 { 8756 $items = $data->get_items(); 8757 $items_by_id = array(); 8758 8759 if (!empty($items)) 8760 { 8761 foreach ($items as $item) 8762 { 8763 $items_by_id[$item->get_id()] = $item; 8764 } 8765 8766 if (count($items_by_id) !== count($items)) 8767 { 8768 $items_by_id = array(); 8769 foreach ($items as $item) 8770 { 8771 $items_by_id[$item->get_id(true)] = $item; 8772 } 8773 } 8774 8775 if (isset($data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0])) 8776 { 8777 $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]; 8778 } 8779 elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0])) 8780 { 8781 $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]; 8782 } 8783 elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0])) 8784 { 8785 $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]; 8786 } 8787 elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['channel'][0])) 8788 { 8789 $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['channel'][0]; 8790 } 8791 else 8792 { 8793 $channel = null; 8794 } 8795 8796 if ($channel !== null) 8797 { 8798 if (isset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry'])) 8799 { 8800 unset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry']); 8801 } 8802 if (isset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['entry'])) 8803 { 8804 unset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['entry']); 8805 } 8806 if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item'])) 8807 { 8808 unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item']); 8809 } 8810 if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item'])) 8811 { 8812 unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item']); 8813 } 8814 if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_20]['item'])) 8815 { 8816 unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_20]['item']); 8817 } 8818 } 8819 if (isset($data->data['items'])) 8820 { 8821 unset($data->data['items']); 8822 } 8823 if (isset($data->data['ordered_items'])) 8824 { 8825 unset($data->data['ordered_items']); 8826 } 8827 } 8828 return array(serialize($data->data), $items_by_id); 8829 } 8830 } 8831 8832 class SimplePie_Cache_MySQL extends SimplePie_Cache_DB 8833 { 8834 var $mysql; 8835 var $options; 8836 var $id; 8837 8838 function SimplePie_Cache_MySQL($mysql_location, $name, $extension) 8839 { 8840 $host = $mysql_location->get_host(); 8841 if (SimplePie_Misc::stripos($host, 'unix(') === 0 && substr($host, -1) === ')') 8842 { 8843 $server = ':' . substr($host, 5, -1); 8844 } 8845 else 8846 { 8847 $server = $host; 8848 if ($mysql_location->get_port() !== null) 8849 { 8850 $server .= ':' . $mysql_location->get_port(); 8851 } 8852 } 8853 8854 if (strpos($mysql_location->get_userinfo(), ':') !== false) 8855 { 8856 list($username, $password) = explode(':', $mysql_location->get_userinfo(), 2); 8857 } 8858 else 8859 { 8860 $username = $mysql_location->get_userinfo(); 8861 $password = null; 8862 } 8863 8864 if ($this->mysql = mysql_connect($server, $username, $password)) 8865 { 8866 $this->id = $name . $extension; 8867 $this->options = SimplePie_Misc::parse_str($mysql_location->get_query()); 8868 if (!isset($this->options['prefix'][0])) 8869 { 8870 $this->options['prefix'][0] = ''; 8871 } 8872 8873 if (mysql_select_db(ltrim($mysql_location->get_path(), '/')) 8874 && mysql_query('SET NAMES utf8') 8875 && ($query = mysql_unbuffered_query('SHOW TABLES'))) 8876 { 8877 $db = array(); 8878 while ($row = mysql_fetch_row($query)) 8879 { 8880 $db[] = $row[0]; 8881 } 8882 8883 if (!in_array($this->options['prefix'][0] . 'cache_data', $db)) 8884 { 8885 if (!mysql_query('CREATE TABLE `' . $this->options['prefix'][0] . 'cache_data` (`id` TEXT CHARACTER SET utf8 NOT NULL, `items` SMALLINT NOT NULL DEFAULT 0, `data` BLOB NOT NULL, `mtime` INT UNSIGNED NOT NULL, UNIQUE (`id`(125)))')) 8886 { 8887 $this->mysql = null; 8888 } 8889 } 8890 8891 if (!in_array($this->options['prefix'][0] . 'items', $db)) 8892 { 8893 if (!mysql_query('CREATE TABLE `' . $this->options['prefix'][0] . 'items` (`feed_id` TEXT CHARACTER SET utf8 NOT NULL, `id` TEXT CHARACTER SET utf8 NOT NULL, `data` TEXT CHARACTER SET utf8 NOT NULL, `posted` INT UNSIGNED NOT NULL, INDEX `feed_id` (`feed_id`(125)))')) 8894 { 8895 $this->mysql = null; 8896 } 8897 } 8898 } 8899 else 8900 { 8901 $this->mysql = null; 8902 } 8903 } 8904 } 8905 8906 function save($data) 8907 { 8908 if ($this->mysql) 8909 { 8910 $feed_id = "'" . mysql_real_escape_string($this->id) . "'"; 8911 8912 if (is_a($data, 'SimplePie')) 8913 { 8914 if (SIMPLEPIE_PHP5) 8915 { 8916 // This keyword needs to defy coding standards for PHP4 compatibility 8917 $data = clone($data); 8918 } 8919 8920 $prepared = $this->prepare_simplepie_object_for_cache($data); 8921 8922 if ($query = mysql_query('SELECT `id` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = ' . $feed_id, $this->mysql)) 8923 { 8924 if (mysql_num_rows($query)) 8925 { 8926 $items = count($prepared[1]); 8927 if ($items) 8928 { 8929 $sql = 'UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `items` = ' . $items . ', `data` = \'' . mysql_real_escape_string($prepared[0]) . '\', `mtime` = ' . time() . ' WHERE `id` = ' . $feed_id; 8930 } 8931 else 8932 { 8933 $sql = 'UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `data` = \'' . mysql_real_escape_string($prepared[0]) . '\', `mtime` = ' . time() . ' WHERE `id` = ' . $feed_id; 8934 } 8935 8936 if (!mysql_query($sql, $this->mysql)) 8937 { 8938 return false; 8939 } 8940 } 8941 elseif (!mysql_query('INSERT INTO `' . $this->options['prefix'][0] . 'cache_data` (`id`, `items`, `data`, `mtime`) VALUES(' . $feed_id . ', ' . count($prepared[1]) . ', \'' . mysql_real_escape_string($prepared[0]) . '\', ' . time() . ')', $this->mysql)) 8942 { 8943 return false; 8944 } 8945 8946 $ids = array_keys($prepared[1]); 8947 if (!empty($ids)) 8948 { 8949 foreach ($ids as $id) 8950 { 8951 $database_ids[] = mysql_real_escape_string($id); 8952 } 8953 8954 if ($query = mysql_unbuffered_query('SELECT `id` FROM `' . $this->options['prefix'][0] . 'items` WHERE `id` = \'' . implode('\' OR `id` = \'', $database_ids) . '\' AND `feed_id` = ' . $feed_id, $this->mysql)) 8955 { 8956 $existing_ids = array(); 8957 while ($row = mysql_fetch_row($query)) 8958 { 8959 $existing_ids[] = $row[0]; 8960 } 8961 8962 $new_ids = array_diff($ids, $existing_ids); 8963 8964 foreach ($new_ids as $new_id) 8965 { 8966 if (!($date = $prepared[1][$new_id]->get_date('U'))) 8967 { 8968 $date = time(); 8969 } 8970 8971 if (!mysql_query('INSERT INTO `' . $this->options['prefix'][0] . 'items` (`feed_id`, `id`, `data`, `posted`) VALUES(' . $feed_id . ', \'' . mysql_real_escape_string($new_id) . '\', \'' . mysql_real_escape_string(serialize($prepared[1][$new_id]->data)) . '\', ' . $date . ')', $this->mysql)) 8972 { 8973 return false; 8974 } 8975 } 8976 return true; 8977 } 8978 } 8979 else 8980 { 8981 return true; 8982 } 8983 } 8984 } 8985 elseif ($query = mysql_query('SELECT `id` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = ' . $feed_id, $this->mysql)) 8986 { 8987 if (mysql_num_rows($query)) 8988 { 8989 if (mysql_query('UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `items` = 0, `data` = \'' . mysql_real_escape_string(serialize($data)) . '\', `mtime` = ' . time() . ' WHERE `id` = ' . $feed_id, $this->mysql)) 8990 { 8991 return true; 8992 } 8993 } 8994 elseif (mysql_query('INSERT INTO `' . $this->options['prefix'][0] . 'cache_data` (`id`, `items`, `data`, `mtime`) VALUES(\'' . mysql_real_escape_string($this->id) . '\', 0, \'' . mysql_real_escape_string(serialize($data)) . '\', ' . time() . ')', $this->mysql)) 8995 { 8996 return true; 8997 } 8998 } 8999 } 9000 return false; 9001 } 9002 9003 function load() 9004 { 9005 if ($this->mysql && ($query = mysql_query('SELECT `items`, `data` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && ($row = mysql_fetch_row($query))) 9006 { 9007 $data = unserialize($row[1]); 9008 9009 if (isset($this->options['items'][0])) 9010 { 9011 $items = (int) $this->options['items'][0]; 9012 } 9013 else 9014 { 9015 $items = (int) $row[0]; 9016 } 9017 9018 if ($items !== 0) 9019 { 9020 if (isset($data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0])) 9021 { 9022 $feed =& $data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]; 9023 } 9024 elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0])) 9025 { 9026 $feed =& $data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]; 9027 } 9028 elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0])) 9029 { 9030 $feed =& $data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]; 9031 } 9032 elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0])) 9033 { 9034 $feed =& $data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]; 9035 } 9036 else 9037 { 9038 $feed = null; 9039 } 9040 9041 if ($feed !== null) 9042 { 9043 $sql = 'SELECT `data` FROM `' . $this->options['prefix'][0] . 'items` WHERE `feed_id` = \'' . mysql_real_escape_string($this->id) . '\' ORDER BY `posted` DESC'; 9044 if ($items > 0) 9045 { 9046 $sql .= ' LIMIT ' . $items; 9047 } 9048 9049 if ($query = mysql_unbuffered_query($sql, $this->mysql)) 9050 { 9051 while ($row = mysql_fetch_row($query)) 9052 { 9053 $feed['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry'][] = unserialize($row[0]); 9054 } 9055 } 9056 else 9057 { 9058 return false; 9059 } 9060 } 9061 } 9062 return $data; 9063 } 9064 return false; 9065 } 9066 9067 function mtime() 9068 { 9069 if ($this->mysql && ($query = mysql_query('SELECT `mtime` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && ($row = mysql_fetch_row($query))) 9070 { 9071 return $row[0]; 9072 } 9073 else 9074 { 9075 return false; 9076 } 9077 } 9078 9079 function touch() 9080 { 9081 if ($this->mysql && ($query = mysql_query('UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `mtime` = ' . time() . ' WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && mysql_affected_rows($this->mysql)) 9082 { 9083 return true; 9084 } 9085 else 9086 { 9087 return false; 9088 } 9089 } 9090 9091 function unlink() 9092 { 9093 if ($this->mysql && ($query = mysql_query('DELETE FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && ($query2 = mysql_query('DELETE FROM `' . $this->options['prefix'][0] . 'items` WHERE `feed_id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql))) 9094 { 9095 return true; 9096 } 9097 else 9098 { 9099 return false; 9100 } 9101 } 9102 } 9103 9104 class SimplePie_Misc 9105 { 9106 function time_hms($seconds) 9107 { 9108 $time = ''; 9109 9110 $hours = floor($seconds / 3600); 9111 $remainder = $seconds % 3600; 9112 if ($hours > 0) 9113 { 9114 $time .= $hours.':'; 9115 } 9116 9117 $minutes = floor($remainder / 60); 9118 $seconds = $remainder % 60; 9119 if ($minutes < 10 && $hours > 0) 9120 { 9121 $minutes = '0' . $minutes; 9122 } 9123 if ($seconds < 10) 9124 { 9125 $seconds = '0' . $seconds; 9126 } 9127 9128 $time .= $minutes.':'; 9129 $time .= $seconds; 9130 9131 return $time; 9132 } 9133 9134 function absolutize_url($relative, $base) 9135 { 9136 $iri = SimplePie_IRI::absolutize(new SimplePie_IRI($base), $relative); 9137 return $iri->get_iri(); 9138 } 9139 9140 function remove_dot_segments($input) 9141 { 9142 $output = ''; 9143 while (strpos($input, './') !== false || strpos($input, '/.') !== false || $input === '.' || $input === '..') 9144 { 9145 // A: If the input buffer begins with a prefix of "../" or "./", then remove that prefix from the input buffer; otherwise, 9146 if (strpos($input, '../') === 0) 9147 { 9148 $input = substr($input, 3); 9149 } 9150 elseif (strpos($input, './') === 0) 9151 { 9152 $input = substr($input, 2); 9153 } 9154 // B: if the input buffer begins with a prefix of "/./" or "/.", where "." is a complete path segment, then replace that prefix with "/" in the input buffer; otherwise, 9155 elseif (strpos($input, '/./') === 0) 9156 { 9157 $input = substr_replace($input, '/', 0, 3); 9158 } 9159 elseif ($input === '/.') 9160 { 9161 $input = '/'; 9162 } 9163 // C: if the input buffer begins with a prefix of "/../" or "/..", where ".." is a complete path segment, then replace that prefix with "/" in the input buffer and remove the last segment and its preceding "/" (if any) from the output buffer; otherwise, 9164 elseif (strpos($input, '/../') === 0) 9165 { 9166 $input = substr_replace($input, '/', 0, 4); 9167 $output = substr_replace($output, '', strrpos($output, '/')); 9168 } 9169 elseif ($input === '/..') 9170 { 9171 $input = '/'; 9172 $output = substr_replace($output, '', strrpos($output, '/')); 9173 } 9174 // D: if the input buffer consists only of "." or "..", then remove that from the input buffer; otherwise, 9175 elseif ($input === '.' || $input === '..') 9176 { 9177 $input = ''; 9178 } 9179 // E: move the first path segment in the input buffer to the end of the output buffer, including the initial "/" character (if any) and any subsequent characters up to, but not including, the next "/" character or the end of the input buffer 9180 elseif (($pos = strpos($input, '/', 1)) !== false) 9181 { 9182 $output .= substr($input, 0, $pos); 9183 $input = substr_replace($input, '', 0, $pos); 9184 } 9185 else 9186 { 9187 $output .= $input; 9188 $input = ''; 9189 } 9190 } 9191 return $output . $input; 9192 } 9193 9194 function get_element($realname, $string) 9195 { 9196 $return = array(); 9197 $name = preg_quote($realname, '/'); 9198 if (preg_match_all("/<($name)" . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . "(>(.*)<\/$name>|(\/)?>)/siU", $string, $matches, PREG_SET_ORDER | PREG_OFFSET_CAPTURE)) 9199 { 9200 for ($i = 0, $total_matches = count($matches); $i < $total_matches; $i++) 9201 { 9202 $return[$i]['tag'] = $realname; 9203 $return[$i]['full'] = $matches[$i][0][0]; 9204 $return[$i]['offset'] = $matches[$i][0][1]; 9205 if (strlen($matches[$i][3][0]) <= 2) 9206 { 9207 $return[$i]['self_closing'] = true; 9208 } 9209 else 9210 { 9211 $return[$i]['self_closing'] = false; 9212 $return[$i]['content'] = $matches[$i][4][0]; 9213 } 9214 $return[$i]['attribs'] = array(); 9215 if (isset($matches[$i][2][0]) && preg_match_all('/[\x09\x0A\x0B\x0C\x0D\x20]+([^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3D\x3E]*)(?:[\x09\x0A\x0B\x0C\x0D\x20]*=[\x09\x0A\x0B\x0C\x0D\x20]*(?:"([^"]*)"|\'([^\']*)\'|([^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?/', ' ' . $matches[$i][2][0] . ' ', $attribs, PREG_SET_ORDER)) 9216 { 9217 for ($j = 0, $total_attribs = count($attribs); $j < $total_attribs; $j++) 9218 { 9219 if (count($attribs[$j]) === 2) 9220 { 9221 $attribs[$j][2] = $attribs[$j][1]; 9222 } 9223 $return[$i]['attribs'][strtolower($attribs[$j][1])]['data'] = SimplePie_Misc::entities_decode(end($attribs[$j]), 'UTF-8'); 9224 } 9225 } 9226 } 9227 } 9228 return $return; 9229 } 9230 9231 function element_implode($element) 9232 { 9233 $full = "<$element[tag]"; 9234 foreach ($element['attribs'] as $key => $value) 9235 { 9236 $key = strtolower($key); 9237 $full .= " $key=\"" . htmlspecialchars($value['data']) . '"'; 9238 } 9239 if ($element['self_closing']) 9240 { 9241 $full .= ' />'; 9242 } 9243 else 9244 { 9245 $full .= ">$element[content]</$element[tag]>"; 9246 } 9247 return $full; 9248 } 9249 9250 function error($message, $level, $file, $line) 9251 { 9252 if ((ini_get('error_reporting') & $level) > 0) 9253 { 9254 switch ($level) 9255 { 9256 case E_USER_ERROR: 9257 $note = 'PHP Error'; 9258 break; 9259 case E_USER_WARNING: 9260 $note = 'PHP Warning'; 9261 break; 9262 case E_USER_NOTICE: 9263 $note = 'PHP Notice'; 9264 break; 9265 default: 9266 $note = 'Unknown Error'; 9267 break; 9268 } 9269 9270 $log_error = true; 9271 if (!function_exists('error_log')) 9272 { 9273 $log_error = false; 9274 } 9275 9276 $log_file = @ini_get('error_log'); 9277 if (!empty($log_file) && ('syslog' != $log_file) && !@is_writable($log_file)) 9278 { 9279 $log_error = false; 9280 } 9281 9282 if ($log_error) 9283 { 9284 @error_log("$note: $message in $file on line $line", 0); 9285 } 9286 } 9287 9288 return $message; 9289 } 9290 9291 /** 9292 * If a file has been cached, retrieve and display it. 9293 * 9294 * This is most useful for caching images (get_favicon(), etc.), 9295 * however it works for all cached files. This WILL NOT display ANY 9296 * file/image/page/whatever, but rather only display what has already 9297 * been cached by SimplePie. 9298 * 9299 * @access public 9300 * @see SimplePie::get_favicon() 9301 * @param str $identifier_url URL that is used to identify the content. 9302 * This may or may not be the actual URL of the live content. 9303 * @param str $cache_location Location of SimplePie's cache. Defaults 9304 * to './cache'. 9305 * @param str $cache_extension The file extension that the file was 9306 * cached with. Defaults to 'spc'. 9307 * @param str $cache_class Name of the cache-handling class being used 9308 * in SimplePie. Defaults to 'SimplePie_Cache', and should be left 9309 * as-is unless you've overloaded the class. 9310 * @param str $cache_name_function Obsolete. Exists for backwards 9311 * compatibility reasons only. 9312 */ 9313 function display_cached_file($identifier_url, $cache_location = './cache', $cache_extension = 'spc', $cache_class = 'SimplePie_Cache', $cache_name_function = 'md5') 9314 { 9315 $cache = call_user_func(array($cache_class, 'create'), $cache_location, $identifier_url, $cache_extension); 9316 9317 if ($file = $cache->load()) 9318 { 9319 if (isset($file['headers']['content-type'])) 9320 { 9321 header('Content-type:' . $file['headers']['content-type']); 9322 } 9323 else 9324 { 9325 header('Content-type: application/octet-stream'); 9326 } 9327 header('Expires: ' . gmdate('D, d M Y H:i:s', time() + 604800) . ' GMT'); // 7 days 9328 echo $file['body']; 9329 exit; 9330 } 9331 9332 die('Cached file for ' . $identifier_url . ' cannot be found.'); 9333 } 9334 9335 function fix_protocol($url, $http = 1) 9336 { 9337 $url = SimplePie_Misc::normalize_url($url); 9338 $parsed = SimplePie_Misc::parse_url($url); 9339 if ($parsed['scheme'] !== '' && $parsed['scheme'] !== 'http' && $parsed['scheme'] !== 'https') 9340 { 9341 return SimplePie_Misc::fix_protocol(SimplePie_Misc::compress_parse_url('http', $parsed['authority'], $parsed['path'], $parsed['query'], $parsed['fragment']), $http); 9342 } 9343 9344 if ($parsed['scheme'] === '' && $parsed['authority'] === '' && !file_exists($url)) 9345 { 9346 return SimplePie_Misc::fix_protocol(SimplePie_Misc::compress_parse_url('http', $parsed['path'], '', $parsed['query'], $parsed['fragment']), $http); 9347 } 9348 9349 if ($http === 2 && $parsed['scheme'] !== '') 9350 { 9351 return "feed:$url"; 9352 } 9353 elseif ($http === 3 && strtolower($parsed['scheme']) === 'http') 9354 { 9355 return substr_replace($url, 'podcast', 0, 4); 9356 } 9357 elseif ($http === 4 && strtolower($parsed['scheme']) === 'http') 9358 { 9359 return substr_replace($url, 'itpc', 0, 4); 9360 } 9361 else 9362 { 9363 return $url; 9364 } 9365 } 9366 9367 function parse_url($url) 9368 { 9369 $iri = new SimplePie_IRI($url); 9370 return array( 9371 'scheme' => (string) $iri->get_scheme(), 9372 'authority' => (string) $iri->get_authority(), 9373 'path' => (string) $iri->get_path(), 9374 'query' => (string) $iri->get_query(), 9375 'fragment' => (string) $iri->get_fragment() 9376 ); 9377 } 9378 9379 function compress_parse_url($scheme = '', $authority = '', $path = '', $query = '', $fragment = '') 9380 { 9381 $iri = new SimplePie_IRI(''); 9382 $iri->set_scheme($scheme); 9383 $iri->set_authority($authority); 9384 $iri->set_path($path); 9385 $iri->set_query($query); 9386 $iri->set_fragment($fragment); 9387 return $iri->get_iri(); 9388 } 9389 9390 function normalize_url($url) 9391 { 9392 $iri = new SimplePie_IRI($url); 9393 return $iri->get_iri(); 9394 } 9395 9396 function percent_encoding_normalization($match) 9397 { 9398 $integer = hexdec($match[1]); 9399 if ($integer >= 0x41 && $integer <= 0x5A || $integer >= 0x61 && $integer <= 0x7A || $integer >= 0x30 && $integer <= 0x39 || $integer === 0x2D || $integer === 0x2E || $integer === 0x5F || $integer === 0x7E) 9400 { 9401 return chr($integer); 9402 } 9403 else 9404 { 9405 return strtoupper($match[0]); 9406 } 9407 } 9408 9409 /** 9410 * Remove bad UTF-8 bytes 9411 * 9412 * PCRE Pattern to locate bad bytes in a UTF-8 string comes from W3C 9413 * FAQ: Multilingual Forms (modified to include full ASCII range) 9414 * 9415 * @author Geoffrey Sneddon 9416 * @see http://www.w3.org/International/questions/qa-forms-utf-8 9417 * @param string $str String to remove bad UTF-8 bytes from 9418 * @return string UTF-8 string 9419 */ 9420 function utf8_bad_replace($str) 9421 { 9422 if (function_exists('iconv') && ($return = @iconv('UTF-8', 'UTF-8//IGNORE', $str))) 9423 { 9424 return $return; 9425 } 9426 elseif (function_exists('mb_convert_encoding') && ($return = @mb_convert_encoding($str, 'UTF-8', 'UTF-8'))) 9427 { 9428 return $return; 9429 } 9430 elseif (preg_match_all('/(?:[\x00-\x7F]|[\xC2-\xDF][\x80-\xBF]|\xE0[\xA0-\xBF][\x80-\xBF]|[\xE1-\xEC\xEE\xEF][\x80-\xBF]{2}|\xED[\x80-\x9F][\x80-\xBF]|\xF0[\x90-\xBF][\x80-\xBF]{2}|[\xF1-\xF3][\x80-\xBF]{3}|\xF4[\x80-\x8F][\x80-\xBF]{2})+/', $str, $matches)) 9431 { 9432 return implode("\xEF\xBF\xBD", $matches[0]); 9433 } 9434 elseif ($str !== '') 9435 { 9436 return "\xEF\xBF\xBD"; 9437 } 9438 else 9439 { 9440 return ''; 9441 } 9442 } 9443 9444 /** 9445 * Converts a Windows-1252 encoded string to a UTF-8 encoded string 9446 * 9447 * @static 9448 * @access public 9449 * @param string $string Windows-1252 encoded string 9450 * @return string UTF-8 encoded string 9451 */ 9452 function windows_1252_to_utf8($string) 9453 { 9454 static $convert_table = array("\x80" => "\xE2\x82\xAC", "\x81" => "\xEF\xBF\xBD", "\x82" => "\xE2\x80\x9A", "\x83" => "\xC6\x92", "\x84" => "\xE2\x80\x9E", "\x85" => "\xE2\x80\xA6", "\x86" => "\xE2\x80\xA0", "\x87" => "\xE2\x80\xA1", "\x88" => "\xCB\x86", "\x89" => "\xE2\x80\xB0", "\x8A" => "\xC5\xA0", "\x8B" => "\xE2\x80\xB9", "\x8C" => "\xC5\x92", "\x8D" => "\xEF\xBF\xBD", "\x8E" => "\xC5\xBD", "\x8F" => "\xEF\xBF\xBD", "\x90" => "\xEF\xBF\xBD", "\x91" => "\xE2\x80\x98", "\x92" => "\xE2\x80\x99", "\x93" => "\xE2\x80\x9C", "\x94" => "\xE2\x80\x9D", "\x95" => "\xE2\x80\xA2", "\x96" => "\xE2\x80\x93", "\x97" => "\xE2\x80\x94", "\x98" => "\xCB\x9C", "\x99" => "\xE2\x84\xA2", "\x9A" => "\xC5\xA1", "\x9B" => "\xE2\x80\xBA", "\x9C" => "\xC5\x93", "\x9D" => "\xEF\xBF\xBD", "\x9E" => "\xC5\xBE", "\x9F" => "\xC5\xB8", "\xA0" => "\xC2\xA0", "\xA1" => "\xC2\xA1", "\xA2" => "\xC2\xA2", "\xA3" => "\xC2\xA3", "\xA4" => "\xC2\xA4", "\xA5" => "\xC2\xA5", "\xA6" => "\xC2\xA6", "\xA7" => "\xC2\xA7", "\xA8" => "\xC2\xA8", "\xA9" => "\xC2\xA9", "\xAA" => "\xC2\xAA", "\xAB" => "\xC2\xAB", "\xAC" => "\xC2\xAC", "\xAD" => "\xC2\xAD", "\xAE" => "\xC2\xAE", "\xAF" => "\xC2\xAF", "\xB0" => "\xC2\xB0", "\xB1" => "\xC2\xB1", "\xB2" => "\xC2\xB2", "\xB3" => "\xC2\xB3", "\xB4" => "\xC2\xB4", "\xB5" => "\xC2\xB5", "\xB6" => "\xC2\xB6", "\xB7" => "\xC2\xB7", "\xB8" => "\xC2\xB8", "\xB9" => "\xC2\xB9", "\xBA" => "\xC2\xBA", "\xBB" => "\xC2\xBB", "\xBC" => "\xC2\xBC", "\xBD" => "\xC2\xBD", "\xBE" => "\xC2\xBE", "\xBF" => "\xC2\xBF", "\xC0" => "\xC3\x80", "\xC1" => "\xC3\x81", "\xC2" => "\xC3\x82", "\xC3" => "\xC3\x83", "\xC4" => "\xC3\x84", "\xC5" => "\xC3\x85", "\xC6" => "\xC3\x86", "\xC7" => "\xC3\x87", "\xC8" => "\xC3\x88", "\xC9" => "\xC3\x89", "\xCA" => "\xC3\x8A", "\xCB" => "\xC3\x8B", "\xCC" => "\xC3\x8C", "\xCD" => "\xC3\x8D", "\xCE" => "\xC3\x8E", "\xCF" => "\xC3\x8F", "\xD0" => "\xC3\x90", "\xD1" => "\xC3\x91", "\xD2" => "\xC3\x92", "\xD3" => "\xC3\x93", "\xD4" => "\xC3\x94", "\xD5" => "\xC3\x95", "\xD6" => "\xC3\x96", "\xD7" => "\xC3\x97", "\xD8" => "\xC3\x98", "\xD9" => "\xC3\x99", "\xDA" => "\xC3\x9A", "\xDB" => "\xC3\x9B", "\xDC" => "\xC3\x9C", "\xDD" => "\xC3\x9D", "\xDE" => "\xC3\x9E", "\xDF" => "\xC3\x9F", "\xE0" => "\xC3\xA0", "\xE1" => "\xC3\xA1", "\xE2" => "\xC3\xA2", "\xE3" => "\xC3\xA3", "\xE4" => "\xC3\xA4", "\xE5" => "\xC3\xA5", "\xE6" => "\xC3\xA6", "\xE7" => "\xC3\xA7", "\xE8" => "\xC3\xA8", "\xE9" => "\xC3\xA9", "\xEA" => "\xC3\xAA", "\xEB" => "\xC3\xAB", "\xEC" => "\xC3\xAC", "\xED" => "\xC3\xAD", "\xEE" => "\xC3\xAE", "\xEF" => "\xC3\xAF", "\xF0" => "\xC3\xB0", "\xF1" => "\xC3\xB1", "\xF2" => "\xC3\xB2", "\xF3" => "\xC3\xB3", "\xF4" => "\xC3\xB4", "\xF5" => "\xC3\xB5", "\xF6" => "\xC3\xB6", "\xF7" => "\xC3\xB7", "\xF8" => "\xC3\xB8", "\xF9" => "\xC3\xB9", "\xFA" => "\xC3\xBA", "\xFB" => "\xC3\xBB", "\xFC" => "\xC3\xBC", "\xFD" => "\xC3\xBD", "\xFE" => "\xC3\xBE", "\xFF" => "\xC3\xBF"); 9455 9456 return strtr($string, $convert_table); 9457 } 9458 9459 function change_encoding($data, $input, $output) 9460 { 9461 $input = SimplePie_Misc::encoding($input); 9462 $output = SimplePie_Misc::encoding($output); 9463 9464 // We fail to fail on non US-ASCII bytes 9465 if ($input === 'US-ASCII') 9466 { 9467 static $non_ascii_octects = ''; 9468 if (!$non_ascii_octects) 9469 { 9470 for ($i = 0x80; $i <= 0xFF; $i++) 9471 { 9472 $non_ascii_octects .= chr($i); 9473 } 9474 } 9475 $data = substr($data, 0, strcspn($data, $non_ascii_octects)); 9476 } 9477 9478 // This is first, as behaviour of this is completely predictable 9479 if ($input === 'windows-1252' && $output === 'UTF-8') 9480 { 9481 return SimplePie_Misc::windows_1252_to_utf8($data); 9482 } 9483 // This is second, as behaviour of this varies only with PHP version (the middle part of this expression checks the encoding is supported). 9484 elseif (function_exists('mb_convert_encoding') && @mb_convert_encoding("\x80", 'UTF-16BE', $input) !== "\x00\x80" && in_array($input, mb_list_encodings()) && ($return = @mb_convert_encoding($data, $output, $input))) 9485 { 9486 return $return; 9487 } 9488 // This is last, as behaviour of this varies with OS userland and PHP version 9489 elseif (function_exists('iconv') && ($return = @iconv($input, $output, $data))) 9490 { 9491 return $return; 9492 } 9493 // If we can't do anything, just fail 9494 else 9495 { 9496 return false; 9497 } 9498 } 9499 9500 /** 9501 * Normalize an encoding name 9502 * 9503 * This is automatically generated by create.php 9504 * 9505 * To generate it, run `php create.php` on the command line, and copy the 9506 * output to replace this function. 9507 * 9508 * @param string $charset Character set to standardise 9509 * @return string Standardised name 9510 */ 9511 function encoding($charset) 9512 { 9513 // Normalization from UTS #22 9514 switch (strtolower(preg_replace('/(?:[^a-zA-Z0-9]+|([^0-9])0+)/', '\1', $charset))) 9515 { 9516 case 'adobestandardencoding': 9517 case 'csadobestandardencoding': 9518 return 'Adobe-Standard-Encoding'; 9519 9520 case 'adobesymbolencoding': 9521 case 'cshppsmath': 9522 return 'Adobe-Symbol-Encoding'; 9523 9524 case 'ami1251': 9525 case 'amiga1251': 9526 return 'Amiga-1251'; 9527 9528 case 'ansix31101983': 9529 case 'csat5001983': 9530 case 'csiso99naplps': 9531 case 'isoir99': 9532 case 'naplps': 9533 return 'ANSI_X3.110-1983'; 9534 9535 case 'arabic7': 9536 case 'asmo449': 9537 case 'csiso89asmo449': 9538 case 'iso9036': 9539 case 'isoir89': 9540 return 'ASMO_449'; 9541 9542 case 'big5': 9543 case 'csbig5': 9544 return 'Big5'; 9545 9546 case 'big5hkscs': 9547 return 'Big5-HKSCS'; 9548 9549 case 'bocu1': 9550 case 'csbocu1': 9551 return 'BOCU-1'; 9552 9553 case 'brf': 9554 case 'csbrf': 9555 return 'BRF'; 9556 9557 case 'bs4730': 9558 case 'csiso4unitedkingdom': 9559 case 'gb': 9560 case 'iso646gb': 9561 case 'isoir4': 9562 case 'uk': 9563 return 'BS_4730'; 9564 9565 case 'bsviewdata': 9566 case 'csiso47bsviewdata': 9567 case 'isoir47': 9568 return 'BS_viewdata'; 9569 9570 case 'cesu8': 9571 case 'cscesu8': 9572 return 'CESU-8'; 9573 9574 case 'ca': 9575 case 'csa71': 9576 case 'csaz243419851': 9577 case 'csiso121canadian1': 9578 case 'iso646ca': 9579 case 'isoir121': 9580 return 'CSA_Z243.4-1985-1'; 9581 9582 case 'csa72': 9583 case 'csaz243419852': 9584 case 'csiso122canadian2': 9585 case 'iso646ca2': 9586 case 'isoir122': 9587 return 'CSA_Z243.4-1985-2'; 9588 9589 case 'csaz24341985gr': 9590 case 'csiso123csaz24341985gr': 9591 case 'isoir123': 9592 return 'CSA_Z243.4-1985-gr'; 9593 9594 case 'csiso139csn369103': 9595 case 'csn369103': 9596 case 'isoir139': 9597 return 'CSN_369103'; 9598 9599 case 'csdecmcs': 9600 case 'dec': 9601 case 'decmcs': 9602 return 'DEC-MCS'; 9603 9604 case 'csiso21german': 9605 case 'de': 9606 case 'din66003': 9607 case 'iso646de': 9608 case 'isoir21': 9609 return 'DIN_66003'; 9610 9611 case 'csdkus': 9612 case 'dkus': 9613 return 'dk-us'; 9614 9615 case 'csiso646danish': 9616 case 'dk': 9617 case 'ds2089': 9618 case 'iso646dk': 9619 return 'DS_2089'; 9620 9621 case 'csibmebcdicatde': 9622 case 'ebcdicatde': 9623 return 'EBCDIC-AT-DE'; 9624 9625 case 'csebcdicatdea': 9626 case 'ebcdicatdea': 9627 return 'EBCDIC-AT-DE-A'; 9628 9629 case 'csebcdiccafr': 9630 case 'ebcdiccafr': 9631 return 'EBCDIC-CA-FR'; 9632 9633 case 'csebcdicdkno': 9634 case 'ebcdicdkno': 9635 return 'EBCDIC-DK-NO'; 9636 9637 case 'csebcdicdknoa': 9638 case 'ebcdicdknoa': 9639 return 'EBCDIC-DK-NO-A'; 9640 9641 case 'csebcdices': 9642 case 'ebcdices': 9643 return 'EBCDIC-ES'; 9644 9645 case 'csebcdicesa': 9646 case 'ebcdicesa': 9647 return 'EBCDIC-ES-A'; 9648 9649 case 'csebcdicess': 9650 case 'ebcdicess': 9651 return 'EBCDIC-ES-S'; 9652 9653 case 'csebcdicfise': 9654 case 'ebcdicfise': 9655 return 'EBCDIC-FI-SE'; 9656 9657 case 'csebcdicfisea': 9658 case 'ebcdicfisea': 9659 return 'EBCDIC-FI-SE-A'; 9660 9661 case 'csebcdicfr': 9662 case 'ebcdicfr': 9663 return 'EBCDIC-FR'; 9664 9665 case 'csebcdicit': 9666 case 'ebcdicit': 9667 return 'EBCDIC-IT'; 9668 9669 case 'csebcdicpt': 9670 case 'ebcdicpt': 9671 return 'EBCDIC-PT'; 9672 9673 case 'csebcdicuk': 9674 case 'ebcdicuk': 9675 return 'EBCDIC-UK'; 9676 9677 case 'csebcdicus': 9678 case 'ebcdicus': 9679 return 'EBCDIC-US'; 9680 9681 case 'csiso111ecmacyrillic': 9682 case 'ecmacyrillic': 9683 case 'isoir111': 9684 case 'koi8e': 9685 return 'ECMA-cyrillic'; 9686 9687 case 'csiso17spanish': 9688 case 'es': 9689 case 'iso646es': 9690 case 'isoir17': 9691 return 'ES'; 9692 9693 case 'csiso85spanish2': 9694 case 'es2': 9695 case 'iso646es2': 9696 case 'isoir85': 9697 return 'ES2'; 9698 9699 case 'cseucpkdfmtjapanese': 9700 case 'eucjp': 9701 case 'extendedunixcodepackedformatforjapanese': 9702 return 'EUC-JP'; 9703 9704 case 'cseucfixwidjapanese': 9705 case 'extendedunixcodefixedwidthforjapanese': 9706 return 'Extended_UNIX_Code_Fixed_Width_for_Japanese'; 9707 9708 case 'gb18030': 9709 return 'GB18030'; 9710 9711 case 'chinese': 9712 case 'cp936': 9713 case 'csgb2312': 9714 case 'csiso58gb231280': 9715 case 'gb2312': 9716 case 'gb231280': 9717 case 'gbk': 9718 case 'isoir58': 9719 case 'ms936': 9720 case 'windows936': 9721 return 'GBK'; 9722 9723 case 'cn': 9724 case 'csiso57gb1988': 9725 case 'gb198880': 9726 case 'iso646cn': 9727 case 'isoir57': 9728 return 'GB_1988-80'; 9729 9730 case 'csiso153gost1976874': 9731 case 'gost1976874': 9732 case 'isoir153': 9733 case 'stsev35888': 9734 return 'GOST_19768-74'; 9735 9736 case 'csiso150': 9737 case 'csiso150greekccitt': 9738 case 'greekccitt': 9739 case 'isoir150': 9740 return 'greek-ccitt'; 9741 9742 case 'csiso88greek7': 9743 case 'greek7': 9744 case 'isoir88': 9745 return 'greek7'; 9746 9747 case 'csiso18greek7old': 9748 case 'greek7old': 9749 case 'isoir18': 9750 return 'greek7-old'; 9751 9752 case 'cshpdesktop': 9753 case 'hpdesktop': 9754 return 'HP-DeskTop'; 9755 9756 case 'cshplegal': 9757 case 'hplegal': 9758 return 'HP-Legal'; 9759 9760 case 'cshpmath8': 9761 case 'hpmath8': 9762 return 'HP-Math8'; 9763 9764 case 'cshppifont': 9765 case 'hppifont': 9766 return 'HP-Pi-font'; 9767 9768 case 'cshproman8': 9769 case 'hproman8': 9770 case 'r8': 9771 case 'roman8': 9772 return 'hp-roman8'; 9773 9774 case 'hzgb2312': 9775 return 'HZ-GB-2312'; 9776 9777 case 'csibmsymbols': 9778 case 'ibmsymbols': 9779 return 'IBM-Symbols'; 9780 9781 case 'csibmthai': 9782 case 'ibmthai': 9783 return 'IBM-Thai'; 9784 9785 case 'cp37': 9786 case 'csibm37': 9787 case 'ebcdiccpca': 9788 case 'ebcdiccpnl': 9789 case 'ebcdiccpus': 9790 case 'ebcdiccpwt': 9791 case 'ibm37': 9792 return 'IBM037'; 9793 9794 case 'cp38': 9795 case 'csibm38': 9796 case 'ebcdicint': 9797 case 'ibm38': 9798 return 'IBM038'; 9799 9800 case 'cp273': 9801 case 'csibm273': 9802 case 'ibm273': 9803 return 'IBM273'; 9804 9805 case 'cp274': 9806 case 'csibm274': 9807 case 'ebcdicbe': 9808 case 'ibm274': 9809 return 'IBM274'; 9810 9811 case 'cp275': 9812 case 'csibm275': 9813 case 'ebcdicbr': 9814 case 'ibm275': 9815 return 'IBM275'; 9816 9817 case 'csibm277': 9818 case 'ebcdiccpdk': 9819 case 'ebcdiccpno': 9820 case 'ibm277': 9821 return 'IBM277'; 9822 9823 case 'cp278': 9824 case 'csibm278': 9825 case 'ebcdiccpfi': 9826 case 'ebcdiccpse': 9827 case 'ibm278': 9828 return 'IBM278'; 9829 9830 case 'cp280': 9831 case 'csibm280': 9832 case 'ebcdiccpit': 9833 case 'ibm280': 9834 return 'IBM280'; 9835 9836 case 'cp281': 9837 case 'csibm281': 9838 case 'ebcdicjpe': 9839 case 'ibm281': 9840 return 'IBM281'; 9841 9842 case 'cp284': 9843 case 'csibm284': 9844 case 'ebcdiccpes': 9845 case 'ibm284': 9846 return 'IBM284'; 9847 9848 case 'cp285': 9849 case 'csibm285': 9850 case 'ebcdiccpgb': 9851 case 'ibm285': 9852 return 'IBM285'; 9853 9854 case 'cp290': 9855 case 'csibm290': 9856 case 'ebcdicjpkana': 9857 case 'ibm290': 9858 return 'IBM290'; 9859 9860 case 'cp297': 9861 case 'csibm297': 9862 case 'ebcdiccpfr': 9863 case 'ibm297': 9864 return 'IBM297'; 9865 9866 case 'cp420': 9867 case 'csibm420': 9868 case 'ebcdiccpar1': 9869 case 'ibm420': 9870 return 'IBM420'; 9871 9872 case 'cp423': 9873 case 'csibm423': 9874 case 'ebcdiccpgr': 9875 case 'ibm423': 9876 return 'IBM423'; 9877 9878 case 'cp424': 9879 case 'csibm424': 9880 case 'ebcdiccphe': 9881 case 'ibm424': 9882 return 'IBM424'; 9883 9884 case '437': 9885 case 'cp437': 9886 case 'cspc8codepage437': 9887 case 'ibm437': 9888 return 'IBM437'; 9889 9890 case 'cp500': 9891 case 'csibm500': 9892 case 'ebcdiccpbe': 9893 case 'ebcdiccpch': 9894 case 'ibm500': 9895 return 'IBM500'; 9896 9897 case 'cp775': 9898 case 'cspc775baltic': 9899 case 'ibm775': 9900 return 'IBM775'; 9901 9902 case '850': 9903 case 'cp850': 9904 case 'cspc850multilingual': 9905 case 'ibm850': 9906 return 'IBM850'; 9907 9908 case '851': 9909 case 'cp851': 9910 case 'csibm851': 9911 case 'ibm851': 9912 return 'IBM851'; 9913 9914 case '852': 9915 case 'cp852': 9916 case 'cspcp852': 9917 case 'ibm852': 9918 return 'IBM852'; 9919 9920 case '855': 9921 case 'cp855': 9922 case 'csibm855': 9923 case 'ibm855': 9924 return 'IBM855'; 9925 9926 case '857': 9927 case 'cp857': 9928 case 'csibm857': 9929 case 'ibm857': 9930 return 'IBM857'; 9931 9932 case 'ccsid858': 9933 case 'cp858': 9934 case 'ibm858': 9935 case 'pcmultilingual850euro': 9936 return 'IBM00858'; 9937 9938 case '860': 9939 case 'cp860': 9940 case 'csibm860': 9941 case 'ibm860': 9942 return 'IBM860'; 9943 9944 case '861': 9945 case 'cp861': 9946 case 'cpis': 9947 case 'csibm861': 9948 case 'ibm861': 9949 return 'IBM861'; 9950 9951 case '862': 9952 case 'cp862': 9953 case 'cspc862latinhebrew': 9954 case 'ibm862': 9955 return 'IBM862'; 9956 9957 case '863': 9958 case 'cp863': 9959 case 'csibm863': 9960 case 'ibm863': 9961 return 'IBM863'; 9962 9963 case 'cp864': 9964 case 'csibm864': 9965 case 'ibm864': 9966 return 'IBM864'; 9967 9968 case '865': 9969 case 'cp865': 9970 case 'csibm865': 9971 case 'ibm865': 9972 return 'IBM865'; 9973 9974 case '866': 9975 case 'cp866': 9976 case 'csibm866': 9977 case 'ibm866': 9978 return 'IBM866'; 9979 9980 case 'cp868': 9981 case 'cpar': 9982 case 'csibm868': 9983 case 'ibm868': 9984 return 'IBM868'; 9985 9986 case '869': 9987 case 'cp869': 9988 case 'cpgr': 9989 case 'csibm869': 9990 case 'ibm869': 9991 return 'IBM869'; 9992 9993 case 'cp870': 9994 case 'csibm870': 9995 case 'ebcdiccproece': 9996 case 'ebcdiccpyu': 9997 case 'ibm870': 9998 return 'IBM870'; 9999 10000 case 'cp871': 10001 case 'csibm871': 10002 case 'ebcdiccpis': 10003 case 'ibm871': 10004 return 'IBM871'; 10005 10006 case 'cp880': 10007 case 'csibm880': 10008 case 'ebcdiccyrillic': 10009 case 'ibm880': 10010 return 'IBM880'; 10011 10012 case 'cp891': 10013 case 'csibm891': 10014 case 'ibm891': 10015 return 'IBM891'; 10016 10017 case 'cp903': 10018 case 'csibm903': 10019 case 'ibm903': 10020 return 'IBM903'; 10021 10022 case '904': 10023 case 'cp904': 10024 case 'csibbm904': 10025 case 'ibm904': 10026 return 'IBM904'; 10027 10028 case 'cp905': 10029 case 'csibm905': 10030 case 'ebcdiccptr': 10031 case 'ibm905': 10032 return 'IBM905'; 10033 10034 case 'cp918': 10035 case 'csibm918': 10036 case 'ebcdiccpar2': 10037 case 'ibm918': 10038 return 'IBM918'; 10039 10040 case 'ccsid924': 10041 case 'cp924': 10042 case 'ebcdiclatin9euro': 10043 case 'ibm924': 10044 return 'IBM00924'; 10045 10046 case 'cp1026': 10047 case 'csibm1026': 10048 case 'ibm1026': 10049 return 'IBM1026'; 10050 10051 case 'ibm1047': 10052 return 'IBM1047'; 10053 10054 case 'ccsid1140': 10055 case 'cp1140': 10056 case 'ebcdicus37euro': 10057 case 'ibm1140': 10058 return 'IBM01140'; 10059 10060 case 'ccsid1141': 10061 case 'cp1141': 10062 case 'ebcdicde273euro': 10063 case 'ibm1141': 10064 return 'IBM01141'; 10065 10066 case 'ccsid1142': 10067 case 'cp1142': 10068 case 'ebcdicdk277euro': 10069 case 'ebcdicno277euro': 10070 case 'ibm1142': 10071 return 'IBM01142'; 10072 10073 case 'ccsid1143': 10074 case 'cp1143': 10075 case 'ebcdicfi278euro': 10076 case 'ebcdicse278euro': 10077 case 'ibm1143': 10078 return 'IBM01143'; 10079 10080 case 'ccsid1144': 10081 case 'cp1144': 10082 case 'ebcdicit280euro': 10083 case 'ibm1144': 10084 return 'IBM01144'; 10085 10086 case 'ccsid1145': 10087 case 'cp1145': 10088 case 'ebcdices284euro': 10089 case 'ibm1145': 10090 return 'IBM01145'; 10091 10092 case 'ccsid1146': 10093 case 'cp1146': 10094 case 'ebcdicgb285euro': 10095 case 'ibm1146': 10096 return 'IBM01146'; 10097 10098 case 'ccsid1147': 10099 case 'cp1147': 10100 case 'ebcdicfr297euro': 10101 case 'ibm1147': 10102 return 'IBM01147'; 10103 10104 case 'ccsid1148': 10105 case 'cp1148': 10106 case 'ebcdicinternational500euro': 10107 case 'ibm1148': 10108 return 'IBM01148'; 10109 10110 case 'ccsid1149': 10111 case 'cp1149': 10112 case 'ebcdicis871euro': 10113 case 'ibm1149': 10114 return 'IBM01149'; 10115 10116 case 'csiso143iecp271': 10117 case 'iecp271': 10118 case 'isoir143': 10119 return 'IEC_P27-1'; 10120 10121 case 'csiso49inis': 10122 case 'inis': 10123 case 'isoir49': 10124 return 'INIS'; 10125 10126 case 'csiso50inis8': 10127 case 'inis8': 10128 case 'isoir50': 10129 return 'INIS-8'; 10130 10131 case 'csiso51iniscyrillic': 10132 case 'iniscyrillic': 10133 case 'isoir51': 10134 return 'INIS-cyrillic'; 10135 10136 case 'csinvariant': 10137 case 'invariant': 10138 return 'INVARIANT'; 10139 10140 case 'iso2022cn': 10141 return 'ISO-2022-CN'; 10142 10143 case 'iso2022cnext': 10144 return 'ISO-2022-CN-EXT'; 10145 10146 case 'csiso2022jp': 10147 case 'iso2022jp': 10148 return 'ISO-2022-JP'; 10149 10150 case 'csiso2022jp2': 10151 case 'iso2022jp2': 10152 return 'ISO-2022-JP-2'; 10153 10154 case 'csiso2022kr': 10155 case 'iso2022kr': 10156 return 'ISO-2022-KR'; 10157 10158 case 'cswindows30latin1': 10159 case 'iso88591windows30latin1': 10160 return 'ISO-8859-1-Windows-3.0-Latin-1'; 10161 10162 case 'cswindows31latin1': 10163 case 'iso88591windows31latin1': 10164 return 'ISO-8859-1-Windows-3.1-Latin-1'; 10165 10166 case 'csisolatin2': 10167 case 'iso88592': 10168 case 'iso885921987': 10169 case 'isoir101': 10170 case 'l2': 10171 case 'latin2': 10172 return 'ISO-8859-2'; 10173 10174 case 'cswindows31latin2': 10175 case 'iso88592windowslatin2': 10176 return 'ISO-8859-2-Windows-Latin-2'; 10177 10178 case 'csisolatin3': 10179 case 'iso88593': 10180 case 'iso885931988': 10181 case 'isoir109': 10182 case 'l3': 10183 case 'latin3': 10184 return 'ISO-8859-3'; 10185 10186 case 'csisolatin4': 10187 case 'iso88594': 10188 case 'iso885941988': 10189 case 'isoir110': 10190 case 'l4': 10191 case 'latin4': 10192 return 'ISO-8859-4'; 10193 10194 case 'csisolatincyrillic': 10195 case 'cyrillic': 10196 case 'iso88595': 10197 case 'iso885951988': 10198 case 'isoir144': 10199 return 'ISO-8859-5'; 10200 10201 case 'arabic': 10202 case 'asmo708': 10203 case 'csisolatinarabic': 10204 case 'ecma114': 10205 case 'iso88596': 10206 case 'iso885961987': 10207 case 'isoir127': 10208 return 'ISO-8859-6'; 10209 10210 case 'csiso88596e': 10211 case 'iso88596e': 10212 return 'ISO-8859-6-E'; 10213 10214 case 'csiso88596i': 10215 case 'iso88596i': 10216 return 'ISO-8859-6-I'; 10217 10218 case 'csisolatingreek': 10219 case 'ecma118': 10220 case 'elot928': 10221 case 'greek': 10222 case 'greek8': 10223 case 'iso88597': 10224 case 'iso885971987': 10225 case 'isoir126': 10226 return 'ISO-8859-7'; 10227 10228 case 'csisolatinhebrew': 10229 case 'hebrew': 10230 case 'iso88598': 10231 case 'iso885981988': 10232 case 'isoir138': 10233 return 'ISO-8859-8'; 10234 10235 case 'csiso88598e': 10236 case 'iso88598e': 10237 return 'ISO-8859-8-E'; 10238 10239 case 'csiso88598i': 10240 case 'iso88598i': 10241 return 'ISO-8859-8-I'; 10242 10243 case 'cswindows31latin5': 10244 case 'iso88599windowslatin5': 10245 return 'ISO-8859-9-Windows-Latin-5'; 10246 10247 case 'csisolatin6': 10248 case 'iso885910': 10249 case 'iso8859101992': 10250 case 'isoir157': 10251 case 'l6': 10252 case 'latin6': 10253 return 'ISO-8859-10'; 10254 10255 case 'iso885913': 10256 return 'ISO-8859-13'; 10257 10258 case 'iso885914': 10259 case 'iso8859141998': 10260 case 'isoceltic': 10261 case 'isoir199': 10262 case 'l8': 10263 case 'latin8': 10264 return 'ISO-8859-14'; 10265 10266 case 'iso885915': 10267 case 'latin9': 10268 return 'ISO-8859-15'; 10269 10270 case 'iso885916': 10271 case 'iso8859162001': 10272 case 'isoir226': 10273 case 'l10': 10274 case 'latin10': 10275 return 'ISO-8859-16'; 10276 10277 case 'iso10646j1': 10278 return 'ISO-10646-J-1'; 10279 10280 case 'csunicode': 10281 case 'iso10646ucs2': 10282 return 'ISO-10646-UCS-2'; 10283 10284 case 'csucs4': 10285 case 'iso10646ucs4': 10286 return 'ISO-10646-UCS-4'; 10287 10288 case 'csunicodeascii': 10289 case 'iso10646ucsbasic': 10290 return 'ISO-10646-UCS-Basic'; 10291 10292 case 'csunicodelatin1': 10293 case 'iso10646': 10294 case 'iso10646unicodelatin1': 10295 return 'ISO-10646-Unicode-Latin1'; 10296 10297 case 'csiso10646utf1': 10298 case 'iso10646utf1': 10299 return 'ISO-10646-UTF-1'; 10300 10301 case 'csiso115481': 10302 case 'iso115481': 10303 case 'isotr115481': 10304 return 'ISO-11548-1'; 10305 10306 case 'csiso90': 10307 case 'isoir90': 10308 return 'iso-ir-90'; 10309 10310 case 'csunicodeibm1261': 10311 case 'isounicodeibm1261': 10312 return 'ISO-Unicode-IBM-1261'; 10313 10314 case 'csunicodeibm1264': 10315 case 'isounicodeibm1264': 10316 return 'ISO-Unicode-IBM-1264'; 10317 10318 case 'csunicodeibm1265': 10319 case 'isounicodeibm1265': 10320 return 'ISO-Unicode-IBM-1265'; 10321 10322 case 'csunicodeibm1268': 10323 case 'isounicodeibm1268': 10324 return 'ISO-Unicode-IBM-1268'; 10325 10326 case 'csunicodeibm1276': 10327 case 'isounicodeibm1276': 10328 return 'ISO-Unicode-IBM-1276'; 10329 10330 case 'csiso646basic1983': 10331 case 'iso646basic1983': 10332 case 'ref': 10333 return 'ISO_646.basic:1983'; 10334 10335 case 'csiso2intlrefversion': 10336 case 'irv': 10337 case 'iso646irv1983': 10338 case 'isoir2': 10339 return 'ISO_646.irv:1983'; 10340 10341 case 'csiso2033': 10342 case 'e13b': 10343 case 'iso20331983': 10344 case 'isoir98': 10345 return 'ISO_2033-1983'; 10346 10347 case 'csiso5427cyrillic': 10348 case 'iso5427': 10349 case 'isoir37': 10350 return 'ISO_5427'; 10351 10352 case 'iso5427cyrillic1981': 10353 case 'iso54271981': 10354 case 'isoir54': 10355 return 'ISO_5427:1981'; 10356 10357 case 'csiso5428greek': 10358 case 'iso54281980': 10359 case 'isoir55': 10360 return 'ISO_5428:1980'; 10361 10362 case 'csiso6937add': 10363 case 'iso6937225': 10364 case 'isoir152': 10365 return 'ISO_6937-2-25'; 10366 10367 case 'csisotextcomm': 10368 case 'iso69372add': 10369 case 'isoir142': 10370 return 'ISO_6937-2-add'; 10371 10372 case 'csiso8859supp': 10373 case 'iso8859supp': 10374 case 'isoir154': 10375 case 'latin125': 10376 return 'ISO_8859-supp'; 10377 10378 case 'csiso10367box': 10379 case 'iso10367box': 10380 case 'isoir155': 10381 return 'ISO_10367-box'; 10382 10383 case 'csiso15italian': 10384 case 'iso646it': 10385 case 'isoir15': 10386 case 'it': 10387 return 'IT'; 10388 10389 case 'csiso13jisc6220jp': 10390 case 'isoir13': 10391 case 'jisc62201969': 10392 case 'jisc62201969jp': 10393 case 'katakana': 10394 case 'x2017': 10395 return 'JIS_C6220-1969-jp'; 10396 10397 case 'csiso14jisc6220ro': 10398 case 'iso646jp': 10399 case 'isoir14': 10400 case 'jisc62201969ro': 10401 case 'jp': 10402 return 'JIS_C6220-1969-ro'; 10403 10404 case 'csiso42jisc62261978': 10405 case 'isoir42': 10406 case 'jisc62261978': 10407 return 'JIS_C6226-1978'; 10408 10409 case 'csiso87jisx208': 10410 case 'isoir87': 10411 case 'jisc62261983': 10412 case 'jisx2081983': 10413 case 'x208': 10414 return 'JIS_C6226-1983'; 10415 10416 case 'csiso91jisc62291984a': 10417 case 'isoir91': 10418 case 'jisc62291984a': 10419 case 'jpocra': 10420 return 'JIS_C6229-1984-a'; 10421 10422 case 'csiso92jisc62991984b': 10423 case 'iso646jpocrb': 10424 case 'isoir92': 10425 case 'jisc62291984b': 10426 case 'jpocrb': 10427 return 'JIS_C6229-1984-b'; 10428 10429 case 'csiso93jis62291984badd': 10430 case 'isoir93': 10431 case 'jisc62291984badd': 10432 case 'jpocrbadd': 10433 return 'JIS_C6229-1984-b-add'; 10434 10435 case 'csiso94jis62291984hand': 10436 case 'isoir94': 10437 case 'jisc62291984hand': 10438 case 'jpocrhand': 10439 return 'JIS_C6229-1984-hand'; 10440 10441 case 'csiso95jis62291984handadd': 10442 case 'isoir95': 10443 case 'jisc62291984handadd': 10444 case 'jpocrhandadd': 10445 return 'JIS_C6229-1984-hand-add'; 10446 10447 case 'csiso96jisc62291984kana': 10448 case 'isoir96': 10449 case 'jisc62291984kana': 10450 return 'JIS_C6229-1984-kana'; 10451 10452 case 'csjisencoding': 10453 case 'jisencoding': 10454 return 'JIS_Encoding'; 10455 10456 case 'cshalfwidthkatakana': 10457 case 'jisx201': 10458 case 'x201': 10459 return 'JIS_X0201'; 10460 10461 case 'csiso159jisx2121990': 10462 case 'isoir159': 10463 case 'jisx2121990': 10464 case 'x212': 10465 return 'JIS_X0212-1990'; 10466 10467 case 'csiso141jusib1002': 10468 case 'iso646yu': 10469 case 'isoir141': 10470 case 'js': 10471 case 'jusib1002': 10472 case 'yu': 10473 return 'JUS_I.B1.002'; 10474 10475 case 'csiso147macedonian': 10476 case 'isoir147': 10477 case 'jusib1003mac': 10478 case 'macedonian': 10479 return 'JUS_I.B1.003-mac'; 10480 10481 case 'csiso146serbian': 10482 case 'isoir146': 10483 case 'jusib1003serb': 10484 case 'serbian': 10485 return 'JUS_I.B1.003-serb'; 10486 10487 case 'koi7switched': 10488 return 'KOI7-switched'; 10489 10490 case 'cskoi8r': 10491 case 'koi8r': 10492 return 'KOI8-R'; 10493 10494 case 'koi8u': 10495 return 'KOI8-U'; 10496 10497 case 'csksc5636': 10498 case 'iso646kr': 10499 case 'ksc5636': 10500 return 'KSC5636'; 10501 10502 case 'cskz1048': 10503 case 'kz1048': 10504 case 'rk1048': 10505 case 'strk10482002': 10506 return 'KZ-1048'; 10507 10508 case 'csiso19latingreek': 10509 case 'isoir19': 10510 case 'latingreek': 10511 return 'latin-greek'; 10512 10513 case 'csiso27latingreek1': 10514 case 'isoir27': 10515 case 'latingreek1': 10516 return 'Latin-greek-1'; 10517 10518 case 'csiso158lap': 10519 case 'isoir158': 10520 case 'lap': 10521 case 'latinlap': 10522 return 'latin-lap'; 10523 10524 case 'csmacintosh': 10525 case 'mac': 10526 case 'macintosh': 10527 return 'macintosh'; 10528 10529 case 'csmicrosoftpublishing': 10530 case 'microsoftpublishing': 10531 return 'Microsoft-Publishing'; 10532 10533 case 'csmnem': 10534 case 'mnem': 10535 return 'MNEM'; 10536 10537 case 'csmnemonic': 10538 case 'mnemonic': 10539 return 'MNEMONIC'; 10540 10541 case 'csiso86hungarian': 10542 case 'hu': 10543 case 'iso646hu': 10544 case 'isoir86': 10545 case 'msz77953': 10546 return 'MSZ_7795.3'; 10547 10548 case 'csnatsdano': 10549 case 'isoir91': 10550 case 'natsdano': 10551 return 'NATS-DANO'; 10552 10553 case 'csnatsdanoadd': 10554 case 'isoir92': 10555 case 'natsdanoadd': 10556 return 'NATS-DANO-ADD'; 10557 10558 case 'csnatssefi': 10559 case 'isoir81': 10560 case 'natssefi': 10561 return 'NATS-SEFI'; 10562 10563 case 'csnatssefiadd': 10564 case 'isoir82': 10565 case 'natssefiadd': 10566 return 'NATS-SEFI-ADD'; 10567 10568 case 'csiso151cuba': 10569 case 'cuba': 10570 case 'iso646cu': 10571 case 'isoir151': 10572 case 'ncnc1081': 10573 return 'NC_NC00-10:81'; 10574 10575 case 'csiso69french': 10576 case 'fr': 10577 case 'iso646fr': 10578 case 'isoir69': 10579 case 'nfz62010': 10580 return 'NF_Z_62-010'; 10581 10582 case 'csiso25french': 10583 case 'iso646fr1': 10584 case 'isoir25': 10585 case 'nfz620101973': 10586 return 'NF_Z_62-010_(1973)'; 10587 10588 case 'csiso60danishnorwegian': 10589 case 'csiso60norwegian1': 10590 case 'iso646no': 10591 case 'isoir60': 10592 case 'no': 10593 case 'ns45511': 10594 return 'NS_4551-1'; 10595 10596 case 'csiso61norwegian2': 10597 case 'iso646no2': 10598 case 'isoir61': 10599 case 'no2': 10600 case 'ns45512': 10601 return 'NS_4551-2'; 10602 10603 case 'osdebcdicdf3irv': 10604 return 'OSD_EBCDIC_DF03_IRV'; 10605 10606 case 'osdebcdicdf41': 10607 return 'OSD_EBCDIC_DF04_1'; 10608 10609 case 'osdebcdicdf415': 10610 return 'OSD_EBCDIC_DF04_15'; 10611 10612 case 'cspc8danishnorwegian': 10613 case 'pc8danishnorwegian': 10614 return 'PC8-Danish-Norwegian'; 10615 10616 case 'cspc8turkish': 10617 case 'pc8turkish': 10618 return 'PC8-Turkish'; 10619 10620 case 'csiso16portuguese': 10621 case 'iso646pt': 10622 case 'isoir16': 10623 case 'pt': 10624 return 'PT'; 10625 10626 case 'csiso84portuguese2': 10627 case 'iso646pt2': 10628 case 'isoir84': 10629 case 'pt2': 10630 return 'PT2'; 10631 10632 case 'cp154': 10633 case 'csptcp154': 10634 case 'cyrillicasian': 10635 case 'pt154': 10636 case 'ptcp154': 10637 return 'PTCP154'; 10638 10639 case 'scsu': 10640 return 'SCSU'; 10641 10642 case 'csiso10swedish': 10643 case 'fi': 10644 case 'iso646fi': 10645 case 'iso646se': 10646 case 'isoir10': 10647 case 'se': 10648 case 'sen850200b': 10649 return 'SEN_850200_B'; 10650 10651 case 'csiso11swedishfornames': 10652 case 'iso646se2': 10653 case 'isoir11': 10654 case 'se2': 10655 case 'sen850200c': 10656 return 'SEN_850200_C'; 10657 10658 case 'csiso102t617bit': 10659 case 'isoir102': 10660 case 't617bit': 10661 return 'T.61-7bit'; 10662 10663 case 'csiso103t618bit': 10664 case 'isoir103': 10665 case 't61': 10666 case 't618bit': 10667 return 'T.61-8bit'; 10668 10669 case 'csiso128t101g2': 10670 case 'isoir128': 10671 case 't101g2': 10672 return 'T.101-G2'; 10673 10674 case 'cstscii': 10675 case 'tscii': 10676 return 'TSCII'; 10677 10678 case 'csunicode11': 10679 case 'unicode11': 10680 return 'UNICODE-1-1'; 10681 10682 case 'csunicode11utf7': 10683 case 'unicode11utf7': 10684 return 'UNICODE-1-1-UTF-7'; 10685 10686 case 'csunknown8bit': 10687 case 'unknown8bit': 10688 return 'UNKNOWN-8BIT'; 10689 10690 case 'ansix341968': 10691 case 'ansix341986': 10692 case 'ascii': 10693 case 'cp367': 10694 case 'csascii': 10695 case 'ibm367': 10696 case 'iso646irv1991': 10697 case 'iso646us': 10698 case 'isoir6': 10699 case 'us': 10700 case 'usascii': 10701 return 'US-ASCII'; 10702 10703 case 'csusdk': 10704 case 'usdk': 10705 return 'us-dk'; 10706 10707 case 'utf7': 10708 return 'UTF-7'; 10709 10710 case 'utf8': 10711 return 'UTF-8'; 10712 10713 case 'utf16': 10714 return 'UTF-16'; 10715 10716 case 'utf16be': 10717 return 'UTF-16BE'; 10718 10719 case 'utf16le': 10720 return 'UTF-16LE'; 10721 10722 case 'utf32': 10723 return 'UTF-32'; 10724 10725 case 'utf32be': 10726 return 'UTF-32BE'; 10727 10728 case 'utf32le': 10729 return 'UTF-32LE'; 10730 10731 case 'csventurainternational': 10732 case 'venturainternational': 10733 return 'Ventura-International'; 10734 10735 case 'csventuramath': 10736 case 'venturamath': 10737 return 'Ventura-Math'; 10738 10739 case 'csventuraus': 10740 case 'venturaus': 10741 return 'Ventura-US'; 10742 10743 case 'csiso70videotexsupp1': 10744 case 'isoir70': 10745 case 'videotexsuppl': 10746 return 'videotex-suppl'; 10747 10748 case 'csviqr': 10749 case 'viqr': 10750 return 'VIQR'; 10751 10752 case 'csviscii': 10753 case 'viscii': 10754 return 'VISCII'; 10755 10756 case 'csshiftjis': 10757 case 'cswindows31j': 10758 case 'mskanji': 10759 case 'shiftjis': 10760 case 'windows31j': 10761 return 'Windows-31J'; 10762 10763 case 'iso885911': 10764 case 'tis620': 10765 return 'windows-874'; 10766 10767 case 'cseuckr': 10768 case 'csksc56011987': 10769 case 'euckr': 10770 case 'isoir149': 10771 case 'korean': 10772 case 'ksc5601': 10773 case 'ksc56011987': 10774 case 'ksc56011989': 10775 case 'windows949': 10776 return 'windows-949'; 10777 10778 case 'windows1250': 10779 return 'windows-1250'; 10780 10781 case 'windows1251': 10782 return 'windows-1251'; 10783 10784 case 'cp819': 10785 case 'csisolatin1': 10786 case 'ibm819': 10787 case 'iso88591': 10788 case 'iso885911987': 10789 case 'isoir100': 10790 case 'l1': 10791 case 'latin1': 10792 case 'windows1252': 10793 return 'windows-1252'; 10794 10795 case 'windows1253': 10796 return 'windows-1253'; 10797 10798 case 'csisolatin5': 10799 case 'iso88599': 10800 case 'iso885991989': 10801 case 'isoir148': 10802 case 'l5': 10803 case 'latin5': 10804 case 'windows1254': 10805 return 'windows-1254'; 10806 10807 case 'windows1255': 10808 return 'windows-1255'; 10809 10810 case 'windows1256': 10811 return 'windows-1256'; 10812 10813 case 'windows1257': 10814 return 'windows-1257'; 10815 10816 case 'windows1258': 10817 return 'windows-1258'; 10818 10819 default: 10820 return $charset; 10821 } 10822 } 10823 10824 function get_curl_version() 10825 { 10826 if (is_array($curl = curl_version())) 10827 { 10828 $curl = $curl['version']; 10829 } 10830 elseif (substr($curl, 0, 5) === 'curl/') 10831 { 10832 $curl = substr($curl, 5, strcspn($curl, "\x09\x0A\x0B\x0C\x0D", 5)); 10833 } 10834 elseif (substr($curl, 0, 8) === 'libcurl/') 10835 { 10836 $curl = substr($curl, 8, strcspn($curl, "\x09\x0A\x0B\x0C\x0D", 8)); 10837 } 10838 else 10839 { 10840 $curl = 0; 10841 } 10842 return $curl; 10843 } 10844 10845 function is_subclass_of($class1, $class2) 10846 { 10847 if (func_num_args() !== 2) 10848 { 10849 trigger_error('Wrong parameter count for SimplePie_Misc::is_subclass_of()', E_USER_WARNING); 10850 } 10851 elseif (version_compare(PHP_VERSION, '5.0.3', '>=') || is_object($class1)) 10852 { 10853 return is_subclass_of($class1, $class2); 10854 } 10855 elseif (is_string($class1) && is_string($class2)) 10856 { 10857 if (class_exists($class1)) 10858 { 10859 if (class_exists($class2)) 10860 { 10861 $class2 = strtolower($class2); 10862 while ($class1 = strtolower(get_parent_class($class1))) 10863 { 10864 if ($class1 === $class2) 10865 { 10866 return true; 10867 } 10868 } 10869 } 10870 } 10871 else 10872 { 10873 trigger_error('Unknown class passed as parameter', E_USER_WARNNG); 10874 } 10875 } 10876 return false; 10877 } 10878 10879 /** 10880 * Strip HTML comments 10881 * 10882 * @access public 10883 * @param string $data Data to strip comments from 10884 * @return string Comment stripped string 10885 */ 10886 function strip_comments($data) 10887 { 10888 $output = ''; 10889 while (($start = strpos($data, '<!--')) !== false) 10890 { 10891 $output .= substr($data, 0, $start); 10892 if (($end = strpos($data, '-->', $start)) !== false) 10893 { 10894 $data = substr_replace($data, '', 0, $end + 3); 10895 } 10896 else 10897 { 10898 $data = ''; 10899 } 10900 } 10901 return $output . $data; 10902 } 10903 10904 function parse_date($dt) 10905 { 10906 $parser = SimplePie_Parse_Date::get(); 10907 return $parser->parse($dt); 10908 } 10909 10910 /** 10911 * Decode HTML entities 10912 * 10913 * @static 10914 * @access public 10915 * @param string $data Input data 10916 * @return string Output data 10917 */ 10918 function entities_decode($data) 10919 { 10920 $decoder = new SimplePie_Decode_HTML_Entities($data); 10921 return $decoder->parse(); 10922 } 10923 10924 /** 10925 * Remove RFC822 comments 10926 * 10927 * @access public 10928 * @param string $data Data to strip comments from 10929 * @return string Comment stripped string 10930 */ 10931 function uncomment_rfc822($string) 10932 { 10933 $string = (string) $string; 10934 $position = 0; 10935 $length = strlen($string); 10936 $depth = 0; 10937 10938 $output = ''; 10939 10940 while ($position < $length && ($pos = strpos($string, '(', $position)) !== false) 10941 { 10942 $output .= substr($string, $position, $pos - $position); 10943 $position = $pos + 1; 10944 if ($string[$pos - 1] !== '\\') 10945 { 10946 $depth++; 10947 while ($depth && $position < $length) 10948 { 10949 $position += strcspn($string, '()', $position); 10950 if ($string[$position - 1] === '\\') 10951 { 10952 $position++; 10953 continue; 10954 } 10955 elseif (isset($string[$position])) 10956 { 10957 switch ($string[$position]) 10958 { 10959 case '(': 10960 $depth++; 10961 break; 10962 10963 case ')': 10964 $depth--; 10965 break; 10966 } 10967 $position++; 10968 } 10969 else 10970 { 10971 break; 10972 } 10973 } 10974 } 10975 else 10976 { 10977 $output .= '('; 10978 } 10979 } 10980 $output .= substr($string, $position); 10981 10982 return $output; 10983 } 10984 10985 function parse_mime($mime) 10986 { 10987 if (($pos = strpos($mime, ';')) === false) 10988 { 10989 return trim($mime); 10990 } 10991 else 10992 { 10993 return trim(substr($mime, 0, $pos)); 10994 } 10995 } 10996 10997 function htmlspecialchars_decode($string, $quote_style) 10998 { 10999 if (function_exists('htmlspecialchars_decode')) 11000 { 11001 return htmlspecialchars_decode($string, $quote_style); 11002 } 11003 else 11004 { 11005 return strtr($string, array_flip(get_html_translation_table(HTML_SPECIALCHARS, $quote_style))); 11006 } 11007 } 11008 11009 function atom_03_construct_type($attribs) 11010 { 11011 if (isset($attribs['']['mode']) && strtolower(trim($attribs['']['mode']) === 'base64')) 11012 { 11013 $mode = SIMPLEPIE_CONSTRUCT_BASE64; 11014 } 11015 else 11016 { 11017 $mode = SIMPLEPIE_CONSTRUCT_NONE; 11018 } 11019 if (isset($attribs['']['type'])) 11020 { 11021 switch (strtolower(trim($attribs['']['type']))) 11022 { 11023 case 'text': 11024 case 'text/plain': 11025 return SIMPLEPIE_CONSTRUCT_TEXT | $mode; 11026 11027 case 'html': 11028 case 'text/html': 11029 return SIMPLEPIE_CONSTRUCT_HTML | $mode; 11030 11031 case 'xhtml': 11032 case 'application/xhtml+xml': 11033 return SIMPLEPIE_CONSTRUCT_XHTML | $mode; 11034 11035 default: 11036 return SIMPLEPIE_CONSTRUCT_NONE | $mode; 11037 } 11038 } 11039 else 11040 { 11041 return SIMPLEPIE_CONSTRUCT_TEXT | $mode; 11042 } 11043 } 11044 11045 function atom_10_construct_type($attribs) 11046 { 11047 if (isset($attribs['']['type'])) 11048 { 11049 switch (strtolower(trim($attribs['']['type']))) 11050 { 11051 case 'text': 11052 return SIMPLEPIE_CONSTRUCT_TEXT; 11053 11054 case 'html': 11055 return SIMPLEPIE_CONSTRUCT_HTML; 11056 11057 case 'xhtml': 11058 return SIMPLEPIE_CONSTRUCT_XHTML; 11059 11060 default: 11061 return SIMPLEPIE_CONSTRUCT_NONE; 11062 } 11063 } 11064 return SIMPLEPIE_CONSTRUCT_TEXT; 11065 } 11066 11067 function atom_10_content_construct_type($attribs) 11068 { 11069 if (isset($attribs['']['type'])) 11070 { 11071 $type = strtolower(trim($attribs['']['type'])); 11072 switch ($type) 11073 { 11074 case 'text': 11075 return SIMPLEPIE_CONSTRUCT_TEXT; 11076 11077 case 'html': 11078 return SIMPLEPIE_CONSTRUCT_HTML; 11079 11080 case 'xhtml': 11081 return SIMPLEPIE_CONSTRUCT_XHTML; 11082 } 11083 if (in_array(substr($type, -4), array('+xml', '/xml')) || substr($type, 0, 5) === 'text/') 11084 { 11085 return SIMPLEPIE_CONSTRUCT_NONE; 11086 } 11087 else 11088 { 11089 return SIMPLEPIE_CONSTRUCT_BASE64; 11090 } 11091 } 11092 else 11093 { 11094 return SIMPLEPIE_CONSTRUCT_TEXT; 11095 } 11096 } 11097 11098 function is_isegment_nz_nc($string) 11099 { 11100 return (bool) preg_match('/^([A-Za-z0-9\-._~\x{A0}-\x{D7FF}\x{F900}-\x{FDCF}\x{FDF0}-\x{FFEF}\x{10000}-\x{1FFFD}\x{20000}-\x{2FFFD}\x{30000}-\x{3FFFD}\x{40000}-\x{4FFFD}\x{50000}-\x{5FFFD}\x{60000}-\x{6FFFD}\x{70000}-\x{7FFFD}\x{80000}-\x{8FFFD}\x{90000}-\x{9FFFD}\x{A0000}-\x{AFFFD}\x{B0000}-\x{BFFFD}\x{C0000}-\x{CFFFD}\x{D0000}-\x{DFFFD}\x{E1000}-\x{EFFFD}!$&\'()*+,;=@]|(%[0-9ABCDEF]{2}))+$/u', $string); 11101 } 11102 11103 function space_seperated_tokens($string) 11104 { 11105 $space_characters = "\x20\x09\x0A\x0B\x0C\x0D"; 11106 $string_length = strlen($string); 11107 11108 $position = strspn($string, $space_characters); 11109 $tokens = array(); 11110 11111 while ($position < $string_length) 11112 { 11113 $len = strcspn($string, $space_characters, $position); 11114 $tokens[] = substr($string, $position, $len); 11115 $position += $len; 11116 $position += strspn($string, $space_characters, $position); 11117 } 11118 11119 return $tokens; 11120 } 11121 11122 function array_unique($array) 11123 { 11124 if (version_compare(PHP_VERSION, '5.2', '>=')) 11125 { 11126 return array_unique($array); 11127 } 11128 else 11129 { 11130 $array = (array) $array; 11131 $new_array = array(); 11132 $new_array_strings = array(); 11133 foreach ($array as $key => $value) 11134 { 11135 if (is_object($value)) 11136 { 11137 if (method_exists($value, '__toString')) 11138 { 11139 $cmp = $value->__toString(); 11140 } 11141 else 11142 { 11143 trigger_error('Object of class ' . get_class($value) . ' could not be converted to string', E_USER_ERROR); 11144 } 11145 } 11146 elseif (is_array($value)) 11147 { 11148 $cmp = (string) reset($value); 11149 } 11150 else 11151 { 11152 $cmp = (string) $value; 11153 } 11154 if (!in_array($cmp, $new_array_strings)) 11155 { 11156 $new_array[$key] = $value; 11157 $new_array_strings[] = $cmp; 11158 } 11159 } 11160 return $new_array; 11161 } 11162 } 11163 11164 /** 11165 * Converts a unicode codepoint to a UTF-8 character 11166 * 11167 * @static 11168 * @access public 11169 * @param int $codepoint Unicode codepoint 11170 * @return string UTF-8 character 11171 */ 11172 function codepoint_to_utf8($codepoint) 11173 { 11174 $codepoint = (int) $codepoint; 11175 if ($codepoint < 0) 11176 { 11177 return false; 11178 } 11179 else if ($codepoint <= 0x7f) 11180 { 11181 return chr($codepoint); 11182 } 11183 else if ($codepoint <= 0x7ff) 11184 { 11185 return chr(0xc0 | ($codepoint >> 6)) . chr(0x80 | ($codepoint & 0x3f)); 11186 } 11187 else if ($codepoint <= 0xffff) 11188 { 11189 return chr(0xe0 | ($codepoint >> 12)) . chr(0x80 | (($codepoint >> 6) & 0x3f)) . chr(0x80 | ($codepoint & 0x3f)); 11190 } 11191 else if ($codepoint <= 0x10ffff) 11192 { 11193 return chr(0xf0 | ($codepoint >> 18)) . chr(0x80 | (($codepoint >> 12) & 0x3f)) . chr(0x80 | (($codepoint >> 6) & 0x3f)) . chr(0x80 | ($codepoint & 0x3f)); 11194 } 11195 else 11196 { 11197 // U+FFFD REPLACEMENT CHARACTER 11198 return "\xEF\xBF\xBD"; 11199 } 11200 } 11201 11202 /** 11203 * Re-implementation of PHP 5's stripos() 11204 * 11205 * Returns the numeric position of the first occurrence of needle in the 11206 * haystack string. 11207 * 11208 * @static 11209 * @access string 11210 * @param object $haystack 11211 * @param string $needle Note that the needle may be a string of one or more 11212 * characters. If needle is not a string, it is converted to an integer 11213 * and applied as the ordinal value of a character. 11214 * @param int $offset The optional offset parameter allows you to specify which 11215 * character in haystack to start searching. The position returned is still 11216 * relative to the beginning of haystack. 11217 * @return bool If needle is not found, stripos() will return boolean false. 11218 */ 11219 function stripos($haystack, $needle, $offset = 0) 11220 { 11221 if (function_exists('stripos')) 11222 { 11223 return stripos($haystack, $needle, $offset); 11224 } 11225 else 11226 { 11227 if (is_string($needle)) 11228 { 11229 $needle = strtolower($needle); 11230 } 11231 elseif (is_int($needle) || is_bool($needle) || is_double($needle)) 11232 { 11233 $needle = strtolower(chr($needle)); 11234 } 11235 else 11236 { 11237 trigger_error('needle is not a string or an integer', E_USER_WARNING); 11238 return false; 11239 } 11240 11241 return strpos(strtolower($haystack), $needle, $offset); 11242 } 11243 } 11244 11245 /** 11246 * Similar to parse_str() 11247 * 11248 * Returns an associative array of name/value pairs, where the value is an 11249 * array of values that have used the same name 11250 * 11251 * @static 11252 * @access string 11253 * @param string $str The input string. 11254 * @return array 11255 */ 11256 function parse_str($str) 11257 { 11258 $return = array(); 11259 $str = explode('&', $str); 11260 11261 foreach ($str as $section) 11262 { 11263 if (strpos($section, '=') !== false) 11264 { 11265 list($name, $value) = explode('=', $section, 2); 11266 $return[urldecode($name)][] = urldecode($value); 11267 } 11268 else 11269 { 11270 $return[urldecode($section)][] = null; 11271 } 11272 } 11273 11274 return $return; 11275 } 11276 11277 /** 11278 * Detect XML encoding, as per XML 1.0 Appendix F.1 11279 * 11280 * @todo Add support for EBCDIC 11281 * @param string $data XML data 11282 * @return array Possible encodings 11283 */ 11284 function xml_encoding($data) 11285 { 11286 // UTF-32 Big Endian BOM 11287 if (substr($data, 0, 4) === "\x00\x00\xFE\xFF") 11288 { 11289 $encoding[] = 'UTF-32BE'; 11290 } 11291 // UTF-32 Little Endian BOM 11292 elseif (substr($data, 0, 4) === "\xFF\xFE\x00\x00") 11293 { 11294 $encoding[] = 'UTF-32LE'; 11295 } 11296 // UTF-16 Big Endian BOM 11297 elseif (substr($data, 0, 2) === "\xFE\xFF") 11298 { 11299 $encoding[] = 'UTF-16BE'; 11300 } 11301 // UTF-16 Little Endian BOM 11302 elseif (substr($data, 0, 2) === "\xFF\xFE") 11303 { 11304 $encoding[] = 'UTF-16LE'; 11305 } 11306 // UTF-8 BOM 11307 elseif (substr($data, 0, 3) === "\xEF\xBB\xBF") 11308 { 11309 $encoding[] = 'UTF-8'; 11310 } 11311 // UTF-32 Big Endian Without BOM 11312 elseif (substr($data, 0, 20) === "\x00\x00\x00\x3C\x00\x00\x00\x3F\x00\x00\x00\x78\x00\x00\x00\x6D\x00\x00\x00\x6C") 11313 { 11314 if ($pos = strpos($data, "\x00\x00\x00\x3F\x00\x00\x00\x3E")) 11315 { 11316 $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 20), 'UTF-32BE', 'UTF-8')); 11317 if ($parser->parse()) 11318 { 11319 $encoding[] = $parser->encoding; 11320 } 11321 } 11322 $encoding[] = 'UTF-32BE'; 11323 } 11324 // UTF-32 Little Endian Without BOM 11325 elseif (substr($data, 0, 20) === "\x3C\x00\x00\x00\x3F\x00\x00\x00\x78\x00\x00\x00\x6D\x00\x00\x00\x6C\x00\x00\x00") 11326 { 11327 if ($pos = strpos($data, "\x3F\x00\x00\x00\x3E\x00\x00\x00")) 11328 { 11329 $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 20), 'UTF-32LE', 'UTF-8')); 11330 if ($parser->parse()) 11331 { 11332 $encoding[] = $parser->encoding; 11333 } 11334 } 11335 $encoding[] = 'UTF-32LE'; 11336 } 11337 // UTF-16 Big Endian Without BOM 11338 elseif (substr($data, 0, 10) === "\x00\x3C\x00\x3F\x00\x78\x00\x6D\x00\x6C") 11339 { 11340 if ($pos = strpos($data, "\x00\x3F\x00\x3E")) 11341 { 11342 $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 10), 'UTF-16BE', 'UTF-8')); 11343 if ($parser->parse()) 11344 { 11345 $encoding[] = $parser->encoding; 11346 } 11347 } 11348 $encoding[] = 'UTF-16BE'; 11349 } 11350 // UTF-16 Little Endian Without BOM 11351 elseif (substr($data, 0, 10) === "\x3C\x00\x3F\x00\x78\x00\x6D\x00\x6C\x00") 11352 { 11353 if ($pos = strpos($data, "\x3F\x00\x3E\x00")) 11354 { 11355 $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 10), 'UTF-16LE', 'UTF-8')); 11356 if ($parser->parse()) 11357 { 11358 $encoding[] = $parser->encoding; 11359 } 11360 } 11361 $encoding[] = 'UTF-16LE'; 11362 } 11363 // US-ASCII (or superset) 11364 elseif (substr($data, 0, 5) === "\x3C\x3F\x78\x6D\x6C") 11365 { 11366 if ($pos = strpos($data, "\x3F\x3E")) 11367 { 11368 $parser = new SimplePie_XML_Declaration_Parser(substr($data, 5, $pos - 5)); 11369 if ($parser->parse()) 11370 { 11371 $encoding[] = $parser->encoding; 11372 } 11373 } 11374 $encoding[] = 'UTF-8'; 11375 } 11376 // Fallback to UTF-8 11377 else 11378 { 11379 $encoding[] = 'UTF-8'; 11380 } 11381 return $encoding; 11382 } 11383 11384 function output_javascript() 11385 { 11386 if (function_exists('ob_gzhandler')) 11387 { 11388 ob_start('ob_gzhandler'); 11389 } 11390 header('Content-type: text/javascript; charset: UTF-8'); 11391 header('Cache-Control: must-revalidate'); 11392 header('Expires: ' . gmdate('D, d M Y H:i:s', time() + 604800) . ' GMT'); // 7 days 11393 ?> 11394 function embed_odeo(link) { 11395 document.writeln('<embed src="http://odeo.com/flash/audio_player_fullsize.swf" pluginspage="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" quality="high" width="440" height="80" wmode="transparent" allowScriptAccess="any" flashvars="valid_sample_rate=true&external_url='+link+'"></embed>'); 11396 } 11397 11398 function embed_quicktime(type, bgcolor, width, height, link, placeholder, loop) { 11399 if (placeholder != '') { 11400 document.writeln('<embed type="'+type+'" style="cursor:hand; cursor:pointer;" href="'+link+'" src="'+placeholder+'" width="'+width+'" height="'+height+'" autoplay="false" target="myself" controller="false" loop="'+loop+'" scale="aspect" bgcolor="'+bgcolor+'" pluginspage="http://www.apple.com/quicktime/download/"></embed>'); 11401 } 11402 else { 11403 document.writeln('<embed type="'+type+'" style="cursor:hand; cursor:pointer;" src="'+link+'" width="'+width+'" height="'+height+'" autoplay="false" target="myself" controller="true" loop="'+loop+'" scale="aspect" bgcolor="'+bgcolor+'" pluginspage="http://www.apple.com/quicktime/download/"></embed>'); 11404 } 11405 } 11406 11407 function embed_flash(bgcolor, width, height, link, loop, type) { 11408 document.writeln('<embed src="'+link+'" pluginspage="http://www.macromedia.com/go/getflashplayer" type="'+type+'" quality="high" width="'+width+'" height="'+height+'" bgcolor="'+bgcolor+'" loop="'+loop+'"></embed>'); 11409 } 11410 11411 function embed_flv(width, height, link, placeholder, loop, player) { 11412 document.writeln('<embed src="'+player+'" pluginspage="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" quality="high" width="'+width+'" height="'+height+'" wmode="transparent" flashvars="file='+link+'&autostart=false&repeat='+loop+'&showdigits=true&showfsbutton=false"></embed>'); 11413 } 11414 11415 function embed_wmedia(width, height, link) { 11416 document.writeln('<embed type="application/x-mplayer2" src="'+link+'" autosize="1" width="'+width+'" height="'+height+'" showcontrols="1" showstatusbar="0" showdisplay="0" autostart="0"></embed>'); 11417 } 11418 <?php 11419 } 11420 11421 11422 11423 /** 11424 * Format debugging information 11425 */ 11426 function debug($sp) 11427 { 11428 $info = 'SimplePie ' . SIMPLEPIE_VERSION . ' Build ' . SIMPLEPIE_BUILD . "\n"; 11429 $info .= 'PHP ' . PHP_VERSION . "\n"; 11430 if ($sp->error() !== null) 11431 { 11432 $info .= 'Error occurred: ' . $sp->error() . "\n"; 11433 } 11434 else 11435 { 11436 $info .= "No error found.\n"; 11437 } 11438 $info .= "Extensions:\n"; 11439 $extensions = array('pcre', 'curl', 'zlib', 'mbstring', 'iconv', 'xmlreader', 'xml'); 11440 foreach ($extensions as $ext) 11441 { 11442 if (extension_loaded($ext)) 11443 { 11444 $info .= " $ext loaded\n"; 11445 switch ($ext) 11446 { 11447 case 'pcre': 11448 $info .= ' Version ' . PCRE_VERSION . "\n"; 11449 break; 11450 case 'curl': 11451 $version = curl_version(); 11452 $info .= ' Version ' . $version['version'] . "\n"; 11453 break; 11454 case 'mbstring': 11455 $info .= ' Overloading: ' . mb_get_info('func_overload') . "\n"; 11456 break; 11457 case 'iconv': 11458 $info .= ' Version ' . ICONV_VERSION . "\n"; 11459 break; 11460 case 'xml': 11461 $info .= ' Version ' . LIBXML_DOTTED_VERSION . "\n"; 11462 break; 11463 } 11464 } 11465 else 11466 { 11467 $info .= " $ext not loaded\n"; 11468 } 11469 } 11470 return $info; 11471 } 11472 } 11473 11474 /** 11475 * Decode HTML Entities 11476 * 11477 * This implements HTML5 as of revision 967 (2007-06-28) 11478 * 11479 * @package SimplePie 11480 */ 11481 class SimplePie_Decode_HTML_Entities 11482 { 11483 /** 11484 * Data to be parsed 11485 * 11486 * @access private 11487 * @var string 11488 */ 11489 var $data = ''; 11490 11491 /** 11492 * Currently consumed bytes 11493 * 11494 * @access private 11495 * @var string 11496 */ 11497 var $consumed = ''; 11498 11499 /** 11500 * Position of the current byte being parsed 11501 * 11502 * @access private 11503 * @var int 11504 */ 11505 var $position = 0; 11506 11507 /** 11508 * Create an instance of the class with the input data 11509 * 11510 * @access public 11511 * @param string $data Input data 11512 */ 11513 function SimplePie_Decode_HTML_Entities($data) 11514 { 11515 $this->data = $data; 11516 } 11517 11518 /** 11519 * Parse the input data 11520 * 11521 * @access public 11522 * @return string Output data 11523 */ 11524 function parse() 11525 { 11526 while (($this->position = strpos($this->data, '&', $this->position)) !== false) 11527 { 11528 $this->consume(); 11529 $this->entity(); 11530 $this->consumed = ''; 11531 } 11532 return $this->data; 11533 } 11534 11535 /** 11536 * Consume the next byte 11537 * 11538 * @access private 11539 * @return mixed The next byte, or false, if there is no more data 11540 */ 11541 function consume() 11542 { 11543 if (isset($this->data[$this->position])) 11544 { 11545 $this->consumed .= $this->data[$this->position]; 11546 return $this->data[$this->position++]; 11547 } 11548 else 11549 { 11550 return false; 11551 } 11552 } 11553 11554 /** 11555 * Consume a range of characters 11556 * 11557 * @access private 11558 * @param string $chars Characters to consume 11559 * @return mixed A series of characters that match the range, or false 11560 */ 11561 function consume_range($chars) 11562 { 11563 if ($len = strspn($this->data, $chars, $this->position)) 11564 { 11565 $data = substr($this->data, $this->position, $len); 11566 $this->consumed .= $data; 11567 $this->position += $len; 11568 return $data; 11569 } 11570 else 11571 { 11572 return false; 11573 } 11574 } 11575 11576 /** 11577 * Unconsume one byte 11578 * 11579 * @access private 11580 */ 11581 function unconsume() 11582 { 11583 $this->consumed = substr($this->consumed, 0, -1); 11584 $this->position--; 11585 } 11586 11587 /** 11588 * Decode an entity 11589 * 11590 * @access private 11591 */ 11592 function entity() 11593 { 11594 switch ($this->consume()) 11595 { 11596 case "\x09": 11597 case "\x0A": 11598 case "\x0B": 11599 case "\x0B": 11600 case "\x0C": 11601 case "\x20": 11602 case "\x3C": 11603 case "\x26": 11604 case false: 11605 break; 11606 11607 case "\x23": 11608 switch ($this->consume()) 11609 { 11610 case "\x78": 11611 case "\x58": 11612 $range = '0123456789ABCDEFabcdef'; 11613 $hex = true; 11614 break; 11615 11616 default: 11617 $range = '0123456789'; 11618 $hex = false; 11619 $this->unconsume(); 11620 break; 11621 } 11622 11623 if ($codepoint = $this->consume_range($range)) 11624 { 11625 static $windows_1252_specials = array(0x0D => "\x0A", 0x80 => "\xE2\x82\xAC", 0x81 => "\xEF\xBF\xBD", 0x82 => "\xE2\x80\x9A", 0x83 => "\xC6\x92", 0x84 => "\xE2\x80\x9E", 0x85 => "\xE2\x80\xA6", 0x86 => "\xE2\x80\xA0", 0x87 => "\xE2\x80\xA1", 0x88 => "\xCB\x86", 0x89 => "\xE2\x80\xB0", 0x8A => "\xC5\xA0", 0x8B => "\xE2\x80\xB9", 0x8C => "\xC5\x92", 0x8D => "\xEF\xBF\xBD", 0x8E => "\xC5\xBD", 0x8F => "\xEF\xBF\xBD", 0x90 => "\xEF\xBF\xBD", 0x91 => "\xE2\x80\x98", 0x92 => "\xE2\x80\x99", 0x93 => "\xE2\x80\x9C", 0x94 => "\xE2\x80\x9D", 0x95 => "\xE2\x80\xA2", 0x96 => "\xE2\x80\x93", 0x97 => "\xE2\x80\x94", 0x98 => "\xCB\x9C", 0x99 => "\xE2\x84\xA2", 0x9A => "\xC5\xA1", 0x9B => "\xE2\x80\xBA", 0x9C => "\xC5\x93", 0x9D => "\xEF\xBF\xBD", 0x9E => "\xC5\xBE", 0x9F => "\xC5\xB8"); 11626 11627 if ($hex) 11628 { 11629 $codepoint = hexdec($codepoint); 11630 } 11631 else 11632 { 11633 $codepoint = intval($codepoint); 11634 } 11635 11636 if (isset($windows_1252_specials[$codepoint])) 11637 { 11638 $replacement = $windows_1252_specials[$codepoint]; 11639 } 11640 else 11641 { 11642 $replacement = SimplePie_Misc::codepoint_to_utf8($codepoint); 11643 } 11644 11645 if (!in_array($this->consume(), array(';', false), true)) 11646 { 11647 $this->unconsume(); 11648 } 11649 11650 $consumed_length = strlen($this->consumed); 11651 $this->data = substr_replace($this->data, $replacement, $this->position - $consumed_length, $consumed_length); 11652 $this->position += strlen($replacement) - $consumed_length; 11653 } 11654 break; 11655 11656 default: 11657 static $entities = array('Aacute' => "\xC3\x81", 'aacute' => "\xC3\xA1", 'Aacute;' => "\xC3\x81", 'aacute;' => "\xC3\xA1", 'Acirc' => "\xC3\x82", 'acirc' => "\xC3\xA2", 'Acirc;' => "\xC3\x82", 'acirc;' => "\xC3\xA2", 'acute' => "\xC2\xB4", 'acute;' => "\xC2\xB4", 'AElig' => "\xC3\x86", 'aelig' => "\xC3\xA6", 'AElig;' => "\xC3\x86", 'aelig;' => "\xC3\xA6", 'Agrave' => "\xC3\x80", 'agrave' => "\xC3\xA0", 'Agrave;' => "\xC3\x80", 'agrave;' => "\xC3\xA0", 'alefsym;' => "\xE2\x84\xB5", 'Alpha;' => "\xCE\x91", 'alpha;' => "\xCE\xB1", 'AMP' => "\x26", 'amp' => "\x26", 'AMP;' => "\x26", 'amp;' => "\x26", 'and;' => "\xE2\x88\xA7", 'ang;' => "\xE2\x88\xA0", 'apos;' => "\x27", 'Aring' => "\xC3\x85", 'aring' => "\xC3\xA5", 'Aring;' => "\xC3\x85", 'aring;' => "\xC3\xA5", 'asymp;' => "\xE2\x89\x88", 'Atilde' => "\xC3\x83", 'atilde' => "\xC3\xA3", 'Atilde;' => "\xC3\x83", 'atilde;' => "\xC3\xA3", 'Auml' => "\xC3\x84", 'auml' => "\xC3\xA4", 'Auml;' => "\xC3\x84", 'auml;' => "\xC3\xA4", 'bdquo;' => "\xE2\x80\x9E", 'Beta;' => "\xCE\x92", 'beta;' => "\xCE\xB2", 'brvbar' => "\xC2\xA6", 'brvbar;' => "\xC2\xA6", 'bull;' => "\xE2\x80\xA2", 'cap;' => "\xE2\x88\xA9", 'Ccedil' => "\xC3\x87", 'ccedil' => "\xC3\xA7", 'Ccedil;' => "\xC3\x87", 'ccedil;' => "\xC3\xA7", 'cedil' => "\xC2\xB8", 'cedil;' => "\xC2\xB8", 'cent' => "\xC2\xA2", 'cent;' => "\xC2\xA2", 'Chi;' => "\xCE\xA7", 'chi;' => "\xCF\x87", 'circ;' => "\xCB\x86", 'clubs;' => "\xE2\x99\xA3", 'cong;' => "\xE2\x89\x85", 'COPY' => "\xC2\xA9", 'copy' => "\xC2\xA9", 'COPY;' => "\xC2\xA9", 'copy;' => "\xC2\xA9", 'crarr;' => "\xE2\x86\xB5", 'cup;' => "\xE2\x88\xAA", 'curren' => "\xC2\xA4", 'curren;' => "\xC2\xA4", 'Dagger;' => "\xE2\x80\xA1", 'dagger;' => "\xE2\x80\xA0", 'dArr;' => "\xE2\x87\x93", 'darr;' => "\xE2\x86\x93", 'deg' => "\xC2\xB0", 'deg;' => "\xC2\xB0", 'Delta;' => "\xCE\x94", 'delta;' => "\xCE\xB4", 'diams;' => "\xE2\x99\xA6", 'divide' => "\xC3\xB7", 'divide;' => "\xC3\xB7", 'Eacute' => "\xC3\x89", 'eacute' => "\xC3\xA9", 'Eacute;' => "\xC3\x89", 'eacute;' => "\xC3\xA9", 'Ecirc' => "\xC3\x8A", 'ecirc' => "\xC3\xAA", 'Ecirc;' => "\xC3\x8A", 'ecirc;' => "\xC3\xAA", 'Egrave' => "\xC3\x88", 'egrave' => "\xC3\xA8", 'Egrave;' => "\xC3\x88", 'egrave;' => "\xC3\xA8", 'empty;' => "\xE2\x88\x85", 'emsp;' => "\xE2\x80\x83", 'ensp;' => "\xE2\x80\x82", 'Epsilon;' => "\xCE\x95", 'epsilon;' => "\xCE\xB5", 'equiv;' => "\xE2\x89\xA1", 'Eta;' => "\xCE\x97", 'eta;' => "\xCE\xB7", 'ETH' => "\xC3\x90", 'eth' => "\xC3\xB0", 'ETH;' => "\xC3\x90", 'eth;' => "\xC3\xB0", 'Euml' => "\xC3\x8B", 'euml' => "\xC3\xAB", 'Euml;' => "\xC3\x8B", 'euml;' => "\xC3\xAB", 'euro;' => "\xE2\x82\xAC", 'exist;' => "\xE2\x88\x83", 'fnof;' => "\xC6\x92", 'forall;' => "\xE2\x88\x80", 'frac12' => "\xC2\xBD", 'frac12;' => "\xC2\xBD", 'frac14' => "\xC2\xBC", 'frac14;' => "\xC2\xBC", 'frac34' => "\xC2\xBE", 'frac34;' => "\xC2\xBE", 'frasl;' => "\xE2\x81\x84", 'Gamma;' => "\xCE\x93", 'gamma;' => "\xCE\xB3", 'ge;' => "\xE2\x89\xA5", 'GT' => "\x3E", 'gt' => "\x3E", 'GT;' => "\x3E", 'gt;' => "\x3E", 'hArr;' => "\xE2\x87\x94", 'harr;' => "\xE2\x86\x94", 'hearts;' => "\xE2\x99\xA5", 'hellip;' => "\xE2\x80\xA6", 'Iacute' => "\xC3\x8D", 'iacute' => "\xC3\xAD", 'Iacute;' => "\xC3\x8D", 'iacute;' => "\xC3\xAD", 'Icirc' => "\xC3\x8E", 'icirc' => "\xC3\xAE", 'Icirc;' => "\xC3\x8E", 'icirc;' => "\xC3\xAE", 'iexcl' => "\xC2\xA1", 'iexcl;' => "\xC2\xA1", 'Igrave' => "\xC3\x8C", 'igrave' => "\xC3\xAC", 'Igrave;' => "\xC3\x8C", 'igrave;' => "\xC3\xAC", 'image;' => "\xE2\x84\x91", 'infin;' => "\xE2\x88\x9E", 'int;' => "\xE2\x88\xAB", 'Iota;' => "\xCE\x99", 'iota;' => "\xCE\xB9", 'iquest' => "\xC2\xBF", 'iquest;' => "\xC2\xBF", 'isin;' => "\xE2\x88\x88", 'Iuml' => "\xC3\x8F", 'iuml' => "\xC3\xAF", 'Iuml;' => "\xC3\x8F", 'iuml;' => "\xC3\xAF", 'Kappa;' => "\xCE\x9A", 'kappa;' => "\xCE\xBA", 'Lambda;' => "\xCE\x9B", 'lambda;' => "\xCE\xBB", 'lang;' => "\xE3\x80\x88", 'laquo' => "\xC2\xAB", 'laquo;' => "\xC2\xAB", 'lArr;' => "\xE2\x87\x90", 'larr;' => "\xE2\x86\x90", 'lceil;' => "\xE2\x8C\x88", 'ldquo;' => "\xE2\x80\x9C", 'le;' => "\xE2\x89\xA4", 'lfloor;' => "\xE2\x8C\x8A", 'lowast;' => "\xE2\x88\x97", 'loz;' => "\xE2\x97\x8A", 'lrm;' => "\xE2\x80\x8E", 'lsaquo;' => "\xE2\x80\xB9", 'lsquo;' => "\xE2\x80\x98", 'LT' => "\x3C", 'lt' => "\x3C", 'LT;' => "\x3C", 'lt;' => "\x3C", 'macr' => "\xC2\xAF", 'macr;' => "\xC2\xAF", 'mdash;' => "\xE2\x80\x94", 'micro' => "\xC2\xB5", 'micro;' => "\xC2\xB5", 'middot' => "\xC2\xB7", 'middot;' => "\xC2\xB7", 'minus;' => "\xE2\x88\x92", 'Mu;' => "\xCE\x9C", 'mu;' => "\xCE\xBC", 'nabla;' => "\xE2\x88\x87", 'nbsp' => "\xC2\xA0", 'nbsp;' => "\xC2\xA0", 'ndash;' => "\xE2\x80\x93", 'ne;' => "\xE2\x89\xA0", 'ni;' => "\xE2\x88\x8B", 'not' => "\xC2\xAC", 'not;' => "\xC2\xAC", 'notin;' => "\xE2\x88\x89", 'nsub;' => "\xE2\x8A\x84", 'Ntilde' => "\xC3\x91", 'ntilde' => "\xC3\xB1", 'Ntilde;' => "\xC3\x91", 'ntilde;' => "\xC3\xB1", 'Nu;' => "\xCE\x9D", 'nu;' => "\xCE\xBD", 'Oacute' => "\xC3\x93", 'oacute' => "\xC3\xB3", 'Oacute;' => "\xC3\x93", 'oacute;' => "\xC3\xB3", 'Ocirc' => "\xC3\x94", 'ocirc' => "\xC3\xB4", 'Ocirc;' => "\xC3\x94", 'ocirc;' => "\xC3\xB4", 'OElig;' => "\xC5\x92", 'oelig;' => "\xC5\x93", 'Ograve' => "\xC3\x92", 'ograve' => "\xC3\xB2", 'Ograve;' => "\xC3\x92", 'ograve;' => "\xC3\xB2", 'oline;' => "\xE2\x80\xBE", 'Omega;' => "\xCE\xA9", 'omega;' => "\xCF\x89", 'Omicron;' => "\xCE\x9F", 'omicron;' => "\xCE\xBF", 'oplus;' => "\xE2\x8A\x95", 'or;' => "\xE2\x88\xA8", 'ordf' => "\xC2\xAA", 'ordf;' => "\xC2\xAA", 'ordm' => "\xC2\xBA", 'ordm;' => "\xC2\xBA", 'Oslash' => "\xC3\x98", 'oslash' => "\xC3\xB8", 'Oslash;' => "\xC3\x98", 'oslash;' => "\xC3\xB8", 'Otilde' => "\xC3\x95", 'otilde' => "\xC3\xB5", 'Otilde;' => "\xC3\x95", 'otilde;' => "\xC3\xB5", 'otimes;' => "\xE2\x8A\x97", 'Ouml' => "\xC3\x96", 'ouml' => "\xC3\xB6", 'Ouml;' => "\xC3\x96", 'ouml;' => "\xC3\xB6", 'para' => "\xC2\xB6", 'para;' => "\xC2\xB6", 'part;' => "\xE2\x88\x82", 'permil;' => "\xE2\x80\xB0", 'perp;' => "\xE2\x8A\xA5", 'Phi;' => "\xCE\xA6", 'phi;' => "\xCF\x86", 'Pi;' => "\xCE\xA0", 'pi;' => "\xCF\x80", 'piv;' => "\xCF\x96", 'plusmn' => "\xC2\xB1", 'plusmn;' => "\xC2\xB1", 'pound' => "\xC2\xA3", 'pound;' => "\xC2\xA3", 'Prime;' => "\xE2\x80\xB3", 'prime;' => "\xE2\x80\xB2", 'prod;' => "\xE2\x88\x8F", 'prop;' => "\xE2\x88\x9D", 'Psi;' => "\xCE\xA8", 'psi;' => "\xCF\x88", 'QUOT' => "\x22", 'quot' => "\x22", 'QUOT;' => "\x22", 'quot;' => "\x22", 'radic;' => "\xE2\x88\x9A", 'rang;' => "\xE3\x80\x89", 'raquo' => "\xC2\xBB", 'raquo;' => "\xC2\xBB", 'rArr;' => "\xE2\x87\x92", 'rarr;' => "\xE2\x86\x92", 'rceil;' => "\xE2\x8C\x89", 'rdquo;' => "\xE2\x80\x9D", 'real;' => "\xE2\x84\x9C", 'REG' => "\xC2\xAE", 'reg' => "\xC2\xAE", 'REG;' => "\xC2\xAE", 'reg;' => "\xC2\xAE", 'rfloor;' => "\xE2\x8C\x8B", 'Rho;' => "\xCE\xA1", 'rho;' => "\xCF\x81", 'rlm;' => "\xE2\x80\x8F", 'rsaquo;' => "\xE2\x80\xBA", 'rsquo;' => "\xE2\x80\x99", 'sbquo;' => "\xE2\x80\x9A", 'Scaron;' => "\xC5\xA0", 'scaron;' => "\xC5\xA1", 'sdot;' => "\xE2\x8B\x85", 'sect' => "\xC2\xA7", 'sect;' => "\xC2\xA7", 'shy' => "\xC2\xAD", 'shy;' => "\xC2\xAD", 'Sigma;' => "\xCE\xA3", 'sigma;' => "\xCF\x83", 'sigmaf;' => "\xCF\x82", 'sim;' => "\xE2\x88\xBC", 'spades;' => "\xE2\x99\xA0", 'sub;' => "\xE2\x8A\x82", 'sube;' => "\xE2\x8A\x86", 'sum;' => "\xE2\x88\x91", 'sup;' => "\xE2\x8A\x83", 'sup1' => "\xC2\xB9", 'sup1;' => "\xC2\xB9", 'sup2' => "\xC2\xB2", 'sup2;' => "\xC2\xB2", 'sup3' => "\xC2\xB3", 'sup3;' => "\xC2\xB3", 'supe;' => "\xE2\x8A\x87", 'szlig' => "\xC3\x9F", 'szlig;' => "\xC3\x9F", 'Tau;' => "\xCE\xA4", 'tau;' => "\xCF\x84", 'there4;' => "\xE2\x88\xB4", 'Theta;' => "\xCE\x98", 'theta;' => "\xCE\xB8", 'thetasym;' => "\xCF\x91", 'thinsp;' => "\xE2\x80\x89", 'THORN' => "\xC3\x9E", 'thorn' => "\xC3\xBE", 'THORN;' => "\xC3\x9E", 'thorn;' => "\xC3\xBE", 'tilde;' => "\xCB\x9C", 'times' => "\xC3\x97", 'times;' => "\xC3\x97", 'TRADE;' => "\xE2\x84\xA2", 'trade;' => "\xE2\x84\xA2", 'Uacute' => "\xC3\x9A", 'uacute' => "\xC3\xBA", 'Uacute;' => "\xC3\x9A", 'uacute;' => "\xC3\xBA", 'uArr;' => "\xE2\x87\x91", 'uarr;' => "\xE2\x86\x91", 'Ucirc' => "\xC3\x9B", 'ucirc' => "\xC3\xBB", 'Ucirc;' => "\xC3\x9B", 'ucirc;' => "\xC3\xBB", 'Ugrave' => "\xC3\x99", 'ugrave' => "\xC3\xB9", 'Ugrave;' => "\xC3\x99", 'ugrave;' => "\xC3\xB9", 'uml' => "\xC2\xA8", 'uml;' => "\xC2\xA8", 'upsih;' => "\xCF\x92", 'Upsilon;' => "\xCE\xA5", 'upsilon;' => "\xCF\x85", 'Uuml' => "\xC3\x9C", 'uuml' => "\xC3\xBC", 'Uuml;' => "\xC3\x9C", 'uuml;' => "\xC3\xBC", 'weierp;' => "\xE2\x84\x98", 'Xi;' => "\xCE\x9E", 'xi;' => "\xCE\xBE", 'Yacute' => "\xC3\x9D", 'yacute' => "\xC3\xBD", 'Yacute;' => "\xC3\x9D", 'yacute;' => "\xC3\xBD", 'yen' => "\xC2\xA5", 'yen;' => "\xC2\xA5", 'yuml' => "\xC3\xBF", 'Yuml;' => "\xC5\xB8", 'yuml;' => "\xC3\xBF", 'Zeta;' => "\xCE\x96", 'zeta;' => "\xCE\xB6", 'zwj;' => "\xE2\x80\x8D", 'zwnj;' => "\xE2\x80\x8C"); 11658 11659 for ($i = 0, $match = null; $i < 9 && $this->consume() !== false; $i++) 11660 { 11661 $consumed = substr($this->consumed, 1); 11662 if (isset($entities[$consumed])) 11663 { 11664 $match = $consumed; 11665 } 11666 } 11667 11668 if ($match !== null) 11669 { 11670 $this->data = substr_replace($this->data, $entities[$match], $this->position - strlen($consumed) - 1, strlen($match) + 1); 11671 $this->position += strlen($entities[$match]) - strlen($consumed) - 1; 11672 } 11673 break; 11674 } 11675 } 11676 } 11677 11678 /** 11679 * IRI parser/serialiser 11680 * 11681 * @package SimplePie 11682 */ 11683 class SimplePie_IRI 11684 { 11685 /** 11686 * Scheme 11687 * 11688 * @access private 11689 * @var string 11690 */ 11691 var $scheme; 11692 11693 /** 11694 * User Information 11695 * 11696 * @access private 11697 * @var string 11698 */ 11699 var $userinfo; 11700 11701 /** 11702 * Host 11703 * 11704 * @access private 11705 * @var string 11706 */ 11707 var $host; 11708 11709 /** 11710 * Port 11711 * 11712 * @access private 11713 * @var string 11714 */ 11715 var $port; 11716 11717 /** 11718 * Path 11719 * 11720 * @access private 11721 * @var string 11722 */ 11723 var $path; 11724 11725 /** 11726 * Query 11727 * 11728 * @access private 11729 * @var string 11730 */ 11731 var $query; 11732 11733 /** 11734 * Fragment 11735 * 11736 * @access private 11737 * @var string 11738 */ 11739 var $fragment; 11740 11741 /** 11742 * Whether the object represents a valid IRI 11743 * 11744 * @access private 11745 * @var array 11746 */ 11747 var $valid = array(); 11748 11749 /** 11750 * Return the entire IRI when you try and read the object as a string 11751 * 11752 * @access public 11753 * @return string 11754 */ 11755 function __toString() 11756 { 11757 return $this->get_iri(); 11758 } 11759 11760 /** 11761 * Create a new IRI object, from a specified string 11762 * 11763 * @access public 11764 * @param string $iri 11765 * @return SimplePie_IRI 11766 */ 11767 function SimplePie_IRI($iri) 11768 { 11769 $iri = (string) $iri; 11770 if ($iri !== '') 11771 { 11772 $parsed = $this->parse_iri($iri); 11773 $this->set_scheme($parsed['scheme']); 11774 $this->set_authority($parsed['authority']); 11775 $this->set_path($parsed['path']); 11776 $this->set_query($parsed['query']); 11777 $this->set_fragment($parsed['fragment']); 11778 } 11779 } 11780 11781 /** 11782 * Create a new IRI object by resolving a relative IRI 11783 * 11784 * @static 11785 * @access public 11786 * @param SimplePie_IRI $base Base IRI 11787 * @param string $relative Relative IRI 11788 * @return SimplePie_IRI 11789 */ 11790 function absolutize($base, $relative) 11791 { 11792 $relative = (string) $relative; 11793 if ($relative !== '') 11794 { 11795 $relative = new SimplePie_IRI($relative); 11796 if ($relative->get_scheme() !== null) 11797 { 11798 $target = $relative; 11799 } 11800 elseif ($base->get_iri() !== null) 11801 { 11802 if ($relative->get_authority() !== null) 11803 { 11804 $target = $relative; 11805 $target->set_scheme($base->get_scheme()); 11806 } 11807 else 11808 { 11809 $target = new SimplePie_IRI(''); 11810 $target->set_scheme($base->get_scheme()); 11811 $target->set_userinfo($base->get_userinfo()); 11812 $target->set_host($base->get_host()); 11813 $target->set_port($base->get_port()); 11814 if ($relative->get_path() !== null) 11815 { 11816 if (strpos($relative->get_path(), '/') === 0) 11817 { 11818 $target->set_path($relative->get_path()); 11819 } 11820 elseif (($base->get_userinfo() !== null || $base->get_host() !== null || $base->get_port() !== null) && $base->get_path() === null) 11821 { 11822 $target->set_path('/' . $relative->get_path()); 11823 } 11824 elseif (($last_segment = strrpos($base->get_path(), '/')) !== false) 11825 { 11826 $target->set_path(substr($base->get_path(), 0, $last_segment + 1) . $relative->get_path()); 11827 } 11828 else 11829 { 11830 $target->set_path($relative->get_path()); 11831 } 11832 $target->set_query($relative->get_query()); 11833 } 11834 else 11835 { 11836 $target->set_path($base->get_path()); 11837 if ($relative->get_query() !== null) 11838 { 11839 $target->set_query($relative->get_query()); 11840 } 11841 elseif ($base->get_query() !== null) 11842 { 11843 $target->set_query($base->get_query()); 11844 } 11845 } 11846 } 11847 $target->set_fragment($relative->get_fragment()); 11848 } 11849 else 11850 { 11851 // No base URL, just return the relative URL 11852 $target = $relative; 11853 } 11854 } 11855 else 11856 { 11857 $target = $base; 11858 } 11859 return $target; 11860 } 11861 11862 /** 11863 * Parse an IRI into scheme/authority/path/query/fragment segments 11864 * 11865 * @access private 11866 * @param string $iri 11867 * @return array 11868 */ 11869 function parse_iri($iri) 11870 { 11871 preg_match('/^(([^:\/?#]+):)?(\/\/([^\/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?$/', $iri, $match); 11872 for ($i = count($match); $i <= 9; $i++) 11873 { 11874 $match[$i] = ''; 11875 } 11876 return array('scheme' => $match[2], 'authority' => $match[4], 'path' => $match[5], 'query' => $match[7], 'fragment' => $match[9]); 11877 } 11878 11879 /** 11880 * Remove dot segments from a path 11881 * 11882 * @access private 11883 * @param string $input 11884 * @return string 11885 */ 11886 function remove_dot_segments($input) 11887 { 11888 $output = ''; 11889 while (strpos($input, './') !== false || strpos($input, '/.') !== false || $input === '.' || $input === '..') 11890 { 11891 // A: If the input buffer begins with a prefix of "../" or "./", then remove that prefix from the input buffer; otherwise, 11892 if (strpos($input, '../') === 0) 11893 { 11894 $input = substr($input, 3); 11895 } 11896 elseif (strpos($input, './') === 0) 11897 { 11898 $input = substr($input, 2); 11899 } 11900 // B: if the input buffer begins with a prefix of "/./" or "/.", where "." is a complete path segment, then replace that prefix with "/" in the input buffer; otherwise, 11901 elseif (strpos($input, '/./') === 0) 11902 { 11903 $input = substr_replace($input, '/', 0, 3); 11904 } 11905 elseif ($input === '/.') 11906 { 11907 $input = '/'; 11908 } 11909 // C: if the input buffer begins with a prefix of "/../" or "/..", where ".." is a complete path segment, then replace that prefix with "/" in the input buffer and remove the last segment and its preceding "/" (if any) from the output buffer; otherwise, 11910 elseif (strpos($input, '/../') === 0) 11911 { 11912 $input = substr_replace($input, '/', 0, 4); 11913 $output = substr_replace($output, '', strrpos($output, '/')); 11914 } 11915 elseif ($input === '/..') 11916 { 11917 $input = '/'; 11918 $output = substr_replace($output, '', strrpos($output, '/')); 11919 } 11920 // D: if the input buffer consists only of "." or "..", then remove that from the input buffer; otherwise, 11921 elseif ($input === '.' || $input === '..') 11922 { 11923 $input = ''; 11924 } 11925 // E: move the first path segment in the input buffer to the end of the output buffer, including the initial "/" character (if any) and any subsequent characters up to, but not including, the next "/" character or the end of the input buffer 11926 elseif (($pos = strpos($input, '/', 1)) !== false) 11927 { 11928 $output .= substr($input, 0, $pos); 11929 $input = substr_replace($input, '', 0, $pos); 11930 } 11931 else 11932 { 11933 $output .= $input; 11934 $input = ''; 11935 } 11936 } 11937 return $output . $input; 11938 } 11939 11940 /** 11941 * Replace invalid character with percent encoding 11942 * 11943 * @param string $string Input string 11944 * @param string $valid_chars Valid characters 11945 * @param int $case Normalise case 11946 * @return string 11947 */ 11948 function replace_invalid_with_pct_encoding($string, $valid_chars, $case = SIMPLEPIE_SAME_CASE, $iprivate = false) 11949 { 11950 // Normalize as many pct-encoded sections as possible 11951 $string = preg_replace_callback('/(?:%[A-Fa-f0-9]{2})+/', array(&$this, 'remove_iunreserved_percent_encoded'), $string); 11952 11953 // Replace invalid percent characters 11954 $string = preg_replace('/%(?![A-Fa-f0-9]{2})/', '%25', $string); 11955 11956 // Add unreserved and % to $valid_chars (the latter is safe because all 11957 // pct-encoded sections are now valid). 11958 $valid_chars .= 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~%'; 11959 11960 // Now replace any bytes that aren't allowed with their pct-encoded versions 11961 $position = 0; 11962 $strlen = strlen($string); 11963 while (($position += strspn($string, $valid_chars, $position)) < $strlen) 11964 { 11965 $value = ord($string[$position]); 11966 11967 // Start position 11968 $start = $position; 11969 11970 // By default we are valid 11971 $valid = true; 11972 11973 // No one byte sequences are valid due to the while. 11974 // Two byte sequence: 11975 if (($value & 0xE0) === 0xC0) 11976 { 11977 $character = ($value & 0x1F) << 6; 11978 $length = 2; 11979 $remaining = 1; 11980 } 11981 // Three byte sequence: 11982 elseif (($value & 0xF0) === 0xE0) 11983 { 11984 $character = ($value & 0x0F) << 12; 11985 $length = 3; 11986 $remaining = 2; 11987 } 11988 // Four byte sequence: 11989 elseif (($value & 0xF8) === 0xF0) 11990 { 11991 $character = ($value & 0x07) << 18; 11992 $length = 4; 11993 $remaining = 3; 11994 } 11995 // Invalid byte: 11996 else 11997 { 11998 $valid = false; 11999 $length = 1; 12000 $remaining = 0; 12001 } 12002 12003 if ($remaining) 12004 { 12005 if ($position + $length <= $strlen) 12006 { 12007 for ($position++; $remaining; $position++) 12008 { 12009 $value = ord($string[$position]); 12010 12011 // Check that the byte is valid, then add it to the character: 12012 if (($value & 0xC0) === 0x80) 12013 { 12014 $character |= ($value & 0x3F) << (--$remaining * 6); 12015 } 12016 // If it is invalid, count the sequence as invalid and reprocess the current byte: 12017 else 12018 { 12019 $valid = false; 12020 $position--; 12021 break; 12022 } 12023 } 12024 } 12025 else 12026 { 12027 $position = $strlen - 1; 12028 $valid = false; 12029 } 12030 } 12031 12032 // Percent encode anything invalid or not in ucschar 12033 if ( 12034 // Invalid sequences 12035 !$valid 12036 // Non-shortest form sequences are invalid 12037 || $length > 1 && $character <= 0x7F 12038 || $length > 2 && $character <= 0x7FF 12039 || $length > 3 && $character <= 0xFFFF 12040 // Outside of range of ucschar codepoints 12041 // Noncharacters 12042 || ($character & 0xFFFE) === 0xFFFE 12043 || $character >= 0xFDD0 && $character <= 0xFDEF 12044 || ( 12045 // Everything else not in ucschar 12046 $character > 0xD7FF && $character < 0xF900 12047 || $character < 0xA0 12048 || $character > 0xEFFFD 12049 ) 12050 && ( 12051 // Everything not in iprivate, if it applies 12052 !$iprivate 12053 || $character < 0xE000 12054 || $character > 0x10FFFD 12055 ) 12056 ) 12057 { 12058 // If we were a character, pretend we weren't, but rather an error. 12059 if ($valid) 12060 $position--; 12061 12062 for ($j = $start; $j <= $position; $j++) 12063 { 12064 $string = substr_replace($string, sprintf('%%%02X', ord($string[$j])), $j, 1); 12065 $j += 2; 12066 $position += 2; 12067 $strlen += 2; 12068 } 12069 } 12070 } 12071 12072 // Normalise case 12073 if ($case & SIMPLEPIE_LOWERCASE) 12074 { 12075 $string = strtolower($string); 12076 } 12077 elseif ($case & SIMPLEPIE_UPPERCASE) 12078 { 12079 $string = strtoupper($string); 12080 } 12081 12082 return $string; 12083 } 12084 12085 /** 12086 * Callback function for preg_replace_callback. 12087 * 12088 * Removes sequences of percent encoded bytes that represent UTF-8 12089 * encoded characters in iunreserved 12090 * 12091 * @access private 12092 * @param array $match PCRE match 12093 * @return string Replacement 12094 */ 12095 function remove_iunreserved_percent_encoded($match) 12096 { 12097 // As we just have valid percent encoded sequences we can just explode 12098 // and ignore the first member of the returned array (an empty string). 12099 $bytes = explode('%', $match[0]); 12100 12101 // Initialize the new string (this is what will be returned) and that 12102 // there are no bytes remaining in the current sequence (unsurprising 12103 // at the first byte!). 12104 $string = ''; 12105 $remaining = 0; 12106 12107 // Loop over each and every byte, and set $value to its value 12108 for ($i = 1, $len = count($bytes); $i < $len; $i++) 12109 { 12110 $value = hexdec($bytes[$i]); 12111 12112 // If we're the first byte of sequence: 12113 if (!$remaining) 12114 { 12115 // Start position 12116 $start = $i; 12117 12118 // By default we are valid 12119 $valid = true; 12120 12121 // One byte sequence: 12122 if ($value <= 0x7F) 12123 { 12124 $character = $value; 12125 $length = 1; 12126 } 12127 // Two byte sequence: 12128 elseif (($value & 0xE0) === 0xC0) 12129 { 12130 $character = ($value & 0x1F) << 6; 12131 $length = 2; 12132 $remaining = 1; 12133 } 12134 // Three byte sequence: 12135 elseif (($value & 0xF0) === 0xE0) 12136 { 12137 $character = ($value & 0x0F) << 12; 12138 $length = 3; 12139 $remaining = 2; 12140 } 12141 // Four byte sequence: 12142 elseif (($value & 0xF8) === 0xF0) 12143 { 12144 $character = ($value & 0x07) << 18; 12145 $length = 4; 12146 $remaining = 3; 12147 } 12148 // Invalid byte: 12149 else 12150 { 12151 $valid = false; 12152 $remaining = 0; 12153 } 12154 } 12155 // Continuation byte: 12156 else 12157 { 12158 // Check that the byte is valid, then add it to the character: 12159 if (($value & 0xC0) === 0x80) 12160 { 12161 $remaining--; 12162 $character |= ($value & 0x3F) << ($remaining * 6); 12163 } 12164 // If it is invalid, count the sequence as invalid and reprocess the current byte as the start of a sequence: 12165 else 12166 { 12167 $valid = false; 12168 $remaining = 0; 12169 $i--; 12170 } 12171 } 12172 12173 // If we've reached the end of the current byte sequence, append it to Unicode::$data 12174 if (!$remaining) 12175 { 12176 // Percent encode anything invalid or not in iunreserved 12177 if ( 12178 // Invalid sequences 12179 !$valid 12180 // Non-shortest form sequences are invalid 12181 || $length > 1 && $character <= 0x7F 12182 || $length > 2 && $character <= 0x7FF 12183 || $length > 3 && $character <= 0xFFFF 12184 // Outside of range of iunreserved codepoints 12185 || $character < 0x2D 12186 || $character > 0xEFFFD 12187 // Noncharacters 12188 || ($character & 0xFFFE) === 0xFFFE 12189 || $character >= 0xFDD0 && $character <= 0xFDEF 12190 // Everything else not in iunreserved (this is all BMP) 12191 || $character === 0x2F 12192 || $character > 0x39 && $character < 0x41 12193 || $character > 0x5A && $character < 0x61 12194 || $character > 0x7A && $character < 0x7E 12195 || $character > 0x7E && $character < 0xA0 12196 || $character > 0xD7FF && $character < 0xF900 12197 ) 12198 { 12199 for ($j = $start; $j <= $i; $j++) 12200 { 12201 $string .= '%' . strtoupper($bytes[$j]); 12202 } 12203 } 12204 else 12205 { 12206 for ($j = $start; $j <= $i; $j++) 12207 { 12208 $string .= chr(hexdec($bytes[$j])); 12209 } 12210 } 12211 } 12212 } 12213 12214 // If we have any bytes left over they are invalid (i.e., we are 12215 // mid-way through a multi-byte sequence) 12216 if ($remaining) 12217 { 12218 for ($j = $start; $j < $len; $j++) 12219 { 12220 $string .= '%' . strtoupper($bytes[$j]); 12221 } 12222 } 12223 12224 return $string; 12225 } 12226 12227 /** 12228 * Check if the object represents a valid IRI 12229 * 12230 * @access public 12231 * @return bool 12232 */ 12233 function is_valid() 12234 { 12235 return array_sum($this->valid) === count($this->valid); 12236 } 12237 12238 /** 12239 * Set the scheme. Returns true on success, false on failure (if there are 12240 * any invalid characters). 12241 * 12242 * @access public 12243 * @param string $scheme 12244 * @return bool 12245 */ 12246 function set_scheme($scheme) 12247 { 12248 if ($scheme === null || $scheme === '') 12249 { 12250 $this->scheme = null; 12251 } 12252 else 12253 { 12254 $len = strlen($scheme); 12255 switch (true) 12256 { 12257 case $len > 1: 12258 if (!strspn($scheme, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+-.', 1)) 12259 { 12260 $this->scheme = null; 12261 $this->valid[__FUNCTION__] = false; 12262 return false; 12263 } 12264 12265 case $len > 0: 12266 if (!strspn($scheme, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz', 0, 1)) 12267 { 12268 $this->scheme = null; 12269 $this->valid[__FUNCTION__] = false; 12270 return false; 12271 } 12272 } 12273 $this->scheme = strtolower($scheme); 12274 } 12275 $this->valid[__FUNCTION__] = true; 12276 return true; 12277 } 12278 12279 /** 12280 * Set the authority. Returns true on success, false on failure (if there are 12281 * any invalid characters). 12282 * 12283 * @access public 12284 * @param string $authority 12285 * @return bool 12286 */ 12287 function set_authority($authority) 12288 { 12289 if (($userinfo_end = strrpos($authority, '@')) !== false) 12290 { 12291 $userinfo = substr($authority, 0, $userinfo_end); 12292 $authority = substr($authority, $userinfo_end + 1); 12293 } 12294 else 12295 { 12296 $userinfo = null; 12297 } 12298 12299 if (($port_start = strpos($authority, ':')) !== false) 12300 { 12301 $port = substr($authority, $port_start + 1); 12302 $authority = substr($authority, 0, $port_start); 12303 } 12304 else 12305 { 12306 $port = null; 12307 } 12308 12309 return $this->set_userinfo($userinfo) && $this->set_host($authority) && $this->set_port($port); 12310 } 12311 12312 /** 12313 * Set the userinfo. 12314 * 12315 * @access public 12316 * @param string $userinfo 12317 * @return bool 12318 */ 12319 function set_userinfo($userinfo) 12320 { 12321 if ($userinfo === null || $userinfo === '') 12322 { 12323 $this->userinfo = null; 12324 } 12325 else 12326 { 12327 $this->userinfo = $this->replace_invalid_with_pct_encoding($userinfo, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=:'); 12328 } 12329 $this->valid[__FUNCTION__] = true; 12330 return true; 12331 } 12332 12333 /** 12334 * Set the host. Returns true on success, false on failure (if there are 12335 * any invalid characters). 12336 * 12337 * @access public 12338 * @param string $host 12339 * @return bool 12340 */ 12341 function set_host($host) 12342 { 12343 if ($host === null || $host === '') 12344 { 12345 $this->host = null; 12346 $this->valid[__FUNCTION__] = true; 12347 return true; 12348 } 12349 elseif ($host[0] === '[' && substr($host, -1) === ']') 12350 { 12351 if (Net_IPv6::checkIPv6(substr($host, 1, -1))) 12352 { 12353 $this->host = $host; 12354 $this->valid[__FUNCTION__] = true; 12355 return true; 12356 } 12357 else 12358 { 12359 $this->host = null; 12360 $this->valid[__FUNCTION__] = false; 12361 return false; 12362 } 12363 } 12364 else 12365 { 12366 $this->host = $this->replace_invalid_with_pct_encoding($host, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=', SIMPLEPIE_LOWERCASE); 12367 $this->valid[__FUNCTION__] = true; 12368 return true; 12369 } 12370 } 12371 12372 /** 12373 * Set the port. Returns true on success, false on failure (if there are 12374 * any invalid characters). 12375 * 12376 * @access public 12377 * @param string $port 12378 * @return bool 12379 */ 12380 function set_port($port) 12381 { 12382 if ($port === null || $port === '') 12383 { 12384 $this->port = null; 12385 $this->valid[__FUNCTION__] = true; 12386 return true; 12387 } 12388 elseif (strspn($port, '0123456789') === strlen($port)) 12389 { 12390 $this->port = (int) $port; 12391 $this->valid[__FUNCTION__] = true; 12392 return true; 12393 } 12394 else 12395 { 12396 $this->port = null; 12397 $this->valid[__FUNCTION__] = false; 12398 return false; 12399 } 12400 } 12401 12402 /** 12403 * Set the path. 12404 * 12405 * @access public 12406 * @param string $path 12407 * @return bool 12408 */ 12409 function set_path($path) 12410 { 12411 if ($path === null || $path === '') 12412 { 12413 $this->path = null; 12414 $this->valid[__FUNCTION__] = true; 12415 return true; 12416 } 12417 elseif (substr($path, 0, 2) === '//' && $this->userinfo === null && $this->host === null && $this->port === null) 12418 { 12419 $this->path = null; 12420 $this->valid[__FUNCTION__] = false; 12421 return false; 12422 } 12423 else 12424 { 12425 $this->path = $this->replace_invalid_with_pct_encoding($path, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=@/'); 12426 if ($this->scheme !== null) 12427 { 12428 $this->path = $this->remove_dot_segments($this->path); 12429 } 12430 $this->valid[__FUNCTION__] = true; 12431 return true; 12432 } 12433 } 12434 12435 /** 12436 * Set the query. 12437 * 12438 * @access public 12439 * @param string $query 12440 * @return bool 12441 */ 12442 function set_query($query) 12443 { 12444 if ($query === null || $query === '') 12445 { 12446 $this->query = null; 12447 } 12448 else 12449 { 12450 $this->query = $this->replace_invalid_with_pct_encoding($query, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$\'()*+,;:@/?&='); 12451 } 12452 $this->valid[__FUNCTION__] = true; 12453 return true; 12454 } 12455 12456 /** 12457 * Set the fragment. 12458 * 12459 * @access public 12460 * @param string $fragment 12461 * @return bool 12462 */ 12463 function set_fragment($fragment) 12464 { 12465 if ($fragment === null || $fragment === '') 12466 { 12467 $this->fragment = null; 12468 } 12469 else 12470 { 12471 $this->fragment = $this->replace_invalid_with_pct_encoding($fragment, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=:@/?'); 12472 } 12473 $this->valid[__FUNCTION__] = true; 12474 return true; 12475 } 12476 12477 /** 12478 * Get the complete IRI 12479 * 12480 * @access public 12481 * @return string 12482 */ 12483 function get_iri() 12484 { 12485 $iri = ''; 12486 if ($this->scheme !== null) 12487 { 12488 $iri .= $this->scheme . ':'; 12489 } 12490 if (($authority = $this->get_authority()) !== null) 12491 { 12492 $iri .= '//' . $authority; 12493 } 12494 if ($this->path !== null) 12495 { 12496 $iri .= $this->path; 12497 } 12498 if ($this->query !== null) 12499 { 12500 $iri .= '?' . $this->query; 12501 } 12502 if ($this->fragment !== null) 12503 { 12504 $iri .= '#' . $this->fragment; 12505 } 12506 12507 if ($iri !== '') 12508 { 12509 return $iri; 12510 } 12511 else 12512 { 12513 return null; 12514 } 12515 } 12516 12517 /** 12518 * Get the scheme 12519 * 12520 * @access public 12521 * @return string 12522 */ 12523 function get_scheme() 12524 { 12525 return $this->scheme; 12526 } 12527 12528 /** 12529 * Get the complete authority 12530 * 12531 * @access public 12532 * @return string 12533 */ 12534 function get_authority() 12535 { 12536 $authority = ''; 12537 if ($this->userinfo !== null) 12538 { 12539 $authority .= $this->userinfo . '@'; 12540 } 12541 if ($this->host !== null) 12542 { 12543 $authority .= $this->host; 12544 } 12545 if ($this->port !== null) 12546 { 12547 $authority .= ':' . $this->port; 12548 } 12549 12550 if ($authority !== '') 12551 { 12552 return $authority; 12553 } 12554 else 12555 { 12556 return null; 12557 } 12558 } 12559 12560 /** 12561 * Get the user information 12562 * 12563 * @access public 12564 * @return string 12565 */ 12566 function get_userinfo() 12567 { 12568 return $this->userinfo; 12569 } 12570 12571 /** 12572 * Get the host 12573 * 12574 * @access public 12575 * @return string 12576 */ 12577 function get_host() 12578 { 12579 return $this->host; 12580 } 12581 12582 /** 12583 * Get the port 12584 * 12585 * @access public 12586 * @return string 12587 */ 12588 function get_port() 12589 { 12590 return $this->port; 12591 } 12592 12593 /** 12594 * Get the path 12595 * 12596 * @access public 12597 * @return string 12598 */ 12599 function get_path() 12600 { 12601 return $this->path; 12602 } 12603 12604 /** 12605 * Get the query 12606 * 12607 * @access public 12608 * @return string 12609 */ 12610 function get_query() 12611 { 12612 return $this->query; 12613 } 12614 12615 /** 12616 * Get the fragment 12617 * 12618 * @access public 12619 * @return string 12620 */ 12621 function get_fragment() 12622 { 12623 return $this->fragment; 12624 } 12625 } 12626 12627 /** 12628 * Class to validate and to work with IPv6 addresses. 12629 * 12630 * @package SimplePie 12631 * @copyright 2003-2005 The PHP Group 12632 * @license http://www.opensource.org/licenses/bsd-license.php 12633 * @link http://pear.php.net/package/Net_IPv6 12634 * @author Alexander Merz <alexander.merz@web.de> 12635 * @author elfrink at introweb dot nl 12636 * @author Josh Peck <jmp at joshpeck dot org> 12637 * @author Geoffrey Sneddon <geoffers@gmail.com> 12638 */ 12639 class SimplePie_Net_IPv6 12640 { 12641 /** 12642 * Removes a possible existing netmask specification of an IP address. 12643 * 12644 * @param string $ip the (compressed) IP as Hex representation 12645 * @return string the IP the without netmask 12646 * @since 1.1.0 12647 * @access public 12648 * @static 12649 */ 12650 function removeNetmaskSpec($ip) 12651 { 12652 if (strpos($ip, '/') !== false) 12653 { 12654 list($addr, $nm) = explode('/', $ip); 12655 } 12656 else 12657 { 12658 $addr = $ip; 12659 } 12660 return $addr; 12661 } 12662 12663 /** 12664 * Uncompresses an IPv6 address 12665 * 12666 * RFC 2373 allows you to compress zeros in an address to '::'. This 12667 * function expects an valid IPv6 address and expands the '::' to 12668 * the required zeros. 12669 * 12670 * Example: FF01::101 -> FF01:0:0:0:0:0:0:101 12671 * ::1 -> 0:0:0:0:0:0:0:1 12672 * 12673 * @access public 12674 * @static 12675 * @param string $ip a valid IPv6-address (hex format) 12676 * @return string the uncompressed IPv6-address (hex format) 12677 */ 12678 function Uncompress($ip) 12679 { 12680 $uip = SimplePie_Net_IPv6::removeNetmaskSpec($ip); 12681 $c1 = -1; 12682 $c2 = -1; 12683 if (strpos($ip, '::') !== false) 12684 { 12685 list($ip1, $ip2) = explode('::', $ip); 12686 if ($ip1 === '') 12687 { 12688 $c1 = -1; 12689 } 12690 else 12691 { 12692 $pos = 0; 12693 if (($pos = substr_count($ip1, ':')) > 0) 12694 { 12695 $c1 = $pos; 12696 } 12697 else 12698 { 12699 $c1 = 0; 12700 } 12701 } 12702 if ($ip2 === '') 12703 { 12704 $c2 = -1; 12705 } 12706 else 12707 { 12708 $pos = 0; 12709 if (($pos = substr_count($ip2, ':')) > 0) 12710 { 12711 $c2 = $pos; 12712 } 12713 else 12714 { 12715 $c2 = 0; 12716 } 12717 } 12718 if (strstr($ip2, '.')) 12719 { 12720 $c2++; 12721 } 12722 // :: 12723 if ($c1 === -1 && $c2 === -1) 12724 { 12725 $uip = '0:0:0:0:0:0:0:0'; 12726 } 12727 // ::xxx 12728 else if ($c1 === -1) 12729 { 12730 $fill = str_repeat('0:', 7 - $c2); 12731 $uip = str_replace('::', $fill, $uip); 12732 } 12733 // xxx:: 12734 else if ($c2 === -1) 12735 { 12736 $fill = str_repeat(':0', 7 - $c1); 12737 $uip = str_replace('::', $fill, $uip); 12738 } 12739 // xxx::xxx 12740 else 12741 { 12742 $fill = str_repeat(':0:', 6 - $c2 - $c1); 12743 $uip = str_replace('::', $fill, $uip); 12744 $uip = str_replace('::', ':', $uip); 12745 } 12746 } 12747 return $uip; 12748 } 12749 12750 /** 12751 * Splits an IPv6 address into the IPv6 and a possible IPv4 part 12752 * 12753 * RFC 2373 allows you to note the last two parts of an IPv6 address as 12754 * an IPv4 compatible address 12755 * 12756 * Example: 0:0:0:0:0:0:13.1.68.3 12757 * 0:0:0:0:0:FFFF:129.144.52.38 12758 * 12759 * @access public 12760 * @static 12761 * @param string $ip a valid IPv6-address (hex format) 12762 * @return array [0] contains the IPv6 part, [1] the IPv4 part (hex format) 12763 */ 12764 function SplitV64($ip) 12765 { 12766 $ip = SimplePie_Net_IPv6::Uncompress($ip); 12767 if (strstr($ip, '.')) 12768 { 12769 $pos = strrpos($ip, ':'); 12770 $ip[$pos] = '_'; 12771 $ipPart = explode('_', $ip); 12772 return $ipPart; 12773 } 12774 else 12775 { 12776 return array($ip, ''); 12777 } 12778 } 12779 12780 /** 12781 * Checks an IPv6 address 12782 * 12783 * Checks if the given IP is IPv6-compatible 12784 * 12785 * @access public 12786 * @static 12787 * @param string $ip a valid IPv6-address 12788 * @return bool true if $ip is an IPv6 address 12789 */ 12790 function checkIPv6($ip) 12791 { 12792 $ipPart = SimplePie_Net_IPv6::SplitV64($ip); 12793 $count = 0; 12794 if (!empty($ipPart[0])) 12795 { 12796 $ipv6 = explode(':', $ipPart[0]); 12797 for ($i = 0; $i < count($ipv6); $i++) 12798 { 12799 $dec = hexdec($ipv6[$i]); 12800 $hex = strtoupper(preg_replace('/^[0]{1,3}(.*[0-9a-fA-F])$/', '\\1', $ipv6[$i])); 12801 if ($ipv6[$i] >= 0 && $dec <= 65535 && $hex === strtoupper(dechex($dec))) 12802 { 12803 $count++; 12804 } 12805 } 12806 if ($count === 8) 12807 { 12808 return true; 12809 } 12810 elseif ($count === 6 && !empty($ipPart[1])) 12811 { 12812 $ipv4 = explode('.', $ipPart[1]); 12813 $count = 0; 12814 foreach ($ipv4 as $ipv4_part) 12815 { 12816 if ($ipv4_part >= 0 && $ipv4_part <= 255 && preg_match('/^\d{1,3}$/', $ipv4_part)) 12817 { 12818 $count++; 12819 } 12820 } 12821 if ($count === 4) 12822 { 12823 return true; 12824 } 12825 } 12826 else 12827 { 12828 return false; 12829 } 12830 12831 } 12832 else 12833 { 12834 return false; 12835 } 12836 } 12837 } 12838 12839 /** 12840 * Date Parser 12841 * 12842 * @package SimplePie 12843 */ 12844 class SimplePie_Parse_Date 12845 { 12846 /** 12847 * Input data 12848 * 12849 * @access protected 12850 * @var string 12851 */ 12852 var $date; 12853 12854 /** 12855 * List of days, calendar day name => ordinal day number in the week 12856 * 12857 * @access protected 12858 * @var array 12859 */ 12860 var $day = array( 12861 // English 12862 'mon' => 1, 12863 'monday' => 1, 12864 'tue' => 2, 12865 'tuesday' => 2, 12866 'wed' => 3, 12867 'wednesday' => 3, 12868 'thu' => 4, 12869 'thursday' => 4, 12870 'fri' => 5, 12871 'friday' => 5, 12872 'sat' => 6, 12873 'saturday' => 6, 12874 'sun' => 7, 12875 'sunday' => 7, 12876 // Dutch 12877 'maandag' => 1, 12878 'dinsdag' => 2, 12879 'woensdag' => 3, 12880 'donderdag' => 4, 12881 'vrijdag' => 5, 12882 'zaterdag' => 6, 12883 'zondag' => 7, 12884 // French 12885 'lundi' => 1, 12886 'mardi' => 2, 12887 'mercredi' => 3, 12888 'jeudi' => 4, 12889 'vendredi' => 5, 12890 'samedi' => 6, 12891 'dimanche' => 7, 12892 // German 12893 'montag' => 1, 12894 'dienstag' => 2, 12895 'mittwoch' => 3, 12896 'donnerstag' => 4, 12897 'freitag' => 5, 12898 'samstag' => 6, 12899 'sonnabend' => 6, 12900 'sonntag' => 7, 12901 // Italian 12902 'lunedì' => 1, 12903 'martedì' => 2, 12904 'mercoledì' => 3, 12905 'giovedì' => 4, 12906 'venerdì' => 5, 12907 'sabato' => 6, 12908 'domenica' => 7, 12909 // Spanish 12910 'lunes' => 1, 12911 'martes' => 2, 12912 'miércoles' => 3, 12913 'jueves' => 4, 12914 'viernes' => 5, 12915 'sábado' => 6, 12916 'domingo' => 7, 12917 // Finnish 12918 'maanantai' => 1, 12919 'tiistai' => 2, 12920 'keskiviikko' => 3, 12921 'torstai' => 4, 12922 'perjantai' => 5, 12923 'lauantai' => 6, 12924 'sunnuntai' => 7, 12925 // Hungarian 12926 'hétfő' => 1, 12927 'kedd' => 2, 12928 'szerda' => 3, 12929 'csütörtok' => 4, 12930 'péntek' => 5, 12931 'szombat' => 6, 12932 'vasárnap' => 7, 12933 // Greek 12934 'Δευ' => 1, 12935 'Τρι' => 2, 12936 'Τετ' => 3, 12937 'Πεμ' => 4, 12938 'Παρ' => 5, 12939 'Σαβ' => 6, 12940 'Κυρ' => 7, 12941 ); 12942 12943 /** 12944 * List of months, calendar month name => calendar month number 12945 * 12946 * @access protected 12947 * @var array 12948 */ 12949 var $month = array( 12950 // English 12951 'jan' => 1, 12952 'january' => 1, 12953 'feb' => 2, 12954 'february' => 2, 12955 'mar' => 3, 12956 'march' => 3, 12957 'apr' => 4, 12958 'april' => 4, 12959 'may' => 5, 12960 // No long form of May 12961 'jun' => 6, 12962 'june' => 6, 12963 'jul' => 7, 12964 'july' => 7, 12965 'aug' => 8, 12966 'august' => 8, 12967 'sep' => 9, 12968 'september' => 8, 12969 'oct' => 10, 12970 'october' => 10, 12971 'nov' => 11, 12972 'november' => 11, 12973 'dec' => 12, 12974 'december' => 12, 12975 // Dutch 12976 'januari' => 1, 12977 'februari' => 2, 12978 'maart' => 3, 12979 'april' => 4, 12980 'mei' => 5, 12981 'juni' => 6, 12982 'juli' => 7, 12983 'augustus' => 8, 12984 'september' => 9, 12985 'oktober' => 10, 12986 'november' => 11, 12987 'december' => 12, 12988 // French 12989 'janvier' => 1, 12990 'février' => 2, 12991 'mars' => 3, 12992 'avril' => 4, 12993 'mai' => 5, 12994 'juin' => 6, 12995 'juillet' => 7, 12996 'août' => 8, 12997 'septembre' => 9, 12998 'octobre' => 10, 12999 'novembre' => 11, 13000 'décembre' => 12, 13001 // German 13002 'januar' => 1, 13003 'februar' => 2, 13004 'märz' => 3, 13005 'april' => 4, 13006 'mai' => 5, 13007 'juni' => 6, 13008 'juli' => 7, 13009 'august' => 8, 13010 'september' => 9, 13011 'oktober' => 10, 13012 'november' => 11, 13013 'dezember' => 12, 13014 // Italian 13015 'gennaio' => 1, 13016 'febbraio' => 2, 13017 'marzo' => 3, 13018 'aprile' => 4, 13019 'maggio' => 5, 13020 'giugno' => 6, 13021 'luglio' => 7, 13022 'agosto' => 8, 13023 'settembre' => 9, 13024 'ottobre' => 10, 13025 'novembre' => 11, 13026 'dicembre' => 12, 13027 // Spanish 13028 'enero' => 1, 13029 'febrero' => 2, 13030 'marzo' => 3, 13031 'abril' => 4, 13032 'mayo' => 5, 13033 'junio' => 6, 13034 'julio' => 7, 13035 'agosto' => 8, 13036 'septiembre' => 9, 13037 'setiembre' => 9, 13038 'octubre' => 10, 13039 'noviembre' => 11, 13040 'diciembre' => 12, 13041 // Finnish 13042 'tammikuu' => 1, 13043 'helmikuu' => 2, 13044 'maaliskuu' => 3, 13045 'huhtikuu' => 4, 13046 'toukokuu' => 5, 13047 'kesäkuu' => 6, 13048 'heinäkuu' => 7, 13049 'elokuu' => 8, 13050 'suuskuu' => 9, 13051 'lokakuu' => 10, 13052 'marras' => 11, 13053 'joulukuu' => 12, 13054 // Hungarian 13055 'január' => 1, 13056 'február' => 2, 13057 'március' => 3, 13058 'április' => 4, 13059 'május' => 5, 13060 'június' => 6, 13061 'július' => 7, 13062 'augusztus' => 8, 13063 'szeptember' => 9, 13064 'október' => 10, 13065 'november' => 11, 13066 'december' => 12, 13067 // Greek 13068 'Ιαν' => 1, 13069 'Φεβ' => 2, 13070 'Μάώ' => 3, 13071 'Μαώ' => 3, 13072 'Απρ' => 4, 13073 'Μάι' => 5, 13074 'Μαϊ' => 5, 13075 'Μαι' => 5, 13076 'Ιούν' => 6, 13077 'Ιον' => 6, 13078 'Ιούλ' => 7, 13079 'Ιολ' => 7, 13080 'Αύγ' => 8, 13081 'Αυγ' => 8, 13082 'Σεπ' => 9, 13083 'Οκτ' => 10, 13084 'Νοέ' => 11, 13085 'Δεκ' => 12, 13086 ); 13087 13088 /** 13089 * List of timezones, abbreviation => offset from UTC 13090 * 13091 * @access protected 13092 * @var array 13093 */ 13094 var $timezone = array( 13095 'ACDT' => 37800, 13096 'ACIT' => 28800, 13097 'ACST' => 34200, 13098 'ACT' => -18000, 13099 'ACWDT' => 35100, 13100 'ACWST' => 31500, 13101 'AEDT' => 39600, 13102 'AEST' => 36000, 13103 'AFT' => 16200, 13104 'AKDT' => -28800, 13105 'AKST' => -32400, 13106 'AMDT' => 18000, 13107 'AMT' => -14400, 13108 'ANAST' => 46800, 13109 'ANAT' => 43200, 13110 'ART' => -10800, 13111 'AZOST' => -3600, 13112 'AZST' => 18000, 13113 'AZT' => 14400, 13114 'BIOT' => 21600, 13115 'BIT' => -43200, 13116 'BOT' => -14400, 13117 'BRST' => -7200, 13118 'BRT' => -10800, 13119 'BST' => 3600, 13120 'BTT' => 21600, 13121 'CAST' => 18000, 13122 'CAT' => 7200, 13123 'CCT' => 23400, 13124 'CDT' => -18000, 13125 'CEDT' => 7200, 13126 'CET' => 3600, 13127 'CGST' => -7200, 13128 'CGT' => -10800, 13129 'CHADT' => 49500, 13130 'CHAST' => 45900, 13131 'CIST' => -28800, 13132 'CKT' => -36000, 13133 'CLDT' => -10800, 13134 'CLST' => -14400, 13135 'COT' => -18000, 13136 'CST' => -21600, 13137 'CVT' => -3600, 13138 'CXT' => 25200, 13139 'DAVT' => 25200, 13140 'DTAT' => 36000, 13141 'EADT' => -18000, 13142 'EAST' => -21600, 13143 'EAT' => 10800, 13144 'ECT' => -18000, 13145 'EDT' => -14400, 13146 'EEST' => 10800, 13147 'EET' => 7200, 13148 'EGT' => -3600, 13149 'EKST' => 21600, 13150 'EST' => -18000, 13151 'FJT' => 43200, 13152 'FKDT' => -10800, 13153 'FKST' => -14400, 13154 'FNT' => -7200, 13155 'GALT' => -21600, 13156 'GEDT' => 14400, 13157 'GEST' => 10800, 13158 'GFT' => -10800, 13159 'GILT' => 43200, 13160 'GIT' => -32400, 13161 'GST' => 14400, 13162 'GST' => -7200, 13163 'GYT' => -14400, 13164 'HAA' => -10800, 13165 'HAC' => -18000, 13166 'HADT' => -32400, 13167 'HAE' => -14400, 13168 'HAP' => -25200, 13169 'HAR' => -21600, 13170 'HAST' => -36000, 13171 'HAT' => -9000, 13172 'HAY' => -28800, 13173 'HKST' => 28800, 13174 'HMT' => 18000, 13175 'HNA' => -14400, 13176 'HNC' => -21600, 13177 'HNE' => -18000, 13178 'HNP' => -28800, 13179 'HNR' => -25200, 13180 'HNT' => -12600, 13181 'HNY' => -32400, 13182 'IRDT' => 16200, 13183 'IRKST' => 32400, 13184 'IRKT' => 28800, 13185 'IRST' => 12600, 13186 'JFDT' => -10800, 13187 'JFST' => -14400, 13188 'JST' => 32400, 13189 'KGST' => 21600, 13190 'KGT' => 18000, 13191 'KOST' => 39600, 13192 'KOVST' => 28800, 13193 'KOVT' => 25200, 13194 'KRAST' => 28800, 13195 'KRAT' => 25200, 13196 'KST' => 32400, 13197 'LHDT' => 39600, 13198 'LHST' => 37800, 13199 'LINT' => 50400, 13200 'LKT' => 21600, 13201 'MAGST' => 43200, 13202 'MAGT' => 39600, 13203 'MAWT' => 21600, 13204 'MDT' => -21600, 13205 'MESZ' => 7200, 13206 'MEZ' => 3600, 13207 'MHT' => 43200, 13208 'MIT' => -34200, 13209 'MNST' => 32400, 13210 'MSDT' => 14400, 13211 'MSST' => 10800, 13212 'MST' => -25200, 13213 'MUT' => 14400, 13214 'MVT' => 18000, 13215 'MYT' => 28800, 13216 'NCT' => 39600, 13217 'NDT' => -9000, 13218 'NFT' => 41400, 13219 'NMIT' => 36000, 13220 'NOVST' => 25200, 13221 'NOVT' => 21600, 13222 'NPT' => 20700, 13223 'NRT' => 43200, 13224 'NST' => -12600, 13225 'NUT' => -39600, 13226 'NZDT' => 46800, 13227 'NZST' => 43200, 13228 'OMSST' => 25200, 13229 'OMST' => 21600, 13230 'PDT' => -25200, 13231 'PET' => -18000, 13232 'PETST' => 46800, 13233 'PETT' => 43200, 13234 'PGT' => 36000, 13235 'PHOT' => 46800, 13236 'PHT' => 28800, 13237 'PKT' => 18000, 13238 'PMDT' => -7200, 13239 'PMST' => -10800, 13240 'PONT' => 39600, 13241 'PST' => -28800, 13242 'PWT' => 32400, 13243 'PYST' => -10800, 13244 'PYT' => -14400, 13245 'RET' => 14400, 13246 'ROTT' => -10800, 13247 'SAMST' => 18000, 13248 'SAMT' => 14400, 13249 'SAST' => 7200, 13250 'SBT' => 39600, 13251 'SCDT' => 46800, 13252 'SCST' => 43200, 13253 'SCT' => 14400, 13254 'SEST' => 3600, 13255 'SGT' => 28800, 13256 'SIT' => 28800, 13257 'SRT' => -10800, 13258 'SST' => -39600, 13259 'SYST' => 10800, 13260 'SYT' => 7200, 13261 'TFT' => 18000, 13262 'THAT' => -36000, 13263 'TJT' => 18000, 13264 'TKT' => -36000, 13265 'TMT' => 18000, 13266 'TOT' => 46800, 13267 'TPT' => 32400, 13268 'TRUT' => 36000, 13269 'TVT' => 43200, 13270 'TWT' => 28800, 13271 'UYST' => -7200, 13272 'UYT' => -10800, 13273 'UZT' => 18000, 13274 'VET' => -14400, 13275 'VLAST' => 39600, 13276 'VLAT' => 36000, 13277 'VOST' => 21600, 13278 'VUT' => 39600, 13279 'WAST' => 7200, 13280 'WAT' => 3600, 13281 'WDT' => 32400, 13282 'WEST' => 3600, 13283 'WFT' => 43200, 13284 'WIB' => 25200, 13285 'WIT' => 32400, 13286 'WITA' => 28800, 13287 'WKST' => 18000, 13288 'WST' => 28800, 13289 'YAKST' => 36000, 13290 'YAKT' => 32400, 13291 'YAPT' => 36000, 13292 'YEKST' => 21600, 13293 'YEKT' => 18000, 13294 ); 13295 13296 /** 13297 * Cached PCRE for SimplePie_Parse_Date::$day 13298 * 13299 * @access protected 13300 * @var string 13301 */ 13302 var $day_pcre; 13303 13304 /** 13305 * Cached PCRE for SimplePie_Parse_Date::$month 13306 * 13307 * @access protected 13308 * @var string 13309 */ 13310 var $month_pcre; 13311 13312 /** 13313 * Array of user-added callback methods 13314 * 13315 * @access private 13316 * @var array 13317 */ 13318 var $built_in = array(); 13319 13320 /** 13321 * Array of user-added callback methods 13322 * 13323 * @access private 13324 * @var array 13325 */ 13326 var $user = array(); 13327 13328 /** 13329 * Create new SimplePie_Parse_Date object, and set self::day_pcre, 13330 * self::month_pcre, and self::built_in 13331 * 13332 * @access private 13333 */ 13334 function SimplePie_Parse_Date() 13335 { 13336 $this->day_pcre = '(' . implode(array_keys($this->day), '|') . ')'; 13337 $this->month_pcre = '(' . implode(array_keys($this->month), '|') . ')'; 13338 13339 static $cache; 13340 if (!isset($cache[get_class($this)])) 13341 { 13342 $all_methods = get_class_methods($this); 13343 13344 foreach ($all_methods as $method) 13345 { 13346 if (strtolower(substr($method, 0, 5)) === 'date_') 13347 { 13348 $cache[get_class($this)][] = $method; 13349 } 13350 } 13351 } 13352 13353 foreach ($cache[get_class($this)] as $method) 13354 { 13355 $this->built_in[] = $method; 13356 } 13357 } 13358 13359 /** 13360 * Get the object 13361 * 13362 * @access public 13363 */ 13364 function get() 13365 { 13366 static $object; 13367 if (!$object) 13368 { 13369 $object = new SimplePie_Parse_Date; 13370 } 13371 return $object; 13372 } 13373 13374 /** 13375 * Parse a date 13376 * 13377 * @final 13378 * @access public 13379 * @param string $date Date to parse 13380 * @return int Timestamp corresponding to date string, or false on failure 13381 */ 13382 function parse($date) 13383 { 13384 foreach ($this->user as $method) 13385 { 13386 if (($returned = call_user_func($method, $date)) !== false) 13387 { 13388 return $returned; 13389 } 13390 } 13391 13392 foreach ($this->built_in as $method) 13393 { 13394 if (($returned = call_user_func(array(&$this, $method), $date)) !== false) 13395 { 13396 return $returned; 13397 } 13398 } 13399 13400 return false; 13401 } 13402 13403 /** 13404 * Add a callback method to parse a date 13405 * 13406 * @final 13407 * @access public 13408 * @param callback $callback 13409 */ 13410 function add_callback($callback) 13411 { 13412 if (is_callable($callback)) 13413 { 13414 $this->user[] = $callback; 13415 } 13416 else 13417 { 13418 trigger_error('User-supplied function must be a valid callback', E_USER_WARNING); 13419 } 13420 } 13421 13422 /** 13423 * Parse a superset of W3C-DTF (allows hyphens and colons to be omitted, as 13424 * well as allowing any of upper or lower case "T", horizontal tabs, or 13425 * spaces to be used as the time seperator (including more than one)) 13426 * 13427 * @access protected 13428 * @return int Timestamp 13429 */ 13430 function date_w3cdtf($date) 13431 { 13432 static $pcre; 13433 if (!$pcre) 13434 { 13435 $year = '([0-9]{4})'; 13436 $month = $day = $hour = $minute = $second = '([0-9]{2})'; 13437 $decimal = '([0-9]*)'; 13438 $zone = '(?:(Z)|([+\-])([0-9]{1,2}):?([0-9]{1,2}))'; 13439 $pcre = '/^' . $year . '(?:-?' . $month . '(?:-?' . $day . '(?:[Tt\x09\x20]+' . $hour . '(?::?' . $minute . '(?::?' . $second . '(?:.' . $decimal . ')?)?)?' . $zone . ')?)?)?$/'; 13440 } 13441 if (preg_match($pcre, $date, $match)) 13442 { 13443 /* 13444 Capturing subpatterns: 13445 1: Year 13446 2: Month 13447 3: Day 13448 4: Hour 13449 5: Minute 13450 6: Second 13451 7: Decimal fraction of a second 13452 8: Zulu 13453 9: Timezone ± 13454 10: Timezone hours 13455 11: Timezone minutes 13456 */ 13457 13458 // Fill in empty matches 13459 for ($i = count($match); $i <= 3; $i++) 13460 { 13461 $match[$i] = '1'; 13462 } 13463 13464 for ($i = count($match); $i <= 7; $i++) 13465 { 13466 $match[$i] = '0'; 13467 } 13468 13469 // Numeric timezone 13470 if (isset($match[9]) && $match[9] !== '') 13471 { 13472 $timezone = $match[10] * 3600; 13473 $timezone += $match[11] * 60; 13474 if ($match[9] === '-') 13475 { 13476 $timezone = 0 - $timezone; 13477 } 13478 } 13479 else 13480 { 13481 $timezone = 0; 13482 } 13483 13484 // Convert the number of seconds to an integer, taking decimals into account 13485 $second = round($match[6] + $match[7] / pow(10, strlen($match[7]))); 13486 13487 return gmmktime($match[4], $match[5], $second, $match[2], $match[3], $match[1]) - $timezone; 13488 } 13489 else 13490 { 13491 return false; 13492 } 13493 } 13494 13495 /** 13496 * Remove RFC822 comments 13497 * 13498 * @access protected 13499 * @param string $data Data to strip comments from 13500 * @return string Comment stripped string 13501 */ 13502 function remove_rfc2822_comments($string) 13503 { 13504 $string = (string) $string; 13505 $position = 0; 13506 $length = strlen($string); 13507 $depth = 0; 13508 13509 $output = ''; 13510 13511 while ($position < $length && ($pos = strpos($string, '(', $position)) !== false) 13512 { 13513 $output .= substr($string, $position, $pos - $position); 13514 $position = $pos + 1; 13515 if ($string[$pos - 1] !== '\\') 13516 { 13517 $depth++; 13518 while ($depth && $position < $length) 13519 { 13520 $position += strcspn($string, '()', $position); 13521 if ($string[$position - 1] === '\\') 13522 { 13523 $position++; 13524 continue; 13525 } 13526 elseif (isset($string[$position])) 13527 { 13528 switch ($string[$position]) 13529 { 13530 case '(': 13531 $depth++; 13532 break; 13533 13534 case ')': 13535 $depth--; 13536 break; 13537 } 13538 $position++; 13539 } 13540 else 13541 { 13542 break; 13543 } 13544 } 13545 } 13546 else 13547 { 13548 $output .= '('; 13549 } 13550 } 13551 $output .= substr($string, $position); 13552 13553 return $output; 13554 } 13555 13556 /** 13557 * Parse RFC2822's date format 13558 * 13559 * @access protected 13560 * @return int Timestamp 13561 */ 13562 function date_rfc2822($date) 13563 { 13564 static $pcre; 13565 if (!$pcre) 13566 { 13567 $wsp = '[\x09\x20]'; 13568 $fws = '(?:' . $wsp . '+|' . $wsp . '*(?:\x0D\x0A' . $wsp . '+)+)'; 13569 $optional_fws = $fws . '?'; 13570 $day_name = $this->day_pcre; 13571 $month = $this->month_pcre; 13572 $day = '([0-9]{1,2})'; 13573 $hour = $minute = $second = '([0-9]{2})'; 13574 $year = '([0-9]{2,4})'; 13575 $num_zone = '([+\-])([0-9]{2})([0-9]{2})'; 13576 $character_zone = '([A-Z]{1,5})'; 13577 $zone = '(?:' . $num_zone . '|' . $character_zone . ')'; 13578 $pcre = '/(?:' . $optional_fws . $day_name . $optional_fws . ',)?' . $optional_fws . $day . $fws . $month . $fws . $year . $fws . $hour . $optional_fws . ':' . $optional_fws . $minute . '(?:' . $optional_fws . ':' . $optional_fws . $second . ')?' . $fws . $zone . '/i'; 13579 } 13580 if (preg_match($pcre, $this->remove_rfc2822_comments($date), $match)) 13581 { 13582 /* 13583 Capturing subpatterns: 13584 1: Day name 13585 2: Day 13586 3: Month 13587 4: Year 13588 5: Hour 13589 6: Minute 13590 7: Second 13591 8: Timezone ± 13592 9: Timezone hours 13593 10: Timezone minutes 13594 11: Alphabetic timezone 13595 */ 13596 13597 // Find the month number 13598 $month = $this->month[strtolower($match[3])]; 13599 13600 // Numeric timezone 13601 if ($match[8] !== '') 13602 { 13603 $timezone = $match[9] * 3600; 13604 $timezone += $match[10] * 60; 13605 if ($match[8] === '-') 13606 { 13607 $timezone = 0 - $timezone; 13608 } 13609 } 13610 // Character timezone 13611 elseif (isset($this->timezone[strtoupper($match[11])])) 13612 { 13613 $timezone = $this->timezone[strtoupper($match[11])]; 13614 } 13615 // Assume everything else to be -0000 13616 else 13617 { 13618 $timezone = 0; 13619 } 13620 13621 // Deal with 2/3 digit years 13622 if ($match[4] < 50) 13623 { 13624 $match[4] += 2000; 13625 } 13626 elseif ($match[4] < 1000) 13627 { 13628 $match[4] += 1900; 13629 } 13630 13631 // Second is optional, if it is empty set it to zero 13632 if ($match[7] !== '') 13633 { 13634 $second = $match[7]; 13635 } 13636 else 13637 { 13638 $second = 0; 13639 } 13640 13641 return gmmktime($match[5], $match[6], $second, $month, $match[2], $match[4]) - $timezone; 13642 } 13643 else 13644 { 13645 return false; 13646 } 13647 } 13648 13649 /** 13650 * Parse RFC850's date format 13651 * 13652 * @access protected 13653 * @return int Timestamp 13654 */ 13655 function date_rfc850($date) 13656 { 13657 static $pcre; 13658 if (!$pcre) 13659 { 13660 $space = '[\x09\x20]+'; 13661 $day_name = $this->day_pcre; 13662 $month = $this->month_pcre; 13663 $day = '([0-9]{1,2})'; 13664 $year = $hour = $minute = $second = '([0-9]{2})'; 13665 $zone = '([A-Z]{1,5})'; 13666 $pcre = '/^' . $day_name . ',' . $space . $day . '-' . $month . '-' . $year . $space . $hour . ':' . $minute . ':' . $second . $space . $zone . '$/i'; 13667 } 13668 if (preg_match($pcre, $date, $match)) 13669 { 13670 /* 13671 Capturing subpatterns: 13672 1: Day name 13673 2: Day 13674 3: Month 13675 4: Year 13676 5: Hour 13677 6: Minute 13678 7: Second 13679 8: Timezone 13680 */ 13681 13682 // Month 13683 $month = $this->month[strtolower($match[3])]; 13684 13685 // Character timezone 13686 if (isset($this->timezone[strtoupper($match[8])])) 13687 { 13688 $timezone = $this->timezone[strtoupper($match[8])]; 13689 } 13690 // Assume everything else to be -0000 13691 else 13692 { 13693 $timezone = 0; 13694 } 13695 13696 // Deal with 2 digit year 13697 if ($match[4] < 50) 13698 { 13699 $match[4] += 2000; 13700 } 13701 else 13702 { 13703 $match[4] += 1900; 13704 } 13705 13706 return gmmktime($match[5], $match[6], $match[7], $month, $match[2], $match[4]) - $timezone; 13707 } 13708 else 13709 { 13710 return false; 13711 } 13712 } 13713 13714 /** 13715 * Parse C99's asctime()'s date format 13716 * 13717 * @access protected 13718 * @return int Timestamp 13719 */ 13720 function date_asctime($date) 13721 { 13722 static $pcre; 13723 if (!$pcre) 13724 { 13725 $space = '[\x09\x20]+'; 13726 $wday_name = $this->day_pcre; 13727 $mon_name = $this->month_pcre; 13728 $day = '([0-9]{1,2})'; 13729 $hour = $sec = $min = '([0-9]{2})'; 13730 $year = '([0-9]{4})'; 13731 $terminator = '\x0A?\x00?'; 13732 $pcre = '/^' . $wday_name . $space . $mon_name . $space . $day . $space . $hour . ':' . $min . ':' . $sec . $space . $year . $terminator . '$/i'; 13733 } 13734 if (preg_match($pcre, $date, $match)) 13735 { 13736 /* 13737 Capturing subpatterns: 13738 1: Day name 13739 2: Month 13740 3: Day 13741 4: Hour 13742 5: Minute 13743 6: Second 13744 7: Year 13745 */ 13746 13747 $month = $this->month[strtolower($match[2])]; 13748 return gmmktime($match[4], $match[5], $match[6], $month, $match[3], $match[7]); 13749 } 13750 else 13751 { 13752 return false; 13753 } 13754 } 13755 13756 /** 13757 * Parse dates using strtotime() 13758 * 13759 * @access protected 13760 * @return int Timestamp 13761 */ 13762 function date_strtotime($date) 13763 { 13764 $strtotime = strtotime($date); 13765 if ($strtotime === -1 || $strtotime === false) 13766 { 13767 return false; 13768 } 13769 else 13770 { 13771 return $strtotime; 13772 } 13773 } 13774 } 13775 13776 /** 13777 * Content-type sniffing 13778 * 13779 * @package SimplePie 13780 */ 13781 class SimplePie_Content_Type_Sniffer 13782 { 13783 /** 13784 * File object 13785 * 13786 * @var SimplePie_File 13787 * @access private 13788 */ 13789 var $file; 13790 13791 /** 13792 * Create an instance of the class with the input file 13793 * 13794 * @access public 13795 * @param SimplePie_Content_Type_Sniffer $file Input file 13796 */ 13797 function SimplePie_Content_Type_Sniffer($file) 13798 { 13799 $this->file = $file; 13800 } 13801 13802 /** 13803 * Get the Content-Type of the specified file 13804 * 13805 * @access public 13806 * @return string Actual Content-Type 13807 */ 13808 function get_type() 13809 { 13810 if (isset($this->file->headers['content-type'])) 13811 { 13812 if (!isset($this->file->headers['content-encoding']) 13813 && ($this->file->headers['content-type'] === 'text/plain' 13814 || $this->file->headers['content-type'] === 'text/plain; charset=ISO-8859-1' 13815 || $this->file->headers['content-type'] === 'text/plain; charset=iso-8859-1')) 13816 { 13817 return $this->text_or_binary(); 13818 } 13819 13820 if (($pos = strpos($this->file->headers['content-type'], ';')) !== false) 13821 { 13822 $official = substr($this->file->headers['content-type'], 0, $pos); 13823 } 13824 else 13825 { 13826 $official = $this->file->headers['content-type']; 13827 } 13828 $official = strtolower($official); 13829 13830 if ($official === 'unknown/unknown' 13831 || $official === 'application/unknown') 13832 { 13833 return $this->unknown(); 13834 } 13835 elseif (substr($official, -4) === '+xml' 13836 || $official === 'text/xml' 13837 || $official === 'application/xml') 13838 { 13839 return $official; 13840 } 13841 elseif (substr($official, 0, 6) === 'image/') 13842 { 13843 if ($return = $this->image()) 13844 { 13845 return $return; 13846 } 13847 else 13848 { 13849 return $official; 13850 } 13851 } 13852 elseif ($official === 'text/html') 13853 { 13854 return $this->feed_or_html(); 13855 } 13856 else 13857 { 13858 return $official; 13859 } 13860 } 13861 else 13862 { 13863 return $this->unknown(); 13864 } 13865 } 13866 13867 /** 13868 * Sniff text or binary 13869 * 13870 * @access private 13871 * @return string Actual Content-Type 13872 */ 13873 function text_or_binary() 13874 { 13875 if (substr($this->file->body, 0, 2) === "\xFE\xFF" 13876 || substr($this->file->body, 0, 2) === "\xFF\xFE" 13877 || substr($this->file->body, 0, 4) === "\x00\x00\xFE\xFF" 13878 || substr($this->file->body, 0, 3) === "\xEF\xBB\xBF") 13879 { 13880 return 'text/plain'; 13881 } 13882 elseif (preg_match('/[\x00-\x08\x0E-\x1A\x1C-\x1F]/', $this->file->body)) 13883 { 13884 return 'application/octect-stream'; 13885 } 13886 else 13887 { 13888 return 'text/plain'; 13889 } 13890 } 13891 13892 /** 13893 * Sniff unknown 13894 * 13895 * @access private 13896 * @return string Actual Content-Type 13897 */ 13898 function unknown() 13899 { 13900 $ws = strspn($this->file->body, "\x09\x0A\x0B\x0C\x0D\x20"); 13901 if (strtolower(substr($this->file->body, $ws, 14)) === '<!doctype html' 13902 || strtolower(substr($this->file->body, $ws, 5)) === '<html' 13903 || strtolower(substr($this->file->body, $ws, 7)) === '<script') 13904 { 13905 return 'text/html'; 13906 } 13907 elseif (substr($this->file->body, 0, 5) === '%PDF-') 13908 { 13909 return 'application/pdf'; 13910 } 13911 elseif (substr($this->file->body, 0, 11) === '%!PS-Adobe-') 13912 { 13913 return 'application/postscript'; 13914 } 13915 elseif (substr($this->file->body, 0, 6) === 'GIF87a' 13916 || substr($this->file->body, 0, 6) === 'GIF89a') 13917 { 13918 return 'image/gif'; 13919 } 13920 elseif (substr($this->file->body, 0, 8) === "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A") 13921 { 13922 return 'image/png'; 13923 } 13924 elseif (substr($this->file->body, 0, 3) === "\xFF\xD8\xFF") 13925 { 13926 return 'image/jpeg'; 13927 } 13928 elseif (substr($this->file->body, 0, 2) === "\x42\x4D") 13929 { 13930 return 'image/bmp'; 13931 } 13932 else 13933 { 13934 return $this->text_or_binary(); 13935 } 13936 } 13937 13938 /** 13939 * Sniff images 13940 * 13941 * @access private 13942 * @return string Actual Content-Type 13943 */ 13944 function image() 13945 { 13946 if (substr($this->file->body, 0, 6) === 'GIF87a' 13947 || substr($this->file->body, 0, 6) === 'GIF89a') 13948 { 13949 return 'image/gif'; 13950 } 13951 elseif (substr($this->file->body, 0, 8) === "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A") 13952 { 13953 return 'image/png'; 13954 } 13955 elseif (substr($this->file->body, 0, 3) === "\xFF\xD8\xFF") 13956 { 13957 return 'image/jpeg'; 13958 } 13959 elseif (substr($this->file->body, 0, 2) === "\x42\x4D") 13960 { 13961 return 'image/bmp'; 13962 } 13963 else 13964 { 13965 return false; 13966 } 13967 } 13968 13969 /** 13970 * Sniff HTML 13971 * 13972 * @access private 13973 * @return string Actual Content-Type 13974 */ 13975 function feed_or_html() 13976 { 13977 $len = strlen($this->file->body); 13978 $pos = strspn($this->file->body, "\x09\x0A\x0D\x20"); 13979 13980 while ($pos < $len) 13981 { 13982 switch ($this->file->body[$pos]) 13983 { 13984 case "\x09": 13985 case "\x0A": 13986 case "\x0D": 13987 case "\x20": 13988 $pos += strspn($this->file->body, "\x09\x0A\x0D\x20", $pos); 13989 continue 2; 13990 13991 case '<': 13992 $pos++; 13993 break; 13994 13995 default: 13996 return 'text/html'; 13997 } 13998 13999 if (substr($this->file->body, $pos, 3) === '!--') 14000 { 14001 $pos += 3; 14002 if ($pos < $len && ($pos = strpos($this->file->body, '-->', $pos)) !== false) 14003 { 14004 $pos += 3; 14005 } 14006 else 14007 { 14008 return 'text/html'; 14009 } 14010 } 14011 elseif (substr($this->file->body, $pos, 1) === '!') 14012 { 14013 if ($pos < $len && ($pos = strpos($this->file->body, '>', $pos)) !== false) 14014 { 14015 $pos++; 14016 } 14017 else 14018 { 14019 return 'text/html'; 14020 } 14021 } 14022 elseif (substr($this->file->body, $pos, 1) === '?') 14023 { 14024 if ($pos < $len && ($pos = strpos($this->file->body, '?>', $pos)) !== false) 14025 { 14026 $pos += 2; 14027 } 14028 else 14029 { 14030 return 'text/html'; 14031 } 14032 } 14033 elseif (substr($this->file->body, $pos, 3) === 'rss' 14034 || substr($this->file->body, $pos, 7) === 'rdf:RDF') 14035 { 14036 return 'application/rss+xml'; 14037 } 14038 elseif (substr($this->file->body, $pos, 4) === 'feed') 14039 { 14040 return 'application/atom+xml'; 14041 } 14042 else 14043 { 14044 return 'text/html'; 14045 } 14046 } 14047 14048 return 'text/html'; 14049 } 14050 } 14051 14052 /** 14053 * Parses the XML Declaration 14054 * 14055 * @package SimplePie 14056 */ 14057 class SimplePie_XML_Declaration_Parser 14058 { 14059 /** 14060 * XML Version 14061 * 14062 * @access public 14063 * @var string 14064 */ 14065 var $version = '1.0'; 14066 14067 /** 14068 * Encoding 14069 * 14070 * @access public 14071 * @var string 14072 */ 14073 var $encoding = 'UTF-8'; 14074 14075 /** 14076 * Standalone 14077 * 14078 * @access public 14079 * @var bool 14080 */ 14081 var $standalone = false; 14082 14083 /** 14084 * Current state of the state machine 14085 * 14086 * @access private 14087 * @var string 14088 */ 14089 var $state = 'before_version_name'; 14090 14091 /** 14092 * Input data 14093 * 14094 * @access private 14095 * @var string 14096 */ 14097 var $data = ''; 14098 14099 /** 14100 * Input data length (to avoid calling strlen() everytime this is needed) 14101 * 14102 * @access private 14103 * @var int 14104 */ 14105 var $data_length = 0; 14106 14107 /** 14108 * Current position of the pointer 14109 * 14110 * @var int 14111 * @access private 14112 */ 14113 var $position = 0; 14114 14115 /** 14116 * Create an instance of the class with the input data 14117 * 14118 * @access public 14119 * @param string $data Input data 14120 */ 14121 function SimplePie_XML_Declaration_Parser($data) 14122 { 14123 $this->data = $data; 14124 $this->data_length = strlen($this->data); 14125 } 14126 14127 /** 14128 * Parse the input data 14129 * 14130 * @access public 14131 * @return bool true on success, false on failure 14132 */ 14133 function parse() 14134 { 14135 while ($this->state && $this->state !== 'emit' && $this->has_data()) 14136 { 14137 $state = $this->state; 14138 $this->$state(); 14139 } 14140 $this->data = ''; 14141 if ($this->state === 'emit') 14142 { 14143 return true; 14144 } 14145 else 14146 { 14147 $this->version = ''; 14148 $this->encoding = ''; 14149 $this->standalone = ''; 14150 return false; 14151 } 14152 } 14153 14154 /** 14155 * Check whether there is data beyond the pointer 14156 * 14157 * @access private 14158 * @return bool true if there is further data, false if not 14159 */ 14160 function has_data() 14161 { 14162 return (bool) ($this->position < $this->data_length); 14163 } 14164 14165 /** 14166 * Advance past any whitespace 14167 * 14168 * @return int Number of whitespace characters passed 14169 */ 14170 function skip_whitespace() 14171 { 14172 $whitespace = strspn($this->data, "\x09\x0A\x0D\x20", $this->position); 14173 $this->position += $whitespace; 14174 return $whitespace; 14175 } 14176 14177 /** 14178 * Read value 14179 */ 14180 function get_value() 14181 { 14182 $quote = substr($this->data, $this->position, 1); 14183 if ($quote === '"' || $quote === "'") 14184 { 14185 $this->position++; 14186 $len = strcspn($this->data, $quote, $this->position); 14187 if ($this->has_data()) 14188 { 14189 $value = substr($this->data, $this->position, $len); 14190 $this->position += $len + 1; 14191 return $value; 14192 } 14193 } 14194 return false; 14195 } 14196 14197 function before_version_name() 14198 { 14199 if ($this->skip_whitespace()) 14200 { 14201 $this->state = 'version_name'; 14202 } 14203 else 14204 { 14205 $this->state = false; 14206 } 14207 } 14208 14209 function version_name() 14210 { 14211 if (substr($this->data, $this->position, 7) === 'version') 14212 { 14213 $this->position += 7; 14214 $this->skip_whitespace(); 14215 $this->state = 'version_equals'; 14216 } 14217 else 14218 { 14219 $this->state = false; 14220 } 14221 } 14222 14223 function version_equals() 14224 { 14225 if (substr($this->data, $this->position, 1) === '=') 14226 { 14227 $this->position++; 14228 $this->skip_whitespace(); 14229 $this->state = 'version_value'; 14230 } 14231 else 14232 { 14233 $this->state = false; 14234 } 14235 } 14236 14237 function version_value() 14238 { 14239 if ($this->version = $this->get_value()) 14240 { 14241 $this->skip_whitespace(); 14242 if ($this->has_data()) 14243 { 14244 $this->state = 'encoding_name'; 14245 } 14246 else 14247 { 14248 $this->state = 'emit'; 14249 } 14250 } 14251 else 14252 { 14253 $this->state = false; 14254 } 14255 } 14256 14257 function encoding_name() 14258 { 14259 if (substr($this->data, $this->position, 8) === 'encoding') 14260 { 14261 $this->position += 8; 14262 $this->skip_whitespace(); 14263 $this->state = 'encoding_equals'; 14264 } 14265 else 14266 { 14267 $this->state = 'standalone_name'; 14268 } 14269 } 14270 14271 function encoding_equals() 14272 { 14273 if (substr($this->data, $this->position, 1) === '=') 14274 { 14275 $this->position++; 14276 $this->skip_whitespace(); 14277 $this->state = 'encoding_value'; 14278 } 14279 else 14280 { 14281 $this->state = false; 14282 } 14283 } 14284 14285 function encoding_value() 14286 { 14287 if ($this->encoding = $this->get_value()) 14288 { 14289 $this->skip_whitespace(); 14290 if ($this->has_data()) 14291 { 14292 $this->state = 'standalone_name'; 14293 } 14294 else 14295 { 14296 $this->state = 'emit'; 14297 } 14298 } 14299 else 14300 { 14301 $this->state = false; 14302 } 14303 } 14304 14305 function standalone_name() 14306 { 14307 if (substr($this->data, $this->position, 10) === 'standalone') 14308 { 14309 $this->position += 10; 14310 $this->skip_whitespace(); 14311 $this->state = 'standalone_equals'; 14312 } 14313 else 14314 { 14315 $this->state = false; 14316 } 14317 } 14318 14319 function standalone_equals() 14320 { 14321 if (substr($this->data, $this->position, 1) === '=') 14322 { 14323 $this->position++; 14324 $this->skip_whitespace(); 14325 $this->state = 'standalone_value'; 14326 } 14327 else 14328 { 14329 $this->state = false; 14330 } 14331 } 14332 14333 function standalone_value() 14334 { 14335 if ($standalone = $this->get_value()) 14336 { 14337 switch ($standalone) 14338 { 14339 case 'yes': 14340 $this->standalone = true; 14341 break; 14342 14343 case 'no': 14344 $this->standalone = false; 14345 break; 14346 14347 default: 14348 $this->state = false; 14349 return; 14350 } 14351 14352 $this->skip_whitespace(); 14353 if ($this->has_data()) 14354 { 14355 $this->state = false; 14356 } 14357 else 14358 { 14359 $this->state = 'emit'; 14360 } 14361 } 14362 else 14363 { 14364 $this->state = false; 14365 } 14366 } 14367 } 14368 14369 class SimplePie_Locator 14370 { 14371 var $useragent; 14372 var $timeout; 14373 var $file; 14374 var $local = array(); 14375 var $elsewhere = array(); 14376 var $file_class = 'SimplePie_File'; 14377 var $cached_entities = array(); 14378 var $http_base; 14379 var $base; 14380 var $base_location = 0; 14381 var $checked_feeds = 0; 14382 var $max_checked_feeds = 10; 14383 var $content_type_sniffer_class = 'SimplePie_Content_Type_Sniffer'; 14384 14385 function SimplePie_Locator(&$file, $timeout = 10, $useragent = null, $file_class = 'SimplePie_File', $max_checked_feeds = 10, $content_type_sniffer_class = 'SimplePie_Content_Type_Sniffer') 14386 { 14387 $this->file =& $file; 14388 $this->file_class = $file_class; 14389 $this->useragent = $useragent; 14390 $this->timeout = $timeout; 14391 $this->max_checked_feeds = $max_checked_feeds; 14392 $this->content_type_sniffer_class = $content_type_sniffer_class; 14393 } 14394 14395 function find($type = SIMPLEPIE_LOCATOR_ALL, &$working) 14396 { 14397 if ($this->is_feed($this->file)) 14398 { 14399 return $this->file; 14400 } 14401 14402 if ($this->file->method & SIMPLEPIE_FILE_SOURCE_REMOTE) 14403 { 14404 $sniffer = new $this->content_type_sniffer_class($this->file); 14405 if ($sniffer->get_type() !== 'text/html') 14406 { 14407 return null; 14408 } 14409 } 14410 14411 if ($type & ~SIMPLEPIE_LOCATOR_NONE) 14412 { 14413 $this->get_base(); 14414 } 14415 14416 if ($type & SIMPLEPIE_LOCATOR_AUTODISCOVERY && $working = $this->autodiscovery()) 14417 { 14418 return $working[0]; 14419 } 14420 14421 if ($type & (SIMPLEPIE_LOCATOR_LOCAL_EXTENSION | SIMPLEPIE_LOCATOR_LOCAL_BODY | SIMPLEPIE_LOCATOR_REMOTE_EXTENSION | SIMPLEPIE_LOCATOR_REMOTE_BODY) && $this->get_links()) 14422 { 14423 if ($type & SIMPLEPIE_LOCATOR_LOCAL_EXTENSION && $working = $this->extension($this->local)) 14424 { 14425 return $working; 14426 } 14427 14428 if ($type & SIMPLEPIE_LOCATOR_LOCAL_BODY && $working = $this->body($this->local)) 14429 { 14430 return $working; 14431 } 14432 14433 if ($type & SIMPLEPIE_LOCATOR_REMOTE_EXTENSION && $working = $this->extension($this->elsewhere)) 14434 { 14435 return $working; 14436 } 14437 14438 if ($type & SIMPLEPIE_LOCATOR_REMOTE_BODY && $working = $this->body($this->elsewhere)) 14439 { 14440 return $working; 14441 } 14442 } 14443 return null; 14444 } 14445 14446 function is_feed(&$file) 14447 { 14448 if ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE) 14449 { 14450 $sniffer = new $this->content_type_sniffer_class($file); 14451 $sniffed = $sniffer->get_type(); 14452 if (in_array($sniffed, array('application/rss+xml', 'application/rdf+xml', 'text/rdf', 'application/atom+xml', 'text/xml', 'application/xml'))) 14453 { 14454 return true; 14455 } 14456 else 14457 { 14458 return false; 14459 } 14460 } 14461 elseif ($file->method & SIMPLEPIE_FILE_SOURCE_LOCAL) 14462 { 14463 return true; 14464 } 14465 else 14466 { 14467 return false; 14468 } 14469 } 14470 14471 function get_base() 14472 { 14473 $this->http_base = $this->file->url; 14474 $this->base = $this->http_base; 14475 $elements = SimplePie_Misc::get_element('base', $this->file->body); 14476 foreach ($elements as $element) 14477 { 14478 if ($element['attribs']['href']['data'] !== '') 14479 { 14480 $this->base = SimplePie_Misc::absolutize_url(trim($element['attribs']['href']['data']), $this->http_base); 14481 $this->base_location = $element['offset']; 14482 break; 14483 } 14484 } 14485 } 14486 14487 function autodiscovery() 14488 { 14489 $links = array_merge(SimplePie_Misc::get_element('link', $this->file->body), SimplePie_Misc::get_element('a', $this->file->body), SimplePie_Misc::get_element('area', $this->file->body)); 14490 $done = array(); 14491 $feeds = array(); 14492 foreach ($links as $link) 14493 { 14494 if ($this->checked_feeds === $this->max_checked_feeds) 14495 { 14496 break; 14497 } 14498 if (isset($link['attribs']['href']['data']) && isset($link['attribs']['rel']['data'])) 14499 { 14500 $rel = array_unique(SimplePie_Misc::space_seperated_tokens(strtolower($link['attribs']['rel']['data']))); 14501 14502 if ($this->base_location < $link['offset']) 14503 { 14504 $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->base); 14505 } 14506 else 14507 { 14508 $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->http_base); 14509 } 14510 14511 if (!in_array($href, $done) && in_array('feed', $rel) || (in_array('alternate', $rel) && !empty($link['attribs']['type']['data']) && in_array(strtolower(SimplePie_Misc::parse_mime($link['attribs']['type']['data'])), array('application/rss+xml', 'application/atom+xml'))) && !isset($feeds[$href])) 14512 { 14513 $this->checked_feeds++; 14514 $feed = new $this->file_class($href, $this->timeout, 5, null, $this->useragent); 14515 if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed)) 14516 { 14517 $feeds[$href] = $feed; 14518 } 14519 } 14520 $done[] = $href; 14521 } 14522 } 14523 14524 if (!empty($feeds)) 14525 { 14526 return array_values($feeds); 14527 } 14528 else { 14529 return null; 14530 } 14531 } 14532 14533 function get_links() 14534 { 14535 $links = SimplePie_Misc::get_element('a', $this->file->body); 14536 foreach ($links as $link) 14537 { 14538 if (isset($link['attribs']['href']['data'])) 14539 { 14540 $href = trim($link['attribs']['href']['data']); 14541 $parsed = SimplePie_Misc::parse_url($href); 14542 if ($parsed['scheme'] === '' || preg_match('/^(http(s)|feed)?$/i', $parsed['scheme'])) 14543 { 14544 if ($this->base_location < $link['offset']) 14545 { 14546 $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->base); 14547 } 14548 else 14549 { 14550 $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->http_base); 14551 } 14552 14553 $current = SimplePie_Misc::parse_url($this->file->url); 14554 14555 if ($parsed['authority'] === '' || $parsed['authority'] === $current['authority']) 14556 { 14557 $this->local[] = $href; 14558 } 14559 else 14560 { 14561 $this->elsewhere[] = $href; 14562 } 14563 } 14564 } 14565 } 14566 $this->local = array_unique($this->local); 14567 $this->elsewhere = array_unique($this->elsewhere); 14568 if (!empty($this->local) || !empty($this->elsewhere)) 14569 { 14570 return true; 14571 } 14572 return null; 14573 } 14574 14575 function extension(&$array) 14576 { 14577 foreach ($array as $key => $value) 14578 { 14579 if ($this->checked_feeds === $this->max_checked_feeds) 14580 { 14581 break; 14582 } 14583 if (in_array(strtolower(strrchr($value, '.')), array('.rss', '.rdf', '.atom', '.xml'))) 14584 { 14585 $this->checked_feeds++; 14586 $feed = new $this->file_class($value, $this->timeout, 5, null, $this->useragent); 14587 if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed)) 14588 { 14589 return $feed; 14590 } 14591 else 14592 { 14593 unset($array[$key]); 14594 } 14595 } 14596 } 14597 return null; 14598 } 14599 14600 function body(&$array) 14601 { 14602 foreach ($array as $key => $value) 14603 { 14604 if ($this->checked_feeds === $this->max_checked_feeds) 14605 { 14606 break; 14607 } 14608 if (preg_match('/(rss|rdf|atom|xml)/i', $value)) 14609 { 14610 $this->checked_feeds++; 14611 $feed = new $this->file_class($value, $this->timeout, 5, null, $this->useragent); 14612 if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed)) 14613 { 14614 return $feed; 14615 } 14616 else 14617 { 14618 unset($array[$key]); 14619 } 14620 } 14621 } 14622 return null; 14623 } 14624 } 14625 14626 class SimplePie_Parser 14627 { 14628 var $error_code; 14629 var $error_string; 14630 var $current_line; 14631 var $current_column; 14632 var $current_byte; 14633 var $separator = ' '; 14634 var $namespace = array(''); 14635 var $element = array(''); 14636 var $xml_base = array(''); 14637 var $xml_base_explicit = array(false); 14638 var $xml_lang = array(''); 14639 var $data = array(); 14640 var $datas = array(array()); 14641 var $current_xhtml_construct = -1; 14642 var $encoding; 14643 14644 function parse(&$data, $encoding) 14645 { 14646 // Use UTF-8 if we get passed US-ASCII, as every US-ASCII character is a UTF-8 character 14647 if (strtoupper($encoding) === 'US-ASCII') 14648 { 14649 $this->encoding = 'UTF-8'; 14650 } 14651 else 14652 { 14653 $this->encoding = $encoding; 14654 } 14655 14656 // Strip BOM: 14657 // UTF-32 Big Endian BOM 14658 if (substr($data, 0, 4) === "\x00\x00\xFE\xFF") 14659 { 14660 $data = substr($data, 4); 14661 } 14662 // UTF-32 Little Endian BOM 14663 elseif (substr($data, 0, 4) === "\xFF\xFE\x00\x00") 14664 { 14665 $data = substr($data, 4); 14666 } 14667 // UTF-16 Big Endian BOM 14668 elseif (substr($data, 0, 2) === "\xFE\xFF") 14669 { 14670 $data = substr($data, 2); 14671 } 14672 // UTF-16 Little Endian BOM 14673 elseif (substr($data, 0, 2) === "\xFF\xFE") 14674 { 14675 $data = substr($data, 2); 14676 } 14677 // UTF-8 BOM 14678 elseif (substr($data, 0, 3) === "\xEF\xBB\xBF") 14679 { 14680 $data = substr($data, 3); 14681 } 14682 14683 if (substr($data, 0, 5) === '<?xml' && strspn(substr($data, 5, 1), "\x09\x0A\x0D\x20") && ($pos = strpos($data, '?>')) !== false) 14684 { 14685 $declaration = new SimplePie_XML_Declaration_Parser(substr($data, 5, $pos - 5)); 14686 if ($declaration->parse()) 14687 { 14688 $data = substr($data, $pos + 2); 14689 $data = '<?xml version="' . $declaration->version . '" encoding="' . $encoding . '" standalone="' . (($declaration->standalone) ? 'yes' : 'no') . '"?>' . $data; 14690 } 14691 else 14692 { 14693 $this->error_string = 'SimplePie bug! Please report this!'; 14694 return false; 14695 } 14696 } 14697 14698 $return = true; 14699 14700 static $xml_is_sane = null; 14701 if ($xml_is_sane === null) 14702 { 14703 $parser_check = xml_parser_create(); 14704 xml_parse_into_struct($parser_check, '<foo>&</foo>', $values); 14705 xml_parser_free($parser_check); 14706 $xml_is_sane = isset($values[0]['value']); 14707 } 14708 14709 // Create the parser 14710 if ($xml_is_sane) 14711 { 14712 $xml = xml_parser_create_ns($this->encoding, $this->separator); 14713 xml_parser_set_option($xml, XML_OPTION_SKIP_WHITE, 1); 14714 xml_parser_set_option($xml, XML_OPTION_CASE_FOLDING, 0); 14715 xml_set_object($xml, $this); 14716 xml_set_character_data_handler($xml, 'cdata'); 14717 xml_set_element_handler($xml, 'tag_open', 'tag_close'); 14718 14719 // Parse! 14720 if (!xml_parse($xml, $data, true)) 14721 { 14722 $this->error_code = xml_get_error_code($xml); 14723 $this->error_string = xml_error_string($this->error_code); 14724 $return = false; 14725 } 14726 $this->current_line = xml_get_current_line_number($xml); 14727 $this->current_column = xml_get_current_column_number($xml); 14728 $this->current_byte = xml_get_current_byte_index($xml); 14729 xml_parser_free($xml); 14730 return $return; 14731 } 14732 else 14733 { 14734 libxml_clear_errors(); 14735 $xml = new XMLReader(); 14736 $xml->xml($data); 14737 while (@$xml->read()) 14738 { 14739 switch ($xml->nodeType) 14740 { 14741 14742 case constant('XMLReader::END_ELEMENT'): 14743 if ($xml->namespaceURI !== '') 14744 { 14745 $tagName = $xml->namespaceURI . $this->separator . $xml->localName; 14746 } 14747 else 14748 { 14749 $tagName = $xml->localName; 14750 } 14751 $this->tag_close(null, $tagName); 14752 break; 14753 case constant('XMLReader::ELEMENT'): 14754 $empty = $xml->isEmptyElement; 14755 if ($xml->namespaceURI !== '') 14756 { 14757 $tagName = $xml->namespaceURI . $this->separator . $xml->localName; 14758 } 14759 else 14760 { 14761 $tagName = $xml->localName; 14762 } 14763 $attributes = array(); 14764 while ($xml->moveToNextAttribute()) 14765 { 14766 if ($xml->namespaceURI !== '') 14767 { 14768 $attrName = $xml->namespaceURI . $this->separator . $xml->localName; 14769 } 14770 else 14771 { 14772 $attrName = $xml->localName; 14773 } 14774 $attributes[$attrName] = $xml->value; 14775 } 14776 $this->tag_open(null, $tagName, $attributes); 14777 if ($empty) 14778 { 14779 $this->tag_close(null, $tagName); 14780 } 14781 break; 14782 case constant('XMLReader::TEXT'): 14783 14784 case constant('XMLReader::CDATA'): 14785 $this->cdata(null, $xml->value); 14786 break; 14787 } 14788 } 14789 if ($error = libxml_get_last_error()) 14790 { 14791 $this->error_code = $error->code; 14792 $this->error_string = $error->message; 14793 $this->current_line = $error->line; 14794 $this->current_column = $error->column; 14795 return false; 14796 } 14797 else 14798 { 14799 return true; 14800 } 14801 } 14802 } 14803 14804 function get_error_code() 14805 { 14806 return $this->error_code; 14807 } 14808 14809 function get_error_string() 14810 { 14811 return $this->error_string; 14812 } 14813 14814 function get_current_line() 14815 { 14816 return $this->current_line; 14817 } 14818 14819 function get_current_column() 14820 { 14821 return $this->current_column; 14822 } 14823 14824 function get_current_byte() 14825 { 14826 return $this->current_byte; 14827 } 14828 14829 function get_data() 14830 { 14831 return $this->data; 14832 } 14833 14834 function tag_open($parser, $tag, $attributes) 14835 { 14836 list($this->namespace[], $this->element[]) = $this->split_ns($tag); 14837 14838 $attribs = array(); 14839 foreach ($attributes as $name => $value) 14840 { 14841 list($attrib_namespace, $attribute) = $this->split_ns($name); 14842 $attribs[$attrib_namespace][$attribute] = $value; 14843 } 14844 14845 if (isset($attribs[SIMPLEPIE_NAMESPACE_XML]['base'])) 14846 { 14847 $this->xml_base[] = SimplePie_Misc::absolutize_url($attribs[SIMPLEPIE_NAMESPACE_XML]['base'], end($this->xml_base)); 14848 $this->xml_base_explicit[] = true; 14849 } 14850 else 14851 { 14852 $this->xml_base[] = end($this->xml_base); 14853 $this->xml_base_explicit[] = end($this->xml_base_explicit); 14854 } 14855 14856 if (isset($attribs[SIMPLEPIE_NAMESPACE_XML]['lang'])) 14857 { 14858 $this->xml_lang[] = $attribs[SIMPLEPIE_NAMESPACE_XML]['lang']; 14859 } 14860 else 14861 { 14862 $this->xml_lang[] = end($this->xml_lang); 14863 } 14864 14865 if ($this->current_xhtml_construct >= 0) 14866 { 14867 $this->current_xhtml_construct++; 14868 if (end($this->namespace) === SIMPLEPIE_NAMESPACE_XHTML) 14869 { 14870 $this->data['data'] .= '<' . end($this->element); 14871 if (isset($attribs[''])) 14872 { 14873 foreach ($attribs[''] as $name => $value) 14874 { 14875 $this->data['data'] .= ' ' . $name . '="' . htmlspecialchars($value, ENT_COMPAT, $this->encoding) . '"'; 14876 } 14877 } 14878 $this->data['data'] .= '>'; 14879 } 14880 } 14881 else 14882 { 14883 $this->datas[] =& $this->data; 14884 $this->data =& $this->data['child'][end($this->namespace)][end($this->element)][]; 14885 $this->data = array('data' => '', 'attribs' => $attribs, 'xml_base' => end($this->xml_base), 'xml_base_explicit' => end($this->xml_base_explicit), 'xml_lang' => end($this->xml_lang)); 14886 if ((end($this->namespace) === SIMPLEPIE_NAMESPACE_ATOM_03 && in_array(end($this->element), array('title', 'tagline', 'copyright', 'info', 'summary', 'content')) && isset($attribs['']['mode']) && $attribs['']['mode'] === 'xml') 14887 || (end($this->namespace) === SIMPLEPIE_NAMESPACE_ATOM_10 && in_array(end($this->element), array('rights', 'subtitle', 'summary', 'info', 'title', 'content')) && isset($attribs['']['type']) && $attribs['']['type'] === 'xhtml')) 14888 { 14889 $this->current_xhtml_construct = 0; 14890 } 14891 } 14892 } 14893 14894 function cdata($parser, $cdata) 14895 { 14896 if ($this->current_xhtml_construct >= 0) 14897 { 14898 $this->data['data'] .= htmlspecialchars($cdata, ENT_QUOTES, $this->encoding); 14899 } 14900 else 14901 { 14902 $this->data['data'] .= $cdata; 14903 } 14904 } 14905 14906 function tag_close($parser, $tag) 14907 { 14908 if ($this->current_xhtml_construct >= 0) 14909 { 14910 $this->current_xhtml_construct--; 14911 if (end($this->namespace) === SIMPLEPIE_NAMESPACE_XHTML && !in_array(end($this->element), array('area', 'base', 'basefont', 'br', 'col', 'frame', 'hr', 'img', 'input', 'isindex', 'link', 'meta', 'param'))) 14912 { 14913 $this->data['data'] .= '</' . end($this->element) . '>'; 14914 } 14915 } 14916 if ($this->current_xhtml_construct === -1) 14917 { 14918 $this->data =& $this->datas[count($this->datas) - 1]; 14919 array_pop($this->datas); 14920 } 14921 14922 array_pop($this->element); 14923 array_pop($this->namespace); 14924 array_pop($this->xml_base); 14925 array_pop($this->xml_base_explicit); 14926 array_pop($this->xml_lang); 14927 } 14928 14929 function split_ns($string) 14930 { 14931 static $cache = array(); 14932 if (!isset($cache[$string])) 14933 { 14934 if ($pos = strpos($string, $this->separator)) 14935 { 14936 static $separator_length; 14937 if (!$separator_length) 14938 { 14939 $separator_length = strlen($this->separator); 14940 } 14941 $namespace = substr($string, 0, $pos); 14942 $local_name = substr($string, $pos + $separator_length); 14943 if (strtolower($namespace) === SIMPLEPIE_NAMESPACE_ITUNES) 14944 { 14945 $namespace = SIMPLEPIE_NAMESPACE_ITUNES; 14946 } 14947 14948 // Normalize the Media RSS namespaces 14949 if ($namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG || 14950 $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG2 || 14951 $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG3 || 14952 $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG4 || 14953 $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG5 ) 14954 { 14955 $namespace = SIMPLEPIE_NAMESPACE_MEDIARSS; 14956 } 14957 $cache[$string] = array($namespace, $local_name); 14958 } 14959 else 14960 { 14961 $cache[$string] = array('', $string); 14962 } 14963 } 14964 return $cache[$string]; 14965 } 14966 } 14967 14968 /** 14969 * @todo Move to using an actual HTML parser (this will allow tags to be properly stripped, and to switch between HTML and XHTML), this will also make it easier to shorten a string while preserving HTML tags 14970 */ 14971 class SimplePie_Sanitize 14972 { 14973 // Private vars 14974 var $base; 14975 14976 // Options 14977 var $remove_div = true; 14978 var $image_handler = ''; 14979 var $strip_htmltags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'iframe', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style'); 14980 var $encode_instead_of_strip = false; 14981 var $strip_attributes = array('bgsound', 'class', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc'); 14982 var $strip_comments = false; 14983 var $output_encoding = 'UTF-8'; 14984 var $enable_cache = true; 14985 var $cache_location = './cache'; 14986 var $cache_name_function = 'md5'; 14987 var $cache_class = 'SimplePie_Cache'; 14988 var $file_class = 'SimplePie_File'; 14989 var $timeout = 10; 14990 var $useragent = ''; 14991 var $force_fsockopen = false; 14992 14993 var $replace_url_attributes = array( 14994 'a' => 'href', 14995 'area' => 'href', 14996 'blockquote' => 'cite', 14997 'del' => 'cite', 14998 'form' => 'action', 14999 'img' => array('longdesc', 'src'), 15000 'input' => 'src', 15001 'ins' => 'cite', 15002 'q' => 'cite' 15003 ); 15004 15005 function remove_div($enable = true) 15006 { 15007 $this->remove_div = (bool) $enable; 15008 } 15009 15010 function set_image_handler($page = false) 15011 { 15012 if ($page) 15013 { 15014 $this->image_handler = (string) $page; 15015 } 15016 else 15017 { 15018 $this->image_handler = false; 15019 } 15020 } 15021 15022 function pass_cache_data($enable_cache = true, $cache_location = './cache', $cache_name_function = 'md5', $cache_class = 'SimplePie_Cache') 15023 { 15024 if (isset($enable_cache)) 15025 { 15026 $this->enable_cache = (bool) $enable_cache; 15027 } 15028 15029 if ($cache_location) 15030 { 15031 $this->cache_location = (string) $cache_location; 15032 } 15033 15034 if ($cache_name_function) 15035 { 15036 $this->cache_name_function = (string) $cache_name_function; 15037 } 15038 15039 if ($cache_class) 15040 { 15041 $this->cache_class = (string) $cache_class; 15042 } 15043 } 15044 15045 function pass_file_data($file_class = 'SimplePie_File', $timeout = 10, $useragent = '', $force_fsockopen = false) 15046 { 15047 if ($file_class) 15048 { 15049 $this->file_class = (string) $file_class; 15050 } 15051 15052 if ($timeout) 15053 { 15054 $this->timeout = (string) $timeout; 15055 } 15056 15057 if ($useragent) 15058 { 15059 $this->useragent = (string) $useragent; 15060 } 15061 15062 if ($force_fsockopen) 15063 { 15064 $this->force_fsockopen = (string) $force_fsockopen; 15065 } 15066 } 15067 15068 function strip_htmltags($tags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'iframe', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style')) 15069 { 15070 if ($tags) 15071 { 15072 if (is_array($tags)) 15073 { 15074 $this->strip_htmltags = $tags; 15075 } 15076 else 15077 { 15078 $this->strip_htmltags = explode(',', $tags); 15079 } 15080 } 15081 else 15082 { 15083 $this->strip_htmltags = false; 15084 } 15085 } 15086 15087 function encode_instead_of_strip($encode = false) 15088 { 15089 $this->encode_instead_of_strip = (bool) $encode; 15090 } 15091 15092 function strip_attributes($attribs = array('bgsound', 'class', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc')) 15093 { 15094 if ($attribs) 15095 { 15096 if (is_array($attribs)) 15097 { 15098 $this->strip_attributes = $attribs; 15099 } 15100 else 15101 { 15102 $this->strip_attributes = explode(',', $attribs); 15103 } 15104 } 15105 else 15106 { 15107 $this->strip_attributes = false; 15108 } 15109 } 15110 15111 function strip_comments($strip = false) 15112 { 15113 $this->strip_comments = (bool) $strip; 15114 } 15115 15116 function set_output_encoding($encoding = 'UTF-8') 15117 { 15118 $this->output_encoding = (string) $encoding; 15119 } 15120 15121 /** 15122 * Set element/attribute key/value pairs of HTML attributes 15123 * containing URLs that need to be resolved relative to the feed 15124 * 15125 * @access public 15126 * @since 1.0 15127 * @param array $element_attribute Element/attribute key/value pairs 15128 */ 15129 function set_url_replacements($element_attribute = array('a' => 'href', 'area' => 'href', 'blockquote' => 'cite', 'del' => 'cite', 'form' => 'action', 'img' => array('longdesc', 'src'), 'input' => 'src', 'ins' => 'cite', 'q' => 'cite')) 15130 { 15131 $this->replace_url_attributes = (array) $element_attribute; 15132 } 15133 15134 function sanitize($data, $type, $base = '') 15135 { 15136 $data = trim($data); 15137 if ($data !== '' || $type & SIMPLEPIE_CONSTRUCT_IRI) 15138 { 15139 if ($type & SIMPLEPIE_CONSTRUCT_MAYBE_HTML) 15140 { 15141 if (preg_match('/(&(#(x[0-9a-fA-F]+|[0-9]+)|[a-zA-Z0-9]+)|<\/[A-Za-z][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E]*' . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . '>)/', $data)) 15142 { 15143 $type |= SIMPLEPIE_CONSTRUCT_HTML; 15144 } 15145 else 15146 { 15147 $type |= SIMPLEPIE_CONSTRUCT_TEXT; 15148 } 15149 } 15150 15151 if ($type & SIMPLEPIE_CONSTRUCT_BASE64) 15152 { 15153 $data = base64_decode($data); 15154 } 15155 15156 if ($type & SIMPLEPIE_CONSTRUCT_XHTML) 15157 { 15158 if ($this->remove_div) 15159 { 15160 $data = preg_replace('/^<div' . SIMPLEPIE_PCRE_XML_ATTRIBUTE . '>/', '', $data); 15161 $data = preg_replace('/<\/div>$/', '', $data); 15162 } 15163 else 15164 { 15165 $data = preg_replace('/^<div' . SIMPLEPIE_PCRE_XML_ATTRIBUTE . '>/', '<div>', $data); 15166 } 15167 } 15168 15169 if ($type & (SIMPLEPIE_CONSTRUCT_HTML | SIMPLEPIE_CONSTRUCT_XHTML)) 15170 { 15171 // Strip comments 15172 if ($this->strip_comments) 15173 { 15174 $data = SimplePie_Misc::strip_comments($data); 15175 } 15176 15177 // Strip out HTML tags and attributes that might cause various security problems. 15178 // Based on recommendations by Mark Pilgrim at: 15179 // http://diveintomark.org/archives/2003/06/12/how_to_consume_rss_safely 15180 if ($this->strip_htmltags) 15181 { 15182 foreach ($this->strip_htmltags as $tag) 15183 { 15184 $pcre = "/<($tag)" . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . "(>(.*)<\/$tag" . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . '>|(\/)?>)/siU'; 15185 while (preg_match($pcre, $data)) 15186 { 15187 $data = preg_replace_callback($pcre, array(&$this, 'do_strip_htmltags'), $data); 15188 } 15189 } 15190 } 15191 15192 if ($this->strip_attributes) 15193 { 15194 foreach ($this->strip_attributes as $attrib) 15195 { 15196 $data = preg_replace('/(<[A-Za-z][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E]*)' . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . trim($attrib) . '(?:\s*=\s*(?:"(?:[^"]*)"|\'(?:[^\']*)\'|(?:[^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?' . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . '>/', '\1\2\3>', $data); 15197 } 15198 } 15199 15200 // Replace relative URLs 15201 $this->base = $base; 15202 foreach ($this->replace_url_attributes as $element => $attributes) 15203 { 15204 $data = $this->replace_urls($data, $element, $attributes); 15205 } 15206 15207 // If image handling (caching, etc.) is enabled, cache and rewrite all the image tags. 15208 if (isset($this->image_handler) && ((string) $this->image_handler) !== '' && $this->enable_cache) 15209 { 15210 $images = SimplePie_Misc::get_element('img', $data); 15211 foreach ($images as $img) 15212 { 15213 if (isset($img['attribs']['src']['data'])) 15214 { 15215 $image_url = call_user_func($this->cache_name_function, $img['attribs']['src']['data']); 15216 $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, $image_url, 'spi'); 15217 15218 if ($cache->load()) 15219 { 15220 $img['attribs']['src']['data'] = $this->image_handler . $image_url; 15221 $data = str_replace($img['full'], SimplePie_Misc::element_implode($img), $data); 15222 } 15223 else 15224 { 15225 $file = new $this->file_class($img['attribs']['src']['data'], $this->timeout, 5, array('X-FORWARDED-FOR' => $_SERVER['REMOTE_ADDR']), $this->useragent, $this->force_fsockopen); 15226 $headers = $file->headers; 15227 15228 if ($file->success && ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300))) 15229 { 15230 if ($cache->save(array('headers' => $file->headers, 'body' => $file->body))) 15231 { 15232 $img['attribs']['src']['data'] = $this->image_handler . $image_url; 15233 $data = str_replace($img['full'], SimplePie_Misc::element_implode($img), $data); 15234 } 15235 else 15236 { 15237 trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING); 15238 } 15239 } 15240 } 15241 } 15242 } 15243 } 15244 15245 // Having (possibly) taken stuff out, there may now be whitespace at the beginning/end of the data 15246 $data = trim($data); 15247 } 15248 15249 if ($type & SIMPLEPIE_CONSTRUCT_IRI) 15250 { 15251 $data = SimplePie_Misc::absolutize_url($data, $base); 15252 } 15253 15254 if ($type & (SIMPLEPIE_CONSTRUCT_TEXT | SIMPLEPIE_CONSTRUCT_IRI)) 15255 { 15256 $data = htmlspecialchars($data, ENT_COMPAT, 'UTF-8'); 15257 } 15258 15259 if ($this->output_encoding !== 'UTF-8') 15260 { 15261 $data = SimplePie_Misc::change_encoding($data, 'UTF-8', $this->output_encoding); 15262 } 15263 } 15264 return $data; 15265 } 15266 15267 function replace_urls($data, $tag, $attributes) 15268 { 15269 if (!is_array($this->strip_htmltags) || !in_array($tag, $this->strip_htmltags)) 15270 { 15271 $elements = SimplePie_Misc::get_element($tag, $data); 15272 foreach ($elements as $element) 15273 { 15274 if (is_array($attributes)) 15275 { 15276 foreach ($attributes as $attribute) 15277 { 15278 if (isset($element['attribs'][$attribute]['data'])) 15279 { 15280 $element['attribs'][$attribute]['data'] = SimplePie_Misc::absolutize_url($element['attribs'][$attribute]['data'], $this->base); 15281 $new_element = SimplePie_Misc::element_implode($element); 15282 $data = str_replace($element['full'], $new_element, $data); 15283 $element['full'] = $new_element; 15284 } 15285 } 15286 } 15287 elseif (isset($element['attribs'][$attributes]['data'])) 15288 { 15289 $element['attribs'][$attributes]['data'] = SimplePie_Misc::absolutize_url($element['attribs'][$attributes]['data'], $this->base); 15290 $data = str_replace($element['full'], SimplePie_Misc::element_implode($element), $data); 15291 } 15292 } 15293 } 15294 return $data; 15295 } 15296 15297 function do_strip_htmltags($match) 15298 { 15299 if ($this->encode_instead_of_strip) 15300 { 15301 if (isset($match[4]) && !in_array(strtolower($match[1]), array('script', 'style'))) 15302 { 15303 $match[1] = htmlspecialchars($match[1], ENT_COMPAT, 'UTF-8'); 15304 $match[2] = htmlspecialchars($match[2], ENT_COMPAT, 'UTF-8'); 15305 return "<$match[1]$match[2]>$match[3]</$match[1]>"; 15306 } 15307 else 15308 { 15309 return htmlspecialchars($match[0], ENT_COMPAT, 'UTF-8'); 15310 } 15311 } 15312 elseif (isset($match[4]) && !in_array(strtolower($match[1]), array('script', 'style'))) 15313 { 15314 return $match[4]; 15315 } 15316 else 15317 { 15318 return ''; 15319 } 15320 } 15321 } 15322 15323 ?>
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
Generated: Sun Jan 29 16:31:14 2012 | Cross-referenced by PHPXref 0.7.1 |