/** * Processes a raw template for conditionals, phrases etc into PHP code for eval() * * @param string Template * * @return string */ function compile_template($template, &$errors = array()) { $orig_template = $template; $template = preg_replace('#[\\x00-\\x08\\x0B\\x0C\\x0E-\\x1F]#', '', $template); $new_syntax = (strpos($template, '<vb:') !== false OR strpos($template, '{vb:') !== false); $old_syntax = (strpos($template, '<if') !== false OR strpos($template, '<phrase') !== false); $maybe_old_syntax = preg_match('/(^|[^{])\$[a-z0-9_]+\[?/si', $template); if (!$new_syntax AND ($old_syntax OR $maybe_old_syntax)) { $template = addslashes($template); $template = process_template_conditionals($template); $template = process_template_phrases('phrase', $template, 'parse_phrase_tag'); $template = process_seo_urls($template); if (!function_exists('replace_template_variables') OR !function_exists('validate_string_for_interpolation')) { require_once(DIR . '/includes/functions_misc.php'); } //only check the old style syntax, the new style doesn't use string interpolation and isn't affected //by this exploit. The new syntax doesn't 100% pass this check. if(!validate_string_for_interpolation($template)) { global $vbphrase; echo "<p> </p><p> </p>"; print_form_header('', '', 0, 1, '', '65%'); print_table_header($vbphrase['vbulletin_message']); print_description_row($vbphrase['template_text_not_safe']); print_table_footer(2, construct_button_code($vbphrase['go_back'], 'javascript:history.back(1)')); print_cp_footer(); exit; } $template = replace_template_variables($template, false); $template = str_replace('\\\\$', '\\$', $template); if (function_exists('token_get_all')) { $tokens = @token_get_all('<?php $var = "' . $template . '"; ?>'); foreach ($tokens AS $token) { if (is_array($token)) { switch ($token[0]) { case T_INCLUDE: case T_INCLUDE_ONCE: case T_REQUIRE: case T_REQUIRE_ONCE: { global $vbphrase; echo "<p> </p><p> </p>"; print_form_header('', '', 0, 1, '', '65%'); print_table_header($vbphrase['vbulletin_message']); print_description_row($vbphrase['file_inclusion_not_permitted']); print_table_footer(2, construct_button_code($vbphrase['go_back'], 'javascript:history.back(1)')); print_cp_footer(); exit; } } } } } } else { require_once(DIR . '/includes/class_template_parser.php'); $parser = new vB_TemplateParser($orig_template); try { $parser->validate($errors); } catch (vB_Exception_TemplateFatalError $e) { global $vbphrase; echo "<p> </p><p> </p>"; print_form_header('', '', 0, 1, '', '65%'); print_table_header($vbphrase['vbulletin_message']); print_description_row($vbphrase[$e->getMessage()]); print_table_footer(2, construct_button_code($vbphrase['go_back'], 'javascript:history.back(1)')); print_cp_footer(); exit; } $template = $parser->compile(); // TODO: Reimplement these - if done, $session[], $bbuserinfo[], $vboptions will parse in the template without using {vb:raw, which isn't what we // necessarily want to happen /* if (!function_exists('replace_template_variables')) { require_once(DIR . '/includes/functions_misc.php'); } $template = replace_template_variables($template, false); */ } if (function_exists('verify_demo_template')) { verify_demo_template($template); } ($hook = vBulletinHook::fetch_hook('template_compile')) ? eval($hook) : false; return $template; }
/** * Compiles a text node in the vB_TemplateParser format (evalable). * * @param object DOM Node of type text * @param object vB_TemplateParser object * * @return string Evalable text */ public static function compile(vB_DomNode $main_node, vB_TemplateParser $parser) { return $parser->_escape_string($main_node->value); }
public static function compile(vB_DomNode $main_node, vB_TemplateParser $parser) { $argument_list = array(); foreach ($main_node->attributes AS $name => $attribute) { if (strval(intval($name)) == $name) { $argument_list["$name"] = $attribute; } } ksort($argument_list, SORT_NUMERIC); $arguments = ''; for ($i = 1; isset($argument_list["$i"]); $i++) { $arguments .= ', "' . $argument_list["$i"] . '"'; } $children = $parser->_parse_nodes($main_node->childNodes()); return 'vB_Template_Runtime::parsePhrase("' . "$children\"$arguments" . ')'; }
public static function compile(vB_Node $main_node, vB_TemplateParser $parser) { $argument_list = $main_node->attributes; $arguments = array(); foreach ($argument_list AS $attribute) { if ($attribute instanceof vB_CurlyNode) { $attribute = "'" . $parser->_default_node_handler($attribute) . "'"; } else { $attribute = "'$attribute'"; } $arguments[] = $attribute; } $arguments = implode(".", $arguments); return 'vB_Template_Runtime::runMaths(' . $arguments . ')'; }
public static function compile(vB_Xml_Node $main_node, vB_TemplateParser $parser) { $attribute = $main_node->attributes[0]; if ($attribute instanceof vB_CurlyNode) { $url = "'" . $parser->_default_node_handler($attribute) . "'"; } else { $url = "'" . $attribute . "'"; } // TODO: Is there a better way of doing this? // I don't want to stop the concatenation cause here we don't really know the output_var value return '\'\'; vB_Template_Runtime::doRedirect(' . $url . '); $final_rendered .= \'\''; }
/** * Compile a template. * * @param string $template_un The uncompiled content of a template. */ public function compile($template, $forcesaveonerror) { // @todo // Incorrect hack warning!!! // The legacy code in class_template_parser.php needs this to be set // but it apparrently does not actually need to be an instance of the // legacy db class for purposes of compiling a template. if (empty($GLOBALS['vbulletin']->db)) { $GLOBALS['vbulletin']->db = false; } require_once DIR . '/includes/class_template_parser.php'; require_once DIR . '/includes/adminfunctions_template.php'; // Required for check_template_errors() $parser = new vB_TemplateParser($template); try { $parser->validate($errors); } catch (vB_Exception_TemplateFatalError $e) { throw new vB_Exception_Api($e->getMessage()); } $template = $parser->compile(); // This is a comment from vB4 moved here. Need to figure out what replace_template_variables // is supposed to do. // TODO: Reimplement these - if done, $session[], $bbuserinfo[], $vboptions // will parse in the template without using {vb:raw, which isn't what we // necessarily want to happen /* if (!function_exists('replace_template_variables')) { require_once(DIR . '/includes/functions_misc.php'); } $template = replace_template_variables($template, false); */ if (function_exists('verify_demo_template')) { verify_demo_template($template); } // Legacy Hook 'template_compile' Removed // if (!$forcesaveonerror and !empty($errors)) { throw new vB_Exception_Api('template_compile_error', array($errors)); } //extra set of error checking. This can be skipped in many situations. if (!$forcesaveonerror) { $errors = check_template_errors($template); if (!empty($errors)) { $vb5_config =& vB::getConfig(); if (!is_array($errors) and $vb5_config['Misc']['debug']) { // show compiled template code with line numbers to debug the problem $errors .= '<h4>Compiled Template Code:</h4><div style="height:200px; overflow:auto; border:1px solid silver; font-style:normal; font-family:Courier New;"><ol><li>' . implode('</li><li>', explode("\n", htmlspecialchars($template))) . '</li></ol></div>'; } throw new vB_Exception_Api('template_eval_error', array($errors)); } } return $template; }