/**
 *
 *
 * @param unknown $params
 * @param unknown $smarty (reference)
 */
function smarty_core_load_resource_plugin($params, &$smarty)
{
    /*
     * Resource plugins are not quite like the other ones, so they are
     * handled differently. The first element of plugin info is the array of
     * functions provided by the plugin, the second one indicates whether
     * all of them exist or not.
     */
    $_plugin =& $smarty->_plugins['resource'][$params['type']];
    if (isset($_plugin)) {
        if (!$_plugin[1] && count($_plugin[0])) {
            $_plugin[1] = true;
            foreach ($_plugin[0] as $_plugin_func) {
                if (!is_callable($_plugin_func)) {
                    $_plugin[1] = false;
                    break;
                }
            }
        }
        if (!$_plugin[1]) {
            $smarty->_trigger_fatal_error("[plugin] resource '" . $params['type'] . "' is not implemented", null, null, __FILE__, __LINE__);
        }
        return;
    }
    $_plugin_file = $smarty->_get_plugin_filepath('resource', $params['type']);
    $_found = $_plugin_file != false;
    if ($_found) {
        /*
         * If the plugin file is found, it -must- provide the properly named
         * plugin functions.
         */
        include_once $_plugin_file;
        /*
         * Locate functions that we require the plugin to provide.
         */
        $_resource_ops = array('source', 'timestamp', 'secure', 'trusted');
        $_resource_funcs = array();
        foreach ($_resource_ops as $_op) {
            $_plugin_func = 'smarty_resource_' . $params['type'] . '_' . $_op;
            if (!function_exists($_plugin_func)) {
                $smarty->_trigger_fatal_error("[plugin] function {$_plugin_func}() not found in {$_plugin_file}", null, null, __FILE__, __LINE__);
                return;
            } else {
                $_resource_funcs[] = $_plugin_func;
            }
        }
        $smarty->_plugins['resource'][$params['type']] = array($_resource_funcs, true);
    }
}
/**
 * Smarty {fetch} plugin
 *
 * Type:     function<br>
 * Name:     fetch<br>
 * Purpose:  fetch file, web or ftp data and display results
 *
 * @link http://smarty.php.net/manual/en/language.function.fetch.php {fetch}
 *       (Smarty online manual)
 * @param array
 * @param Smarty
 *                     result to a template variable
 * @param unknown $params
 * @param unknown $smarty (reference)
 * @return string|null if the assign parameter is passed, Smarty assigns the
 */
