gluon-web-remote

Web remote Administration for big size of gluon routers
git clone git://archive.git.mtrnord.blog/MTRNord/gluon-web-remote.git
Log | Files | Refs | README

Smarty.class.php (49369B)


      1 <?php
      2 /**
      3  * Project:     Smarty: the PHP compiling template engine
      4  * File:        Smarty.class.php
      5  *
      6  * This library is free software; you can redistribute it and/or
      7  * modify it under the terms of the GNU Lesser General Public
      8  * License as published by the Free Software Foundation; either
      9  * version 2.1 of the License, or (at your option) any later version.
     10  *
     11  * This library is distributed in the hope that it will be useful,
     12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
     13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     14  * Lesser General Public License for more details.
     15  *
     16  * You should have received a copy of the GNU Lesser General Public
     17  * License along with this library; if not, write to the Free Software
     18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
     19  * For questions, help, comments, discussion, etc., please join the
     20  * Smarty mailing list. Send a blank e-mail to
     21  * smarty-discussion-subscribe@googlegroups.com
     22  *
     23  * @link      http://www.smarty.net/
     24  * @copyright 2015 New Digital Group, Inc.
     25  * @copyright 2015 Uwe Tews
     26  * @author    Monte Ohrt <monte at ohrt dot com>
     27  * @author    Uwe Tews
     28  * @author    Rodney Rehm
     29  * @package   Smarty
     30  * @version   3.1.27
     31  */
     32 
     33 /**
     34  * define shorthand directory separator constant
     35  */
     36 if (!defined('DS')) {
     37     define('DS', DIRECTORY_SEPARATOR);
     38 }
     39 
     40 /**
     41  * set SMARTY_DIR to absolute path to Smarty library files.
     42  * Sets SMARTY_DIR only if user application has not already defined it.
     43  */
     44 if (!defined('SMARTY_DIR')) {
     45     define('SMARTY_DIR', dirname(__FILE__) . DS);
     46 }
     47 
     48 /**
     49  * set SMARTY_SYSPLUGINS_DIR to absolute path to Smarty internal plugins.
     50  * Sets SMARTY_SYSPLUGINS_DIR only if user application has not already defined it.
     51  */
     52 if (!defined('SMARTY_SYSPLUGINS_DIR')) {
     53     define('SMARTY_SYSPLUGINS_DIR', SMARTY_DIR . 'sysplugins' . DS);
     54 }
     55 if (!defined('SMARTY_PLUGINS_DIR')) {
     56     define('SMARTY_PLUGINS_DIR', SMARTY_DIR . 'plugins' . DS);
     57 }
     58 if (!defined('SMARTY_MBSTRING')) {
     59     define('SMARTY_MBSTRING', function_exists('mb_get_info'));
     60 }
     61 if (!defined('SMARTY_RESOURCE_CHAR_SET')) {
     62     // UTF-8 can only be done properly when mbstring is available!
     63     /**
     64      * @deprecated in favor of Smarty::$_CHARSET
     65      */
     66     define('SMARTY_RESOURCE_CHAR_SET', SMARTY_MBSTRING ? 'UTF-8' : 'ISO-8859-1');
     67 }
     68 if (!defined('SMARTY_RESOURCE_DATE_FORMAT')) {
     69     /**
     70      * @deprecated in favor of Smarty::$_DATE_FORMAT
     71      */
     72     define('SMARTY_RESOURCE_DATE_FORMAT', '%b %e, %Y');
     73 }
     74 
     75 /**
     76  * Try loading the Smarty_Internal_Data class
     77  * If we fail we must load Smarty's autoloader.
     78  * Otherwise we may have a global autoloader like Composer
     79  */
     80 if (!class_exists('Smarty_Autoloader', false)) {
     81     if (!class_exists('Smarty_Internal_Data', true)) {
     82         require_once 'Autoloader.php';
     83         Smarty_Autoloader::registerBC();
     84     }
     85 }
     86 
     87 /**
     88  * Load always needed external class files
     89  */
     90 
     91 if (!class_exists('Smarty_Internal_Data', false)) {
     92     require_once SMARTY_SYSPLUGINS_DIR . 'smarty_internal_data.php';
     93 }
     94 require_once SMARTY_SYSPLUGINS_DIR . 'smarty_internal_templatebase.php';
     95 require_once SMARTY_SYSPLUGINS_DIR . 'smarty_internal_template.php';
     96 require_once SMARTY_SYSPLUGINS_DIR . 'smarty_resource.php';
     97 require_once SMARTY_SYSPLUGINS_DIR . 'smarty_variable.php';
     98 require_once SMARTY_SYSPLUGINS_DIR . 'smarty_template_source.php';
     99 
    100 /**
    101  * This is the main Smarty class
    102  *
    103  * @package Smarty
    104  */
    105 class Smarty extends Smarty_Internal_TemplateBase
    106 {
    107     /**#@+
    108      * constant definitions
    109      */
    110 
    111     /**
    112      * smarty version
    113      */
    114     const SMARTY_VERSION = '3.1.27';
    115 
    116     /**
    117      * define variable scopes
    118      */
    119     const SCOPE_LOCAL = 0;
    120 
    121     const SCOPE_PARENT = 1;
    122 
    123     const SCOPE_ROOT = 2;
    124 
    125     const SCOPE_GLOBAL = 3;
    126 
    127     /**
    128      * define caching modes
    129      */
    130     const CACHING_OFF = 0;
    131 
    132     const CACHING_LIFETIME_CURRENT = 1;
    133 
    134     const CACHING_LIFETIME_SAVED = 2;
    135 
    136     /**
    137      * define constant for clearing cache files be saved expiration datees
    138      */
    139     const CLEAR_EXPIRED = - 1;
    140 
    141     /**
    142      * define compile check modes
    143      */
    144     const COMPILECHECK_OFF = 0;
    145 
    146     const COMPILECHECK_ON = 1;
    147 
    148     const COMPILECHECK_CACHEMISS = 2;
    149 
    150     /**
    151      * define debug modes
    152      */
    153     const DEBUG_OFF = 0;
    154 
    155     const DEBUG_ON = 1;
    156 
    157     const DEBUG_INDIVIDUAL = 2;
    158 
    159     /**
    160      * modes for handling of "<?php ... ?>" tags in templates.
    161      */
    162     const PHP_PASSTHRU = 0; //-> print tags as plain text
    163 
    164     const PHP_QUOTE = 1; //-> escape tags as entities
    165 
    166     const PHP_REMOVE = 2; //-> escape tags as entities
    167 
    168     const PHP_ALLOW = 3; //-> escape tags as entities
    169 
    170     /**
    171      * filter types
    172      */
    173     const FILTER_POST = 'post';
    174 
    175     const FILTER_PRE = 'pre';
    176 
    177     const FILTER_OUTPUT = 'output';
    178 
    179     const FILTER_VARIABLE = 'variable';
    180 
    181     /**
    182      * plugin types
    183      */
    184     const PLUGIN_FUNCTION = 'function';
    185 
    186     const PLUGIN_BLOCK = 'block';
    187 
    188     const PLUGIN_COMPILER = 'compiler';
    189 
    190     const PLUGIN_MODIFIER = 'modifier';
    191 
    192     const PLUGIN_MODIFIERCOMPILER = 'modifiercompiler';
    193 
    194     /**#@-*/
    195 
    196     /**
    197      * assigned global tpl vars
    198      */
    199     public static $global_tpl_vars = array();
    200 
    201     /**
    202      * error handler returned by set_error_hanlder() in Smarty::muteExpectedErrors()
    203      */
    204     public static $_previous_error_handler = null;
    205 
    206     /**
    207      * contains directories outside of SMARTY_DIR that are to be muted by muteExpectedErrors()
    208      */
    209     public static $_muted_directories = array('./templates_c/' => null, './cache/' => null);
    210 
    211     /**
    212      * Flag denoting if Multibyte String functions are available
    213      */
    214     public static $_MBSTRING = SMARTY_MBSTRING;
    215 
    216     /**
    217      * The character set to adhere to (e.g. "UTF-8")
    218      */
    219     public static $_CHARSET = SMARTY_RESOURCE_CHAR_SET;
    220 
    221     /**
    222      * The date format to be used internally
    223      * (accepts date() and strftime())
    224      */
    225     public static $_DATE_FORMAT = SMARTY_RESOURCE_DATE_FORMAT;
    226 
    227     /**
    228      * Flag denoting if PCRE should run in UTF-8 mode
    229      */
    230     public static $_UTF8_MODIFIER = 'u';
    231 
    232     /**
    233      * Flag denoting if operating system is windows
    234      */
    235     public static $_IS_WINDOWS = false;
    236 
    237     /**#@+
    238      * variables
    239      */
    240 
    241     /**
    242      * auto literal on delimiters with whitspace
    243      *
    244      * @var boolean
    245      */
    246     public $auto_literal = true;
    247 
    248     /**
    249      * display error on not assigned variables
    250      *
    251      * @var boolean
    252      */
    253     public $error_unassigned = false;
    254 
    255     /**
    256      * look up relative filepaths in include_path
    257      *
    258      * @var boolean
    259      */
    260     public $use_include_path = false;
    261 
    262     /**
    263      * template directory
    264      *
    265      * @var array
    266      */
    267     private $template_dir = array('./templates/');
    268 
    269     /**
    270      * joined template directory string used in cache keys
    271      *
    272      * @var string
    273      */
    274     public $joined_template_dir = './templates/';
    275 
    276     /**
    277      * joined config directory string used in cache keys
    278      *
    279      * @var string
    280      */
    281     public $joined_config_dir = './configs/';
    282 
    283     /**
    284      * default template handler
    285      *
    286      * @var callable
    287      */
    288     public $default_template_handler_func = null;
    289 
    290     /**
    291      * default config handler
    292      *
    293      * @var callable
    294      */
    295     public $default_config_handler_func = null;
    296 
    297     /**
    298      * default plugin handler
    299      *
    300      * @var callable
    301      */
    302     public $default_plugin_handler_func = null;
    303 
    304     /**
    305      * compile directory
    306      *
    307      * @var string
    308      */
    309     private $compile_dir = './templates_c/';
    310 
    311     /**
    312      * plugins directory
    313      *
    314      * @var array
    315      */
    316     private $plugins_dir = null;
    317 
    318     /**
    319      * cache directory
    320      *
    321      * @var string
    322      */
    323     private $cache_dir = './cache/';
    324 
    325     /**
    326      * config directory
    327      *
    328      * @var array
    329      */
    330     private $config_dir = array('./configs/');
    331 
    332     /**
    333      * force template compiling?
    334      *
    335      * @var boolean
    336      */
    337     public $force_compile = false;
    338 
    339     /**
    340      * check template for modifications?
    341      *
    342      * @var boolean
    343      */
    344     public $compile_check = true;
    345 
    346     /**
    347      * use sub dirs for compiled/cached files?
    348      *
    349      * @var boolean
    350      */
    351     public $use_sub_dirs = false;
    352 
    353     /**
    354      * allow ambiguous resources (that are made unique by the resource handler)
    355      *
    356      * @var boolean
    357      */
    358     public $allow_ambiguous_resources = false;
    359 
    360     /**
    361      * merge compiled includes
    362      *
    363      * @var boolean
    364      */
    365     public $merge_compiled_includes = false;
    366 
    367     /**
    368      * template inheritance merge compiled includes
    369      *
    370      * @var boolean
    371      */
    372     public $inheritance_merge_compiled_includes = true;
    373 
    374     /**
    375      * force cache file creation
    376      *
    377      * @var boolean
    378      */
    379     public $force_cache = false;
    380 
    381     /**
    382      * template left-delimiter
    383      *
    384      * @var string
    385      */
    386     public $left_delimiter = "{";
    387 
    388     /**
    389      * template right-delimiter
    390      *
    391      * @var string
    392      */
    393     public $right_delimiter = "}";
    394 
    395     /**#@+
    396      * security
    397      */
    398     /**
    399      * class name
    400      * This should be instance of Smarty_Security.
    401      *
    402      * @var string
    403      * @see Smarty_Security
    404      */
    405     public $security_class = 'Smarty_Security';
    406 
    407     /**
    408      * implementation of security class
    409      *
    410      * @var Smarty_Security
    411      */
    412     public $security_policy = null;
    413 
    414     /**
    415      * controls handling of PHP-blocks
    416      *
    417      * @var integer
    418      */
    419     public $php_handling = self::PHP_PASSTHRU;
    420 
    421     /**
    422      * controls if the php template file resource is allowed
    423      *
    424      * @var bool
    425      */
    426     public $allow_php_templates = false;
    427 
    428     /**
    429      * Should compiled-templates be prevented from being called directly?
    430      * {@internal
    431      * Currently used by Smarty_Internal_Template only.
    432      * }}
    433      *
    434      * @var boolean
    435      */
    436     public $direct_access_security = true;
    437 
    438     /**#@-*/
    439     /**
    440      * debug mode
    441      * Setting this to true enables the debug-console.
    442      *
    443      * @var boolean
    444      */
    445     public $debugging = false;
    446 
    447     /**
    448      * This determines if debugging is enable-able from the browser.
    449      * <ul>
    450      *  <li>NONE => no debugging control allowed</li>
    451      *  <li>URL => enable debugging when SMARTY_DEBUG is found in the URL.</li>
    452      * </ul>
    453      *
    454      * @var string
    455      */
    456     public $debugging_ctrl = 'NONE';
    457 
    458     /**
    459      * Name of debugging URL-param.
    460      * Only used when $debugging_ctrl is set to 'URL'.
    461      * The name of the URL-parameter that activates debugging.
    462      *
    463      * @var string
    464      */
    465     public $smarty_debug_id = 'SMARTY_DEBUG';
    466 
    467     /**
    468      * Path of debug template.
    469      *
    470      * @var string
    471      */
    472     public $debug_tpl = null;
    473 
    474     /**
    475      * When set, smarty uses this value as error_reporting-level.
    476      *
    477      * @var int
    478      */
    479     public $error_reporting = null;
    480 
    481     /**
    482      * Internal flag for getTags()
    483      *
    484      * @var boolean
    485      */
    486     public $get_used_tags = false;
    487 
    488     /**#@+
    489      * config var settings
    490      */
    491 
    492     /**
    493      * Controls whether variables with the same name overwrite each other.
    494      *
    495      * @var boolean
    496      */
    497     public $config_overwrite = true;
    498 
    499     /**
    500      * Controls whether config values of on/true/yes and off/false/no get converted to boolean.
    501      *
    502      * @var boolean
    503      */
    504     public $config_booleanize = true;
    505 
    506     /**
    507      * Controls whether hidden config sections/vars are read from the file.
    508      *
    509      * @var boolean
    510      */
    511     public $config_read_hidden = false;
    512 
    513     /**#@-*/
    514 
    515     /**#@+
    516      * resource locking
    517      */
    518 
    519     /**
    520      * locking concurrent compiles
    521      *
    522      * @var boolean
    523      */
    524     public $compile_locking = true;
    525 
    526     /**
    527      * Controls whether cache resources should emply locking mechanism
    528      *
    529      * @var boolean
    530      */
    531     public $cache_locking = false;
    532 
    533     /**
    534      * seconds to wait for acquiring a lock before ignoring the write lock
    535      *
    536      * @var float
    537      */
    538     public $locking_timeout = 10;
    539 
    540     /**#@-*/
    541 
    542     /**
    543      * resource type used if none given
    544      * Must be an valid key of $registered_resources.
    545      *
    546      * @var string
    547      */
    548     public $default_resource_type = 'file';
    549 
    550     /**
    551      * caching type
    552      * Must be an element of $cache_resource_types.
    553      *
    554      * @var string
    555      */
    556     public $caching_type = 'file';
    557 
    558     /**
    559      * internal config properties
    560      *
    561      * @var array
    562      */
    563     public $properties = array();
    564 
    565     /**
    566      * config type
    567      *
    568      * @var string
    569      */
    570     public $default_config_type = 'file';
    571 
    572     /**
    573      * cached template objects
    574      *
    575      * @var array
    576      */
    577     public $source_objects = array();
    578 
    579     /**
    580      * cached template objects
    581      *
    582      * @var array
    583      */
    584     public $template_objects = array();
    585 
    586     /**
    587      * enable resource caching
    588      *
    589      * @var bool
    590      */
    591     public $resource_caching = false;
    592 
    593     /**
    594      * enable template resource caching
    595      *
    596      * @var bool
    597      */
    598     public $template_resource_caching = true;
    599 
    600     /**
    601      * check If-Modified-Since headers
    602      *
    603      * @var boolean
    604      */
    605     public $cache_modified_check = false;
    606 
    607     /**
    608      * registered plugins
    609      *
    610      * @var array
    611      */
    612     public $registered_plugins = array();
    613 
    614     /**
    615      * plugin search order
    616      *
    617      * @var array
    618      */
    619     public $plugin_search_order = array('function', 'block', 'compiler', 'class');
    620 
    621     /**
    622      * registered objects
    623      *
    624      * @var array
    625      */
    626     public $registered_objects = array();
    627 
    628     /**
    629      * registered classes
    630      *
    631      * @var array
    632      */
    633     public $registered_classes = array();
    634 
    635     /**
    636      * registered filters
    637      *
    638      * @var array
    639      */
    640     public $registered_filters = array();
    641 
    642     /**
    643      * registered resources
    644      *
    645      * @var array
    646      */
    647     public $registered_resources = array();
    648 
    649     /**
    650      * resource handler cache
    651      *
    652      * @var array
    653      */
    654     public $_resource_handlers = array();
    655 
    656     /**
    657      * registered cache resources
    658      *
    659      * @var array
    660      */
    661     public $registered_cache_resources = array();
    662 
    663     /**
    664      * cache resource handler cache
    665      *
    666      * @var array
    667      */
    668     public $_cacheresource_handlers = array();
    669 
    670     /**
    671      * autoload filter
    672      *
    673      * @var array
    674      */
    675     public $autoload_filters = array();
    676 
    677     /**
    678      * default modifier
    679      *
    680      * @var array
    681      */
    682     public $default_modifiers = array();
    683 
    684     /**
    685      * autoescape variable output
    686      *
    687      * @var boolean
    688      */
    689     public $escape_html = false;
    690 
    691     /**
    692      * global internal smarty vars
    693      *
    694      * @var array
    695      */
    696     public static $_smarty_vars = array();
    697 
    698     /**
    699      * start time for execution time calculation
    700      *
    701      * @var int
    702      */
    703     public $start_time = 0;
    704 
    705     /**
    706      * default file permissions
    707      *
    708      * @var int
    709      */
    710     public $_file_perms = 0644;
    711 
    712     /**
    713      * default dir permissions
    714      *
    715      * @var int
    716      */
    717     public $_dir_perms = 0771;
    718 
    719     /**
    720      * block tag hierarchy
    721      *
    722      * @var array
    723      */
    724     public $_tag_stack = array();
    725 
    726     /**
    727      * required by the compiler for BC
    728      *
    729      * @var string
    730      */
    731     public $_current_file = null;
    732 
    733     /**
    734      * internal flag to enable parser debugging
    735      *
    736      * @var bool
    737      */
    738     public $_parserdebug = false;
    739 
    740     /**
    741      * Cache of is_file results of loadPlugin()
    742      *
    743      * @var array
    744      */
    745     public $_is_file_cache = array();
    746 
    747     /**#@-*/
    748 
    749     /**
    750      * Initialize new Smarty object
    751      */
    752     public function __construct()
    753     {
    754         if (is_callable('mb_internal_encoding')) {
    755             mb_internal_encoding(Smarty::$_CHARSET);
    756         }
    757         $this->start_time = microtime(true);
    758         // check default dirs for overloading
    759         if ($this->template_dir[0] !== './templates/' || isset($this->template_dir[1])) {
    760             $this->setTemplateDir($this->template_dir);
    761         }
    762         if ($this->config_dir[0] !== './configs/' || isset($this->config_dir[1])) {
    763             $this->setConfigDir($this->config_dir);
    764         }
    765         if ($this->compile_dir !== './templates_c/') {
    766             unset(self::$_muted_directories['./templates_c/']);
    767             $this->setCompileDir($this->compile_dir);
    768         }
    769         if ($this->cache_dir !== './cache/') {
    770             unset(self::$_muted_directories['./cache/']);
    771             $this->setCacheDir($this->cache_dir);
    772         }
    773         if (isset($this->plugins_dir)) {
    774             $this->setPluginsDir($this->plugins_dir);
    775         } else {
    776             $this->setPluginsDir(SMARTY_PLUGINS_DIR);
    777         }
    778         if (isset($_SERVER['SCRIPT_NAME'])) {
    779             Smarty::$global_tpl_vars['SCRIPT_NAME'] = new Smarty_Variable($_SERVER['SCRIPT_NAME']);
    780         }
    781 
    782         // Check if we're running on windows
    783         Smarty::$_IS_WINDOWS = strtoupper(substr(PHP_OS, 0, 3)) === 'WIN';
    784 
    785         // let PCRE (preg_*) treat strings as ISO-8859-1 if we're not dealing with UTF-8
    786         if (Smarty::$_CHARSET !== 'UTF-8') {
    787             Smarty::$_UTF8_MODIFIER = '';
    788         }
    789     }
    790 
    791     /**
    792      * fetches a rendered Smarty template
    793      *
    794      * @param  string $template         the resource handle of the template file or template object
    795      * @param  mixed  $cache_id         cache id to be used with this template
    796      * @param  mixed  $compile_id       compile id to be used with this template
    797      * @param  object $parent           next higher level of Smarty variables
    798      * @param  bool   $display          true: display, false: fetch
    799      * @param  bool   $merge_tpl_vars   not used - left for BC
    800      * @param  bool   $no_output_filter not used - left for BC
    801      *
    802      * @throws Exception
    803      * @throws SmartyException
    804      * @return string rendered template output
    805      */
    806     public function fetch($template = null, $cache_id = null, $compile_id = null, $parent = null, $display = false, $merge_tpl_vars = true, $no_output_filter = false)
    807     {
    808         if ($cache_id !== null && is_object($cache_id)) {
    809             $parent = $cache_id;
    810             $cache_id = null;
    811         }
    812         if ($parent === null) {
    813             $parent = $this;
    814         }
    815         // get template object
    816         $_template = is_object($template) ? $template : $this->createTemplate($template, $cache_id, $compile_id, $parent, false);
    817         // set caching in template object
    818         $_template->caching = $this->caching;
    819         // fetch template content
    820         return $_template->render(true, false, $display);
    821     }
    822 
    823     /**
    824      * displays a Smarty template
    825      *
    826      * @param string $template   the resource handle of the template file or template object
    827      * @param mixed  $cache_id   cache id to be used with this template
    828      * @param mixed  $compile_id compile id to be used with this template
    829      * @param object $parent     next higher level of Smarty variables
    830      */
    831     public function display($template = null, $cache_id = null, $compile_id = null, $parent = null)
    832     {
    833         // display template
    834         $this->fetch($template, $cache_id, $compile_id, $parent, true);
    835     }
    836 
    837     /**
    838      * Check if a template resource exists
    839      *
    840      * @param  string $resource_name template name
    841      *
    842      * @return boolean status
    843      */
    844     public function templateExists($resource_name)
    845     {
    846         // create template object
    847         $save = $this->template_objects;
    848         $tpl = new $this->template_class($resource_name, $this);
    849         // check if it does exists
    850         $result = $tpl->source->exists;
    851         $this->template_objects = $save;
    852 
    853         return $result;
    854     }
    855 
    856     /**
    857      * Returns a single or all global  variables
    858      *
    859      * @param  string $varname variable name or null
    860      *
    861      * @return string variable value or or array of variables
    862      */
    863     public function getGlobal($varname = null)
    864     {
    865         if (isset($varname)) {
    866             if (isset(self::$global_tpl_vars[$varname])) {
    867                 return self::$global_tpl_vars[$varname]->value;
    868             } else {
    869                 return '';
    870             }
    871         } else {
    872             $_result = array();
    873             foreach (self::$global_tpl_vars AS $key => $var) {
    874                 $_result[$key] = $var->value;
    875             }
    876 
    877             return $_result;
    878         }
    879     }
    880 
    881     /**
    882      * Empty cache folder
    883      *
    884      * @param  integer $exp_time expiration time
    885      * @param  string  $type     resource type
    886      *
    887      * @return integer number of cache files deleted
    888      */
    889     public function clearAllCache($exp_time = null, $type = null)
    890     {
    891         // load cache resource and call clearAll
    892         $_cache_resource = Smarty_CacheResource::load($this, $type);
    893         Smarty_CacheResource::invalidLoadedCache($this);
    894 
    895         return $_cache_resource->clearAll($this, $exp_time);
    896     }
    897 
    898     /**
    899      * Empty cache for a specific template
    900      *
    901      * @param  string  $template_name template name
    902      * @param  string  $cache_id      cache id
    903      * @param  string  $compile_id    compile id
    904      * @param  integer $exp_time      expiration time
    905      * @param  string  $type          resource type
    906      *
    907      * @return integer number of cache files deleted
    908      */
    909     public function clearCache($template_name, $cache_id = null, $compile_id = null, $exp_time = null, $type = null)
    910     {
    911         // load cache resource and call clear
    912         $_cache_resource = Smarty_CacheResource::load($this, $type);
    913         Smarty_CacheResource::invalidLoadedCache($this);
    914 
    915         return $_cache_resource->clear($this, $template_name, $cache_id, $compile_id, $exp_time);
    916     }
    917 
    918     /**
    919      * Loads security class and enables security
    920      *
    921      * @param  string|Smarty_Security $security_class if a string is used, it must be class-name
    922      *
    923      * @return Smarty                 current Smarty instance for chaining
    924      * @throws SmartyException        when an invalid class name is provided
    925      */
    926     public function enableSecurity($security_class = null)
    927     {
    928         if ($security_class instanceof Smarty_Security) {
    929             $this->security_policy = $security_class;
    930 
    931             return $this;
    932         } elseif (is_object($security_class)) {
    933             throw new SmartyException("Class '" . get_class($security_class) . "' must extend Smarty_Security.");
    934         }
    935         if ($security_class == null) {
    936             $security_class = $this->security_class;
    937         }
    938         if (!class_exists($security_class)) {
    939             throw new SmartyException("Security class '$security_class' is not defined");
    940         } elseif ($security_class !== 'Smarty_Security' && !is_subclass_of($security_class, 'Smarty_Security')) {
    941             throw new SmartyException("Class '$security_class' must extend Smarty_Security.");
    942         } else {
    943             $this->security_policy = new $security_class($this);
    944         }
    945 
    946         return $this;
    947     }
    948 
    949     /**
    950      * Disable security
    951      *
    952      * @return Smarty current Smarty instance for chaining
    953      */
    954     public function disableSecurity()
    955     {
    956         $this->security_policy = null;
    957 
    958         return $this;
    959     }
    960 
    961     /**
    962      * Set template directory
    963      *
    964      * @param  string|array $template_dir directory(s) of template sources
    965      *
    966      * @return Smarty       current Smarty instance for chaining
    967      */
    968     public function setTemplateDir($template_dir)
    969     {
    970         $this->template_dir = array();
    971         foreach ((array) $template_dir as $k => $v) {
    972             $this->template_dir[$k] = rtrim($v, '/\\') . DS;
    973         }
    974         $this->joined_template_dir = join(' # ', $this->template_dir);
    975         return $this;
    976     }
    977 
    978     /**
    979      * Add template directory(s)
    980      *
    981      * @param  string|array $template_dir directory(s) of template sources
    982      * @param  string       $key          of the array element to assign the template dir to
    983      *
    984      * @return Smarty          current Smarty instance for chaining
    985      * @throws SmartyException when the given template directory is not valid
    986      */
    987     public function addTemplateDir($template_dir, $key = null)
    988     {
    989         $this->_addDir('template_dir', $template_dir, $key);
    990         $this->joined_template_dir = join(' # ', $this->template_dir);
    991         return $this;
    992     }
    993 
    994     /**
    995      * Get template directories
    996      *
    997      * @param mixed $index index of directory to get, null to get all
    998      *
    999      * @return array|string list of template directories, or directory of $index
   1000      */
   1001     public function getTemplateDir($index = null)
   1002     {
   1003         if ($index !== null) {
   1004             return isset($this->template_dir[$index]) ? $this->template_dir[$index] : null;
   1005         }
   1006         return (array) $this->template_dir;
   1007     }
   1008 
   1009     /**
   1010      * Set config directory
   1011      *
   1012      * @param $config_dir
   1013      *
   1014      * @return Smarty       current Smarty instance for chaining
   1015      */
   1016     public function setConfigDir($config_dir)
   1017     {
   1018         $this->config_dir = array();
   1019         foreach ((array) $config_dir as $k => $v) {
   1020             $this->config_dir[$k] = rtrim($v, '/\\') . DS;
   1021         }
   1022         $this->joined_config_dir = join(' # ', $this->config_dir);
   1023         return $this;
   1024     }
   1025 
   1026     /**
   1027      * Add config directory(s)
   1028      *
   1029      * @param string|array $config_dir directory(s) of config sources
   1030      * @param mixed        $key        key of the array element to assign the config dir to
   1031      *
   1032      * @return Smarty current Smarty instance for chaining
   1033      */
   1034     public function addConfigDir($config_dir, $key = null)
   1035     {
   1036         $this->_addDir('config_dir', $config_dir, $key);
   1037         $this->joined_config_dir = join(' # ', $this->config_dir);
   1038         return $this;
   1039     }
   1040 
   1041     /**
   1042      * Get config directory
   1043      *
   1044      * @param mixed $index index of directory to get, null to get all
   1045      *
   1046      * @return array|string configuration directory
   1047      */
   1048     public function getConfigDir($index = null)
   1049     {
   1050         if ($index !== null) {
   1051             return isset($this->config_dir[$index]) ? $this->config_dir[$index] : null;
   1052         }
   1053         return (array) $this->config_dir;
   1054     }
   1055 
   1056     /**
   1057      * Set plugins directory
   1058      *
   1059      * @param  string|array $plugins_dir directory(s) of plugins
   1060      *
   1061      * @return Smarty       current Smarty instance for chaining
   1062      */
   1063     public function setPluginsDir($plugins_dir)
   1064     {
   1065         $this->plugins_dir = array();
   1066         $this->addPluginsDir($plugins_dir);
   1067         return $this;
   1068     }
   1069 
   1070     /**
   1071      * Adds directory of plugin files
   1072      *
   1073      * @param $plugins_dir
   1074      *
   1075      * @return Smarty current Smarty instance for chaining
   1076      */
   1077     public function addPluginsDir($plugins_dir)
   1078     {
   1079         // make sure we're dealing with an array
   1080         $this->plugins_dir = (array) $this->plugins_dir;
   1081         foreach ((array) $plugins_dir as $v) {
   1082             $this->plugins_dir[] = rtrim($v, '/\\') . DS;
   1083         }
   1084         $this->plugins_dir = array_unique($this->plugins_dir);
   1085         $this->_is_file_cache = array();
   1086         return $this;
   1087     }
   1088 
   1089     /**
   1090      * Get plugin directories
   1091      *
   1092      * @return array list of plugin directories
   1093      */
   1094     public function getPluginsDir()
   1095     {
   1096         return (array) $this->plugins_dir;
   1097     }
   1098 
   1099     /**
   1100      * Set compile directory
   1101      *
   1102      * @param  string $compile_dir directory to store compiled templates in
   1103      *
   1104      * @return Smarty current Smarty instance for chaining
   1105      */
   1106     public function setCompileDir($compile_dir)
   1107     {
   1108         $this->compile_dir = rtrim($compile_dir, '/\\') . DS;
   1109         if (!isset(Smarty::$_muted_directories[$this->compile_dir])) {
   1110             Smarty::$_muted_directories[$this->compile_dir] = null;
   1111         }
   1112 
   1113         return $this;
   1114     }
   1115 
   1116     /**
   1117      * Get compiled directory
   1118      *
   1119      * @return string path to compiled templates
   1120      */
   1121     public function getCompileDir()
   1122     {
   1123         return $this->compile_dir;
   1124     }
   1125 
   1126     /**
   1127      * Set cache directory
   1128      *
   1129      * @param  string $cache_dir directory to store cached templates in
   1130      *
   1131      * @return Smarty current Smarty instance for chaining
   1132      */
   1133     public function setCacheDir($cache_dir)
   1134     {
   1135         $this->cache_dir = rtrim($cache_dir, '/\\') . DS;
   1136         if (!isset(Smarty::$_muted_directories[$this->cache_dir])) {
   1137             Smarty::$_muted_directories[$this->cache_dir] = null;
   1138         }
   1139         return $this;
   1140     }
   1141 
   1142     /**
   1143      * Get cache directory
   1144      *
   1145      * @return string path of cache directory
   1146      */
   1147     public function getCacheDir()
   1148     {
   1149         return $this->cache_dir;
   1150     }
   1151 
   1152     /**
   1153      * add directories to given property name
   1154      *
   1155      * @param string       $dirName directory property name
   1156      * @param string|array $dir     directory string or array of strings
   1157      * @param mixed        $key     optional key
   1158      */
   1159     private function _addDir($dirName, $dir, $key = null)
   1160     {
   1161         // make sure we're dealing with an array
   1162         $this->$dirName = (array) $this->$dirName;
   1163 
   1164         if (is_array($dir)) {
   1165             foreach ($dir as $k => $v) {
   1166                 if (is_int($k)) {
   1167                     // indexes are not merged but appended
   1168                     $this->{$dirName}[] = rtrim($v, '/\\') . DS;
   1169                 } else {
   1170                     // string indexes are overridden
   1171                     $this->{$dirName}[$k] = rtrim($v, '/\\') . DS;
   1172                 }
   1173             }
   1174         } else {
   1175             if ($key !== null) {
   1176                 // override directory at specified index
   1177                 $this->{$dirName}[$key] = rtrim($dir, '/\\') . DS;
   1178             } else {
   1179                 // append new directory
   1180                 $this->{$dirName}[] = rtrim($dir, '/\\') . DS;
   1181             }
   1182         }
   1183     }
   1184 
   1185     /**
   1186      * Set default modifiers
   1187      *
   1188      * @param  array|string $modifiers modifier or list of modifiers to set
   1189      *
   1190      * @return Smarty       current Smarty instance for chaining
   1191      */
   1192     public function setDefaultModifiers($modifiers)
   1193     {
   1194         $this->default_modifiers = (array) $modifiers;
   1195 
   1196         return $this;
   1197     }
   1198 
   1199     /**
   1200      * Add default modifiers
   1201      *
   1202      * @param  array|string $modifiers modifier or list of modifiers to add
   1203      *
   1204      * @return Smarty       current Smarty instance for chaining
   1205      */
   1206     public function addDefaultModifiers($modifiers)
   1207     {
   1208         if (is_array($modifiers)) {
   1209             $this->default_modifiers = array_merge($this->default_modifiers, $modifiers);
   1210         } else {
   1211             $this->default_modifiers[] = $modifiers;
   1212         }
   1213 
   1214         return $this;
   1215     }
   1216 
   1217     /**
   1218      * Get default modifiers
   1219      *
   1220      * @return array list of default modifiers
   1221      */
   1222     public function getDefaultModifiers()
   1223     {
   1224         return $this->default_modifiers;
   1225     }
   1226 
   1227     /**
   1228      * Set autoload filters
   1229      *
   1230      * @param  array  $filters filters to load automatically
   1231      * @param  string $type    "pre", "output", … specify the filter type to set. Defaults to none treating $filters'
   1232      *                         keys as the appropriate types
   1233      *
   1234      * @return Smarty current Smarty instance for chaining
   1235      */
   1236     public function setAutoloadFilters($filters, $type = null)
   1237     {
   1238         if ($type !== null) {
   1239             $this->autoload_filters[$type] = (array) $filters;
   1240         } else {
   1241             $this->autoload_filters = (array) $filters;
   1242         }
   1243 
   1244         return $this;
   1245     }
   1246 
   1247     /**
   1248      * Add autoload filters
   1249      *
   1250      * @param  array  $filters filters to load automatically
   1251      * @param  string $type    "pre", "output", … specify the filter type to set. Defaults to none treating $filters'
   1252      *                         keys as the appropriate types
   1253      *
   1254      * @return Smarty current Smarty instance for chaining
   1255      */
   1256     public function addAutoloadFilters($filters, $type = null)
   1257     {
   1258         if ($type !== null) {
   1259             if (!empty($this->autoload_filters[$type])) {
   1260                 $this->autoload_filters[$type] = array_merge($this->autoload_filters[$type], (array) $filters);
   1261             } else {
   1262                 $this->autoload_filters[$type] = (array) $filters;
   1263             }
   1264         } else {
   1265             foreach ((array) $filters as $key => $value) {
   1266                 if (!empty($this->autoload_filters[$key])) {
   1267                     $this->autoload_filters[$key] = array_merge($this->autoload_filters[$key], (array) $value);
   1268                 } else {
   1269                     $this->autoload_filters[$key] = (array) $value;
   1270                 }
   1271             }
   1272         }
   1273 
   1274         return $this;
   1275     }
   1276 
   1277     /**
   1278      * Get autoload filters
   1279      *
   1280      * @param  string $type type of filter to get autoloads for. Defaults to all autoload filters
   1281      *
   1282      * @return array  array( 'type1' => array( 'filter1', 'filter2', … ) ) or array( 'filter1', 'filter2', …) if $type
   1283      *                was specified
   1284      */
   1285     public function getAutoloadFilters($type = null)
   1286     {
   1287         if ($type !== null) {
   1288             return isset($this->autoload_filters[$type]) ? $this->autoload_filters[$type] : array();
   1289         }
   1290 
   1291         return $this->autoload_filters;
   1292     }
   1293 
   1294     /**
   1295      * return name of debugging template
   1296      *
   1297      * @return string
   1298      */
   1299     public function getDebugTemplate()
   1300     {
   1301         return $this->debug_tpl;
   1302     }
   1303 
   1304     /**
   1305      * set the debug template
   1306      *
   1307      * @param  string $tpl_name
   1308      *
   1309      * @return Smarty          current Smarty instance for chaining
   1310      * @throws SmartyException if file is not readable
   1311      */
   1312     public function setDebugTemplate($tpl_name)
   1313     {
   1314         if (!is_readable($tpl_name)) {
   1315             throw new SmartyException("Unknown file '{$tpl_name}'");
   1316         }
   1317         $this->debug_tpl = $tpl_name;
   1318 
   1319         return $this;
   1320     }
   1321 
   1322     /**
   1323      * creates a template object
   1324      *
   1325      * @param  string  $template   the resource handle of the template file
   1326      * @param  mixed   $cache_id   cache id to be used with this template
   1327      * @param  mixed   $compile_id compile id to be used with this template
   1328      * @param  object  $parent     next higher level of Smarty variables
   1329      * @param  boolean $do_clone   flag is Smarty object shall be cloned
   1330      *
   1331      * @return object  template object
   1332      */
   1333     public function createTemplate($template, $cache_id = null, $compile_id = null, $parent = null, $do_clone = true)
   1334     {
   1335         if ($cache_id !== null && (is_object($cache_id) || is_array($cache_id))) {
   1336             $parent = $cache_id;
   1337             $cache_id = null;
   1338         }
   1339         if ($parent !== null && is_array($parent)) {
   1340             $data = $parent;
   1341             $parent = null;
   1342         } else {
   1343             $data = null;
   1344         }
   1345         $_templateId = $this->getTemplateId($template, $cache_id, $compile_id);
   1346         if (isset($this->template_objects[$_templateId])) {
   1347             if ($do_clone) {
   1348                 $tpl = clone $this->template_objects[$_templateId];
   1349                 $tpl->smarty = clone $tpl->smarty;
   1350             } else {
   1351                 $tpl = $this->template_objects[$_templateId];
   1352             }
   1353             $tpl->parent = $parent;
   1354             $tpl->tpl_vars = array();
   1355             $tpl->config_vars = array();
   1356         } else {
   1357             $tpl = new $this->template_class($template, $this, $parent, $cache_id, $compile_id);
   1358             if ($do_clone) {
   1359                 $tpl->smarty = clone $tpl->smarty;
   1360             }
   1361             $tpl->templateId = $_templateId;
   1362         }
   1363         // fill data if present
   1364         if (!empty($data) && is_array($data)) {
   1365             // set up variable values
   1366             foreach ($data as $_key => $_val) {
   1367                 $tpl->tpl_vars[$_key] = new Smarty_Variable($_val);
   1368             }
   1369         }
   1370         if ($this->debugging) {
   1371             Smarty_Internal_Debug::register_template($tpl);
   1372         }
   1373         return $tpl;
   1374     }
   1375 
   1376     /**
   1377      * Takes unknown classes and loads plugin files for them
   1378      * class name format: Smarty_PluginType_PluginName
   1379      * plugin filename format: plugintype.pluginname.php
   1380      *
   1381      * @param  string $plugin_name class plugin name to load
   1382      * @param  bool   $check       check if already loaded
   1383      *
   1384      * @throws SmartyException
   1385      * @return string |boolean filepath of loaded file or false
   1386      */
   1387     public function loadPlugin($plugin_name, $check = true)
   1388     {
   1389         // if function or class exists, exit silently (already loaded)
   1390         if ($check && (is_callable($plugin_name) || class_exists($plugin_name, false))) {
   1391             return true;
   1392         }
   1393         // Plugin name is expected to be: Smarty_[Type]_[Name]
   1394         $_name_parts = explode('_', $plugin_name, 3);
   1395         // class name must have three parts to be valid plugin
   1396         // count($_name_parts) < 3 === !isset($_name_parts[2])
   1397         if (!isset($_name_parts[2]) || strtolower($_name_parts[0]) !== 'smarty') {
   1398             throw new SmartyException("plugin {$plugin_name} is not a valid name format");
   1399         }
   1400         // if type is "internal", get plugin from sysplugins
   1401         if (strtolower($_name_parts[1]) == 'internal') {
   1402             $file = SMARTY_SYSPLUGINS_DIR . strtolower($plugin_name) . '.php';
   1403             if (isset($this->_is_file_cache[$file]) ? $this->_is_file_cache[$file] : $this->_is_file_cache[$file] = is_file($file)) {
   1404                 require_once($file);
   1405                 return $file;
   1406             } else {
   1407                 return false;
   1408             }
   1409         }
   1410         // plugin filename is expected to be: [type].[name].php
   1411         $_plugin_filename = "{$_name_parts[1]}.{$_name_parts[2]}.php";
   1412 
   1413         $_stream_resolve_include_path = function_exists('stream_resolve_include_path');
   1414 
   1415         // loop through plugin dirs and find the plugin
   1416         foreach ($this->getPluginsDir() as $_plugin_dir) {
   1417             $names = array($_plugin_dir . $_plugin_filename, $_plugin_dir . strtolower($_plugin_filename),);
   1418             foreach ($names as $file) {
   1419                 if (isset($this->_is_file_cache[$file]) ? $this->_is_file_cache[$file] : $this->_is_file_cache[$file] = is_file($file)) {
   1420                     require_once($file);
   1421                     return $file;
   1422                 }
   1423                 if ($this->use_include_path && !preg_match('/^([\/\\\\]|[a-zA-Z]:[\/\\\\])/', $_plugin_dir)) {
   1424                     // try PHP include_path
   1425                     if ($_stream_resolve_include_path) {
   1426                         $file = stream_resolve_include_path($file);
   1427                     } else {
   1428                         $file = Smarty_Internal_Get_Include_Path::getIncludePath($file);
   1429                     }
   1430 
   1431                     if ($file !== false) {
   1432                         require_once($file);
   1433 
   1434                         return $file;
   1435                     }
   1436                 }
   1437             }
   1438         }
   1439         // no plugin loaded
   1440         return false;
   1441     }
   1442 
   1443     /**
   1444      * Compile all template files
   1445      *
   1446      * @param  string $extension     file extension
   1447      * @param  bool   $force_compile force all to recompile
   1448      * @param  int    $time_limit
   1449      * @param  int    $max_errors
   1450      *
   1451      * @return integer number of template files recompiled
   1452      */
   1453     public function compileAllTemplates($extension = '.tpl', $force_compile = false, $time_limit = 0, $max_errors = null)
   1454     {
   1455         return Smarty_Internal_Utility::compileAllTemplates($extension, $force_compile, $time_limit, $max_errors, $this);
   1456     }
   1457 
   1458     /**
   1459      * Compile all config files
   1460      *
   1461      * @param  string $extension     file extension
   1462      * @param  bool   $force_compile force all to recompile
   1463      * @param  int    $time_limit
   1464      * @param  int    $max_errors
   1465      *
   1466      * @return integer number of template files recompiled
   1467      */
   1468     public function compileAllConfig($extension = '.conf', $force_compile = false, $time_limit = 0, $max_errors = null)
   1469     {
   1470         return Smarty_Internal_Utility::compileAllConfig($extension, $force_compile, $time_limit, $max_errors, $this);
   1471     }
   1472 
   1473     /**
   1474      * Delete compiled template file
   1475      *
   1476      * @param  string  $resource_name template name
   1477      * @param  string  $compile_id    compile id
   1478      * @param  integer $exp_time      expiration time
   1479      *
   1480      * @return integer number of template files deleted
   1481      */
   1482     public function clearCompiledTemplate($resource_name = null, $compile_id = null, $exp_time = null)
   1483     {
   1484         return Smarty_Internal_Utility::clearCompiledTemplate($resource_name, $compile_id, $exp_time, $this);
   1485     }
   1486 
   1487     /**
   1488      * Return array of tag/attributes of all tags used by an template
   1489      *
   1490      * @param Smarty_Internal_Template $template
   1491      *
   1492      * @return array  of tag/attributes
   1493      */
   1494     public function getTags(Smarty_Internal_Template $template)
   1495     {
   1496         return Smarty_Internal_Utility::getTags($template);
   1497     }
   1498 
   1499     /**
   1500      * Run installation test
   1501      *
   1502      * @param  array $errors Array to write errors into, rather than outputting them
   1503      *
   1504      * @return boolean true if setup is fine, false if something is wrong
   1505      */
   1506     public function testInstall(&$errors = null)
   1507     {
   1508         return Smarty_Internal_TestInstall::testInstall($this, $errors);
   1509     }
   1510 
   1511     /**
   1512      * @param boolean $compile_check
   1513      */
   1514     public function setCompileCheck($compile_check)
   1515     {
   1516         $this->compile_check = $compile_check;
   1517     }
   1518 
   1519     /**
   1520      * @param boolean $use_sub_dirs
   1521      */
   1522     public function setUseSubDirs($use_sub_dirs)
   1523     {
   1524         $this->use_sub_dirs = $use_sub_dirs;
   1525     }
   1526 
   1527     /**
   1528      * @param boolean $caching
   1529      */
   1530     public function setCaching($caching)
   1531     {
   1532         $this->caching = $caching;
   1533     }
   1534 
   1535     /**
   1536      * @param int $cache_lifetime
   1537      */
   1538     public function setCacheLifetime($cache_lifetime)
   1539     {
   1540         $this->cache_lifetime = $cache_lifetime;
   1541     }
   1542 
   1543     /**
   1544      * @param string $compile_id
   1545      */
   1546     public function setCompileId($compile_id)
   1547     {
   1548         $this->compile_id = $compile_id;
   1549     }
   1550 
   1551     /**
   1552      * @param string $cache_id
   1553      */
   1554     public function setCacheId($cache_id)
   1555     {
   1556         $this->cache_id = $cache_id;
   1557     }
   1558 
   1559     /**
   1560      * @param int $error_reporting
   1561      */
   1562     public function setErrorReporting($error_reporting)
   1563     {
   1564         $this->error_reporting = $error_reporting;
   1565     }
   1566 
   1567     /**
   1568      * @param boolean $escape_html
   1569      */
   1570     public function setEscapeHtml($escape_html)
   1571     {
   1572         $this->escape_html = $escape_html;
   1573     }
   1574 
   1575     /**
   1576      * @param boolean $auto_literal
   1577      */
   1578     public function setAutoLiteral($auto_literal)
   1579     {
   1580         $this->auto_literal = $auto_literal;
   1581     }
   1582 
   1583     /**
   1584      * @param boolean $force_compile
   1585      */
   1586     public function setForceCompile($force_compile)
   1587     {
   1588         $this->force_compile = $force_compile;
   1589     }
   1590 
   1591     /**
   1592      * @param boolean $merge_compiled_includes
   1593      */
   1594     public function setMergeCompiledIncludes($merge_compiled_includes)
   1595     {
   1596         $this->merge_compiled_includes = $merge_compiled_includes;
   1597     }
   1598 
   1599     /**
   1600      * @param string $left_delimiter
   1601      */
   1602     public function setLeftDelimiter($left_delimiter)
   1603     {
   1604         $this->left_delimiter = $left_delimiter;
   1605     }
   1606 
   1607     /**
   1608      * @param string $right_delimiter
   1609      */
   1610     public function setRightDelimiter($right_delimiter)
   1611     {
   1612         $this->right_delimiter = $right_delimiter;
   1613     }
   1614 
   1615     /**
   1616      * @param boolean $debugging
   1617      */
   1618     public function setDebugging($debugging)
   1619     {
   1620         $this->debugging = $debugging;
   1621     }
   1622 
   1623     /**
   1624      * @param boolean $config_overwrite
   1625      */
   1626     public function setConfigOverwrite($config_overwrite)
   1627     {
   1628         $this->config_overwrite = $config_overwrite;
   1629     }
   1630 
   1631     /**
   1632      * @param boolean $config_booleanize
   1633      */
   1634     public function setConfigBooleanize($config_booleanize)
   1635     {
   1636         $this->config_booleanize = $config_booleanize;
   1637     }
   1638 
   1639     /**
   1640      * @param boolean $config_read_hidden
   1641      */
   1642     public function setConfigReadHidden($config_read_hidden)
   1643     {
   1644         $this->config_read_hidden = $config_read_hidden;
   1645     }
   1646 
   1647     /**
   1648      * @param boolean $compile_locking
   1649      */
   1650     public function setCompileLocking($compile_locking)
   1651     {
   1652         $this->compile_locking = $compile_locking;
   1653     }
   1654 
   1655     /**
   1656      * Class destructor
   1657      */
   1658     public function __destruct()
   1659     {
   1660         // intentionally left blank
   1661     }
   1662 
   1663     /**
   1664      * <<magic>> Generic getter.
   1665      * Calls the appropriate getter function.
   1666      * Issues an E_USER_NOTICE if no valid getter is found.
   1667      *
   1668      * @param  string $name property name
   1669      *
   1670      * @return mixed
   1671      */
   1672     public function __get($name)
   1673     {
   1674         $allowed = array('template_dir' => 'getTemplateDir', 'config_dir' => 'getConfigDir',
   1675                          'plugins_dir'  => 'getPluginsDir', 'compile_dir' => 'getCompileDir',
   1676                          'cache_dir'    => 'getCacheDir',);
   1677 
   1678         if (isset($allowed[$name])) {
   1679             return $this->{$allowed[$name]}();
   1680         } else {
   1681             trigger_error('Undefined property: ' . get_class($this) . '::$' . $name, E_USER_NOTICE);
   1682         }
   1683     }
   1684 
   1685     /**
   1686      * <<magic>> Generic setter.
   1687      * Calls the appropriate setter function.
   1688      * Issues an E_USER_NOTICE if no valid setter is found.
   1689      *
   1690      * @param string $name  property name
   1691      * @param mixed  $value parameter passed to setter
   1692      */
   1693     public function __set($name, $value)
   1694     {
   1695         $allowed = array('template_dir' => 'setTemplateDir', 'config_dir' => 'setConfigDir',
   1696                          'plugins_dir'  => 'setPluginsDir', 'compile_dir' => 'setCompileDir',
   1697                          'cache_dir'    => 'setCacheDir',);
   1698 
   1699         if (isset($allowed[$name])) {
   1700             $this->{$allowed[$name]}($value);
   1701         } else {
   1702             trigger_error('Undefined property: ' . get_class($this) . '::$' . $name, E_USER_NOTICE);
   1703         }
   1704     }
   1705 
   1706     /**
   1707      * Error Handler to mute expected messages
   1708      *
   1709      * @link http://php.net/set_error_handler
   1710      *
   1711      * @param  integer $errno Error level
   1712      * @param          $errstr
   1713      * @param          $errfile
   1714      * @param          $errline
   1715      * @param          $errcontext
   1716      *
   1717      * @return boolean
   1718      */
   1719     public static function mutingErrorHandler($errno, $errstr, $errfile, $errline, $errcontext)
   1720     {
   1721         $_is_muted_directory = false;
   1722 
   1723         // add the SMARTY_DIR to the list of muted directories
   1724         if (!isset(Smarty::$_muted_directories[SMARTY_DIR])) {
   1725             $smarty_dir = realpath(SMARTY_DIR);
   1726             if ($smarty_dir !== false) {
   1727                 Smarty::$_muted_directories[SMARTY_DIR] = array('file'   => $smarty_dir,
   1728                                                                 'length' => strlen($smarty_dir),);
   1729             }
   1730         }
   1731 
   1732         // walk the muted directories and test against $errfile
   1733         foreach (Smarty::$_muted_directories as $key => &$dir) {
   1734             if (!$dir) {
   1735                 // resolve directory and length for speedy comparisons
   1736                 $file = realpath($key);
   1737                 if ($file === false) {
   1738                     // this directory does not exist, remove and skip it
   1739                     unset(Smarty::$_muted_directories[$key]);
   1740                     continue;
   1741                 }
   1742                 $dir = array('file' => $file, 'length' => strlen($file),);
   1743             }
   1744             if (!strncmp($errfile, $dir['file'], $dir['length'])) {
   1745                 $_is_muted_directory = true;
   1746                 break;
   1747             }
   1748         }
   1749 
   1750         // pass to next error handler if this error did not occur inside SMARTY_DIR
   1751         // or the error was within smarty but masked to be ignored
   1752         if (!$_is_muted_directory || ($errno && $errno & error_reporting())) {
   1753             if (Smarty::$_previous_error_handler) {
   1754                 return call_user_func(Smarty::$_previous_error_handler, $errno, $errstr, $errfile, $errline, $errcontext);
   1755             } else {
   1756                 return false;
   1757             }
   1758         }
   1759     }
   1760 
   1761     /**
   1762      * Enable error handler to mute expected messages
   1763      *
   1764      * @return void
   1765      */
   1766     public static function muteExpectedErrors()
   1767     {
   1768         /*
   1769             error muting is done because some people implemented custom error_handlers using
   1770             http://php.net/set_error_handler and for some reason did not understand the following paragraph:
   1771 
   1772                 It is important to remember that the standard PHP error handler is completely bypassed for the
   1773                 error types specified by error_types unless the callback function returns FALSE.
   1774                 error_reporting() settings will have no effect and your error handler will be called regardless -
   1775                 however you are still able to read the current value of error_reporting and act appropriately.
   1776                 Of particular note is that this value will be 0 if the statement that caused the error was
   1777                 prepended by the @ error-control operator.
   1778 
   1779             Smarty deliberately uses @filemtime() over file_exists() and filemtime() in some places. Reasons include
   1780                 - @filemtime() is almost twice as fast as using an additional file_exists()
   1781                 - between file_exists() and filemtime() a possible race condition is opened,
   1782                   which does not exist using the simple @filemtime() approach.
   1783         */
   1784         $error_handler = array('Smarty', 'mutingErrorHandler');
   1785         $previous = set_error_handler($error_handler);
   1786 
   1787         // avoid dead loops
   1788         if ($previous !== $error_handler) {
   1789             Smarty::$_previous_error_handler = $previous;
   1790         }
   1791     }
   1792 
   1793     /**
   1794      * Disable error handler muting expected messages
   1795      *
   1796      * @return void
   1797      */
   1798     public static function unmuteExpectedErrors()
   1799     {
   1800         restore_error_handler();
   1801     }
   1802 }