function smarty_function_fetch($params, &$smarty)
{
    if (empty($params['file'])) {
        $smarty->_trigger_fatal_error("[plugin] parameter 'file' cannot be empty");
        return;
    }
    if ($smarty->security && !preg_match('!^(http|ftp)://!i', $params['file'])) {
        $_params = array('resource_type' => 'file', 'resource_name' => $params['file']);
        require_once SMARTY_DIR . 'core' . DIRECTORY_SEPARATOR . 'core.is_secure.php';
        if (!smarty_core_is_secure($_params, $smarty)) {
            $smarty->_trigger_fatal_error('[plugin] (secure mode) fetch \'' . $params['file'] . '\' is not allowed');
            return;
        }
        // fetch the file
        if ($fp = @fopen($params['file'], 'r')) {
            while (!feof($fp)) {
                $content .= fgets($fp, 4096);
            }
            fclose($fp);
        } else {
            $smarty->_trigger_fatal_error('[plugin] fetch cannot read file \'' . $params['file'] . '\'');
            return;
        }
    } else {
        // not a local file
        if (preg_match('!^http://!i', $params['file'])) {
            // http fetch
            if ($uri_parts = parse_url($params['file'])) {
                // set defaults
                $host = $server_name = $uri_parts['host'];
                $timeout = 30;
                $accept = "image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, */*";
                $agent = "Smarty Template Engine " . $smarty->_version;
                $referer = "";
                $uri = !empty($uri_parts['path']) ? $uri_parts['path'] : '/';
                $uri .= !empty($uri_parts['query']) ? '?' . $uri_parts['query'] : '';
                $_is_proxy = false;
                if (empty($uri_parts['port'])) {
                    $port = 80;
                } else {
                    $port = $uri_parts['port'];
                }
                if (empty($uri_parts['user'])) {
                    $user = '';
                }
                // loop through parameters, setup headers
                foreach ($params as $param_key => $param_value) {
                    switch ($param_key) {
                        case "file":
                        case "assign":
                        case "assign_headers":
                            break;
                        case "user":
                            if (!empty($param_value)) {
                                $user = $param_value;
                            }
                            break;
                        case "pass":
                            if (!empty($param_value)) {
                                $pass = $param_value;
                            }
                            break;
                        case "accept":
                            if (!empty($param_value)) {
                                $accept = $param_value;
                            }
                            break;
                        case "header":
                            if (!empty($param_value)) {
                                if (!preg_match('![\\w\\d-]+: .+!', $param_value)) {
                                    $smarty->_trigger_fatal_error("[plugin] invalid header format '" . $param_value . "'");
                                    return;
                                } else {
                                    $extra_headers[] = $param_value;
                                }
                            }
                            break;
                        case "proxy_host":
                            if (!empty($param_value)) {
                                $proxy_host = $param_value;
                            }
                            break;
                        case "proxy_port":
                            if (!preg_match('!\\D!', $param_value)) {
                                $proxy_port = (int) $param_value;
                            } else {
                                $smarty->_trigger_fatal_error("[plugin] invalid value for attribute '" . $param_key . "'");
                                return;
                            }
                            break;
                        case "agent":
                            if (!empty($param_value)) {
                                $agent = $param_value;
                            }
                            break;
                        case "referer":
                            if (!empty($param_value)) {
                                $referer = $param_value;
                            }
                            break;
                        case "timeout":
                            if (!preg_match('!\\D!', $param_value)) {
                                $timeout = (int) $param_value;
                            } else {
                                $smarty->_trigger_fatal_error("[plugin] invalid value for attribute '" . $param_key . "'");
                                return;
                            }
                            break;
                        default:
                            $smarty->_trigger_fatal_error("[plugin] unrecognized attribute '" . $param_key . "'");
                            return;
                    }
                }
                if (!empty($proxy_host) && !empty($proxy_port)) {
                    $_is_proxy = true;
                    $fp = fsockopen($proxy_host, $proxy_port, $errno, $errstr, $timeout);
                } else {
                    $fp = fsockopen($server_name, $port, $errno, $errstr, $timeout);
                }
                if (!$fp) {
                    $smarty->_trigger_fatal_error("[plugin] unable to fetch: {$errstr} ({$errno})");
                    return;
                } else {
                    if ($_is_proxy) {
                        fputs($fp, 'GET ' . $params['file'] . " HTTP/1.0\r\n");
                    } else {
                        fputs($fp, "GET {$uri} HTTP/1.0\r\n");
                    }
                    if (!empty($host)) {
                        fputs($fp, "Host: {$host}\r\n");
                    }
                    if (!empty($accept)) {
                        fputs($fp, "Accept: {$accept}\r\n");
                    }
                    if (!empty($agent)) {
                        fputs($fp, "User-Agent: {$agent}\r\n");
                    }
                    if (!empty($referer)) {
                        fputs($fp, "Referer: {$referer}\r\n");
                    }
                    if (isset($extra_headers) && is_array($extra_headers)) {
                        foreach ($extra_headers as $curr_header) {
                            fputs($fp, $curr_header . "\r\n");
                        }
                    }
                    if (!empty($user) && !empty($pass)) {
                        fputs($fp, "Authorization: BASIC " . base64_encode("{$user}:{$pass}") . "\r\n");
                    }
                    $content = '';
                    fputs($fp, "\r\n");
                    while (!feof($fp)) {
                        $content .= fgets($fp, 4096);
                    }
                    fclose($fp);
                    $csplit = split("\r\n\r\n", $content, 2);
                    $content = $csplit[1];
                    if (!empty($params['assign_headers'])) {
                        $smarty->assign($params['assign_headers'], split("\r\n", $csplit[0]));
                    }
                }
            } else {
                $smarty->_trigger_fatal_error("[plugin] unable to parse URL, check syntax");
                return;
            }
        } else {
            // ftp fetch
            if ($fp = @fopen($params['file'], 'r')) {
                while (!feof($fp)) {
                    $content .= fgets($fp, 4096);
                }
                fclose($fp);
            } else {
                $smarty->_trigger_fatal_error('[plugin] fetch cannot read file \'' . $params['file'] . '\'');
                return;
            }
        }
    }
    if (!empty($params['assign'])) {
        $smarty->assign($params['assign'], $content);
    } else {
        return $content;
    }
}
/**
 *
 *
 * @param unknown $params
 * @param unknown $smarty (reference)
 */
function smarty_core_load_plugins($params, &$smarty)
{
    foreach ($params['plugins'] as $_plugin_info) {
        list($_type, $_name, $_tpl_file, $_tpl_line, $_delayed_loading) = $_plugin_info;
        $_plugin =& $smarty->_plugins[$_type][$_name];
        /*
         * We do not load plugin more than once for each instance of Smarty.
         * The following code checks for that. The plugin can also be
         * registered dynamically at runtime, in which case template file
         * and line number will be unknown, so we fill them in.
         *
         * The final element of the info array is a flag that indicates
         * whether the dynamically registered plugin function has been
         * checked for existence yet or not.
         */
        if (isset($_plugin)) {
            if (empty($_plugin[3])) {
                if (!is_callable($_plugin[0])) {
                    $smarty->_trigger_fatal_error("[plugin] {$_type} '{$_name}' is not implemented", $_tpl_file, $_tpl_line, __FILE__, __LINE__);
                } else {
                    $_plugin[1] = $_tpl_file;
                    $_plugin[2] = $_tpl_line;
                    $_plugin[3] = true;
                    if (!isset($_plugin[4])) {
                        $_plugin[4] = true;
                    }
                    /* cacheable */
                }
            }
            continue;
        } else {
            if ($_type == 'insert') {
                /*
                 * For backwards compatibility, we check for insert functions in
                 * the symbol table before trying to load them as a plugin.
                 */
                $_plugin_func = 'insert_' . $_name;
                if (function_exists($_plugin_func)) {
                    $_plugin = array($_plugin_func, $_tpl_file, $_tpl_line, true, false);
                    continue;
                }
            }
        }
        $_plugin_file = $smarty->_get_plugin_filepath($_type, $_name);
        if (!($_found = $_plugin_file != false)) {
            $_message = "could not load plugin file '{$_type}.{$_name}.php'\n";
        }
        /*
         * If plugin file is found, it -must- provide the properly named
         * plugin function. In case it doesn't, simply output the error and
         * do not fall back on any other method.
         */
        if ($_found) {
            include_once $_plugin_file;
            $_plugin_func = 'smarty_' . $_type . '_' . $_name;
            if (!function_exists($_plugin_func)) {
                $smarty->_trigger_fatal_error("[plugin] function {$_plugin_func}() not found in {$_plugin_file}", $_tpl_file, $_tpl_line, __FILE__, __LINE__);
                continue;
            }
        } else {
            if ($_type == 'insert' && $_delayed_loading) {
                $_plugin_func = 'smarty_' . $_type . '_' . $_name;
                $_found = true;
            }
        }
        /*
         * Plugin specific processing and error checking.
         */
        if (!$_found) {
            if ($_type == 'modifier') {
                /*
                 * In case modifier falls back on using PHP functions
                 * directly, we only allow those specified in the security
                 * context.
                 */
                if ($smarty->security && !in_array($_name, $smarty->security_settings['MODIFIER_FUNCS'])) {
                    $_message = "(secure mode) modifier '{$_name}' is not allowed";
                } else {
                    if (!function_exists($_name)) {
                        $_message = "modifier '{$_name}' is not implemented";
                    } else {
                        $_plugin_func = $_name;
                        $_found = true;
                    }
                }
            } else {
                if ($_type == 'function') {
                    /*
                     * This is a catch-all situation.
                     */
                    $_message = "unknown tag - '{$_name}'";
                }
            }
        }
        if ($_found) {
            $smarty->_plugins[$_type][$_name] = array($_plugin_func, $_tpl_file, $_tpl_line, true, true);
        } else {
            // output error
            $smarty->_trigger_fatal_error('[plugin] ' . $_message, $_tpl_file, $_tpl_line, __FILE__, __LINE__);
        }
    }
}