function construct_nav_option($title, $url) { // creates an <option> or <a href for the left-panel of index.php // (depending on value of $cpnavjs) // NOTE: '&' . vB::getCurrentSession()->get('sessionurl') will be AUTOMATICALLY added to the URL - do not add to your link! global $options; static $sessionlink = ''; $url_query = vB_String::parseUrl($url, PHP_URL_QUERY); if (!isset($options)) { $options = array(); if (vB::getCurrentSession()->get('sessionurl') == '') { $sessionlink = ''; } else { $sessionlink = "s=" . vB::getCurrentSession()->get('sessionhash'); } } $url .= empty($url_query) ? '?' : '&'; $options[] = "\t\t<a class=\"navlink\" href=\"{$url}{$sessionlink}\">{$title}</a>\n"; }
function admin_login_error($error, array $args = array()) { global $vbulletin; if ($vbulletin->GPC['logintype'] === 'cplogin' or $vbulletin->GPC['logintype'] === 'modcplogin') { require_once DIR . '/includes/adminfunctions.php'; $url = unhtmlspecialchars($vbulletin->url); $urlarr = vB_String::parseUrl($url); $urlquery = $urlarr['query']; $oldargs = array(); if ($urlquery) { parse_str($urlquery, $oldargs); } $args = array_merge($oldargs, $args); unset($args['loginerror']); $argstr = http_build_query($args); $url = "/{$urlarr['path']}?loginerror=" . $error; if ($argstr) { $url .= '&' . $argstr; } print_cp_redirect($url); } }
/** * Performs fetching of the file if possible * * @return integer Returns one of two constants, VURL_NEXT or VURL_HANDLED */ function exec() { $urlinfo = @vB_String::parseUrl($this->vurl->options[VURL_URL]); // VBV-11823, only allow http/https schemes if (!isset($urlinfo['scheme']) or !in_array(strtolower($urlinfo['scheme']), array('http', 'https'))) { return VURL_NEXT; } // VBV-11823, do not allow localhost and 127.0.0.0/8 range by default if (!isset($urlinfo['host']) or preg_match('#localhost|127\\.(\\d)+\\.(\\d)+\\.(\\d)+#i', $urlinfo['host'])) { return VURL_NEXT; } if (empty($urlinfo['port'])) { if ($urlinfo['scheme'] == 'https') { $urlinfo['port'] = 443; } else { $urlinfo['port'] = 80; } } // VBV-11823, restrict destination ports to 80 and 443 by default // allow the admin to override the allowed ports in config.php (in case they have a proxy server they need to go to). $config = vB::getConfig(); $allowedPorts = isset($config['Misc']['uploadallowedports']) ? $config['Misc']['uploadallowedports'] : array(); if (!is_array($allowedPorts)) { $allowedPorts = array(80, 443, $allowedPorts); } else { $allowedPorts = array_merge(array(80, 443), $allowedPorts); } if (!in_array($urlinfo['port'], $allowedPorts)) { return VURL_NEXT; } if (!function_exists('curl_init') or ($this->ch = curl_init()) === false) { return VURL_NEXT; } if ($urlinfo['scheme'] == 'https') { // curl_version crashes if no zlib support in cURL (php <= 5.2.5) $curlinfo = curl_version(); if (empty($curlinfo['ssl_version'])) { curl_close($this->ch); return VURL_NEXT; } } curl_setopt($this->ch, CURLOPT_URL, $this->vurl->options[VURL_URL]); curl_setopt($this->ch, CURLOPT_TIMEOUT, $this->vurl->options[VURL_TIMEOUT]); if (!empty($this->vurl->options[VURL_CUSTOMREQUEST])) { curl_setopt($this->ch, CURLOPT_CUSTOMREQUEST, $this->vurl->options[VURL_CUSTOMREQUEST]); } else { if ($this->vurl->bitoptions & VURL_POST) { curl_setopt($this->ch, CURLOPT_POST, 1); curl_setopt($this->ch, CURLOPT_POSTFIELDS, $this->vurl->options[VURL_POSTFIELDS]); } else { curl_setopt($this->ch, CURLOPT_POST, 0); } } curl_setopt($this->ch, CURLOPT_HEADER, $this->vurl->bitoptions & VURL_HEADER ? 1 : 0); curl_setopt($this->ch, CURLOPT_HTTPHEADER, $this->vurl->options[VURL_HTTPHEADER]); curl_setopt($this->ch, CURLOPT_RETURNTRANSFER, $this->vurl->bitoptions & VURL_RETURNTRANSFER ? 1 : 0); if ($this->vurl->bitoptions & VURL_NOBODY) { curl_setopt($this->ch, CURLOPT_NOBODY, 1); } if ($this->vurl->bitoptions & VURL_FOLLOWLOCATION) { if (@curl_setopt($this->ch, CURLOPT_FOLLOWLOCATION, 1) === false) { curl_close($this->ch); return VURL_NEXT; } curl_setopt($this->ch, CURLOPT_MAXREDIRS, $this->vurl->options[VURL_MAXREDIRS]); } else { curl_setopt($this->ch, CURLOPT_FOLLOWLOCATION, 0); } if ($this->vurl->options[VURL_ENCODING]) { @curl_setopt($this->ch, CURLOPT_ENCODING, $this->vurl->options[VURL_ENCODING]); // this will work on versions of cURL after 7.10, though was broken on PHP 4.3.6/Win32 } $this->reset(); curl_setopt($this->ch, CURLOPT_WRITEFUNCTION, array(&$this, 'curl_callback_response')); curl_setopt($this->ch, CURLOPT_HEADERFUNCTION, array(&$this, 'curl_callback_header')); if (!($this->vurl->bitoptions & VURL_VALIDSSLONLY)) { curl_setopt($this->ch, CURLOPT_SSL_VERIFYPEER, 0); curl_setopt($this->ch, CURLOPT_SSL_VERIFYHOST, 0); } $result = curl_exec($this->ch); if ($urlinfo['scheme'] == 'https' and $result === false and curl_errno($this->ch) == '60') { curl_setopt($this->ch, CURLOPT_CAINFO, DIR . '/includes/paymentapi/ca-bundle.crt'); $result = curl_exec($this->ch); } curl_close($this->ch); if ($this->fp) { fclose($this->fp); $this->fp = null; } if ($result !== false or !$this->vurl->options[VURL_DIEONMAXSIZE] and $this->max_limit_reached) { return VURL_HANDLED; } return VURL_NEXT; }
$phrasegroups = array('cphome', 'cpuser'); $specialtemplates = array(); global $DEVDEBUG, $cpnavjs; // ########################## REQUIRE BACK-END ############################ require_once dirname(__FILE__) . '/global.php'; // ############################# LOG ACTION ############################### if (empty($_REQUEST['do'])) { log_admin_action(); } // ######################################################################## // ######################### START MAIN SCRIPT ############################ // ######################################################################## $vbulletin->input->clean_array_gpc('r', array('redirect' => vB_Cleaner::TYPE_NOHTML)); # Not sure where this comes from if (!empty($vbulletin->GPC['redirect'])) { $redirect = vB_String::parseUrl($vbulletin->GPC['redirect']); $pathinfo = pathinfo($redirect['path']); $file = $pathinfo['filename']; parse_str($redirect['query'], $args); print_stop_message2('redirecting_please_wait', $file, $args); } // ############################################################################# // ############################### LOG OUT OF CP ############################### // ############################################################################# if ($_REQUEST['do'] == 'cplogout') { vbsetcookie('cpsession', '', false, true, true); $vbulletin->db->query_write("DELETE FROM " . TABLE_PREFIX . "cpsession WHERE userid = " . $vbulletin->userinfo['userid'] . " AND hash = '" . $vbulletin->db->escape_string($vbulletin->GPC[COOKIE_PREFIX . 'cpsession']) . "'"); $sessionurl_js = vB::getCurrentSession()->get('sessionurl_js'); if (!empty($sessionurl_js)) { exec_header_redirect('index.php?' . $sessionurl_js); } else {
/** * Get information for a page * @param int $pageid * @param array $routeData -- The needed to render this pages route. Will vary by page * * @return array * pageid int * parentid int -- the parent page (currently unused) * pagetemplateid int * title string * metadescription string -- the metadescription to display when page is rendered as html * routeid int -- route associated with this page * moderatorid int -- need to determine * displayorder int -- the order to display page when displaying lists of pages * pagetype string -- default or custom depending of if this is a page we install with the system * product string -- product the page belongs to 'vbulletin' for pages created by the system and via the admincp * guid string -- globally unique identifier * screenlayoutid int -- layout for the page * screenlayouttemplate string -- name of the layout template * templatetitle string -- need to determine * ishomepage boolean -- is this the homepage * makehomepagecheckattr string -- DEPRECATED 'checked=checked' if this is the homepage * isgeneric boolean -- DEPRECATED true if this is of type default * urlprefix string -- prefix for the route * url string -- url generated from the route -- will be relative to the frontend base * urlscheme string -- DEPRECATED -- will be blank * urlhostname string -- DEPRECATED -- will be blank * noindex boolean -- should this page be indexed. * nofollow boolean -- should this page be followed. */ public function fetchPageById($pageid, $routeData = array()) { $pageid = intval($pageid); $db = vB::getDbAssertor(); $conditions = array('pageid' => $pageid); //$page = $db->getRow('fetch_page_pagetemplate_screenlayout', $conditions); $page = $db->assertQuery('fetch_page_pagetemplate_screenlayout', $conditions); $page = $page->current(); if ($page) { // Fetch phrases $guidforphrase = vB_Library::instance('phrase')->cleanGuidForPhrase($page['guid']); $phrases = vB_Api::instanceInternal('phrase')->fetch(array('page_' . $guidforphrase . '_title', 'page_' . $guidforphrase . '_metadesc')); $page['title'] = !empty($phrases['page_' . $guidforphrase . '_title']) ? $phrases['page_' . $guidforphrase . '_title'] : $page['title']; $page['metadescription'] = !empty($phrases['page_' . $guidforphrase . '_metadesc']) ? $phrases['page_' . $guidforphrase . '_metadesc'] : $page['metadescription']; // check if this is currently the homepage $route = vB5_Route::getHomePageRouteInfo(); if ($route and $route['contentid'] == $page['pageid']) { $page['ishomepage'] = true; //todo shouldn't use html in the API. $page['makehomepagecheckattr'] = ' checked="checked"'; } else { $page['ishomepage'] = false; $page['makehomepagecheckattr'] = ''; } $page['isgeneric'] = $page['pagetype'] == vB_Page::TYPE_DEFAULT; // get url scheme, hostname and path $route = vB5_Route::getRoute(intval($page['routeid']), $routeData); if ($route) { $page['urlprefix'] = $route->getCanonicalPrefix(); $page['url'] = $route->getCanonicalUrl(); $parsed = vB_String::parseUrl($page['url']); $page['urlscheme'] = isset($parsed['scheme']) ? $parsed['scheme'] : ''; $page['urlhostname'] = isset($parsed['host']) ? $parsed['host'] : ''; $page['urlpath'] = base64_encode($parsed['path']); $page['noindex'] = false; $page['nofollow'] = false; $arguments = $route->getArguments(); if (!empty($arguments['noindex'])) { $page['noindex'] = $arguments['noindex']; } if (!empty($arguments['nofollow'])) { $page['nofollow'] = $arguments['nofollow']; } } } return $page; }
/** * Removes bad $_GET variables that may be set by apache when using mod_rewrite. * @see https://issues.apache.org/bugzilla/show_bug.cgi?id=34602 * * When using mod_rewrite, the fragment is urldecoded before the QS is appended * to the rewritten url. If the fragment contains & then $_GET will be * corrupted. * * This method checks the correct uri and resolves the correct values for $_GET. * * @param string $fragment - The decoded fragment */ public function fix_query_string($uri) { static $fixed = false; if ($fixed) { return; } $fixed = true; // Probably also need to return if this is not apache if (FRIENDLY_URL_REWRITE != FRIENDLY_URL) { return; } $uri = vB_String::parseUrl($uri); $_SERVER['QUERY_STRING'] = $uri['query']; $_REQUEST = array_diff($_REQUEST, array_diff($_GET, $_POST, $_COOKIE)); $_GET = array(); if ($_SERVER['QUERY_STRING']) { // Get the query string parse_str($_SERVER['QUERY_STRING'], $query); $_GET = array_merge($_GET, $query); $_REQUEST = array_merge($_REQUEST, $_GET); } $this->registry->input->convert_shortvars($_REQUEST); $this->registry->input->convert_shortvars($_GET); }
/** * Performs fetching of the file if possible * * @return integer Returns one of two constants, VURL_NEXT or VURL_HANDLED */ public function exec() { $urlinfo = @vB_String::parseUrl($this->vurl->options[VURL_URL]); if (!$this->validateUrl($urlinfo)) { return VURL_NEXT; } if (!function_exists('curl_init') or ($this->ch = curl_init()) === false) { return VURL_NEXT; } curl_setopt($this->ch, CURLOPT_TIMEOUT, $this->vurl->options[VURL_TIMEOUT]); if (!empty($this->vurl->options[VURL_CUSTOMREQUEST])) { curl_setopt($this->ch, CURLOPT_CUSTOMREQUEST, $this->vurl->options[VURL_CUSTOMREQUEST]); } else { if ($this->vurl->bitoptions & VURL_POST) { curl_setopt($this->ch, CURLOPT_POST, 1); curl_setopt($this->ch, CURLOPT_POSTFIELDS, $this->vurl->options[VURL_POSTFIELDS]); } else { curl_setopt($this->ch, CURLOPT_POST, 0); } } curl_setopt($this->ch, CURLOPT_HEADER, $this->vurl->bitoptions & VURL_HEADER ? 1 : 0); curl_setopt($this->ch, CURLOPT_HTTPHEADER, $this->vurl->options[VURL_HTTPHEADER]); curl_setopt($this->ch, CURLOPT_RETURNTRANSFER, $this->vurl->bitoptions & VURL_RETURNTRANSFER ? 1 : 0); if ($this->vurl->bitoptions & VURL_NOBODY) { curl_setopt($this->ch, CURLOPT_NOBODY, 1); } //if we aren't following the location or we're using the built in curl method of following //redirects we only want to try to load the url once. Otherwise we'll want to loop internally //to handle redirects up to the limit. $redirect_tries = 1; if ($this->vurl->bitoptions & VURL_FOLLOWLOCATION) { // disabled in safe_mode/open_basedir in PHP 5.1.6/4.4.4 // Added method to force "safe mode" behavior without setting it primarily for unit testing if ($this->vurl->bitoptions & VURL_NOCURLFOLLOW or @curl_setopt($this->ch, CURLOPT_FOLLOWLOCATION, 1) === false) { $redirect_tries = $this->vurl->options[VURL_MAXREDIRS]; } else { curl_setopt($this->ch, CURLOPT_MAXREDIRS, $this->vurl->options[VURL_MAXREDIRS]); } } else { curl_setopt($this->ch, CURLOPT_FOLLOWLOCATION, 0); } if ($this->vurl->options[VURL_ENCODING]) { // this will work on versions of cURL after 7.10, though was broken on PHP 4.3.6/Win32 @curl_setopt($this->ch, CURLOPT_ENCODING, $this->vurl->options[VURL_ENCODING]); } curl_setopt($this->ch, CURLOPT_WRITEFUNCTION, array(&$this, 'curl_callback_response')); curl_setopt($this->ch, CURLOPT_HEADERFUNCTION, array(&$this, 'curl_callback_header')); if (!($this->vurl->bitoptions & VURL_VALIDSSLONLY)) { curl_setopt($this->ch, CURLOPT_SSL_VERIFYPEER, 0); curl_setopt($this->ch, CURLOPT_SSL_VERIFYHOST, 0); } $url = $this->vurl->options[VURL_URL]; $redirectCodes = array(301, 302); for ($i = $redirect_tries; $i > 0; $i--) { $isHttps = $urlinfo['scheme'] == 'https'; if ($isHttps) { // curl_version crashes if no zlib support in cURL (php <= 5.2.5) $curlinfo = curl_version(); if (empty($curlinfo['ssl_version'])) { curl_close($this->ch); return VURL_NEXT; } } $result = $this->execCurl($url, $isHttps); //if we don't have another iteration of the loop to go, skip the effort here. if ($i > 1 and in_array(curl_getinfo($this->ch, CURLINFO_HTTP_CODE), $redirectCodes)) { $url = curl_getinfo($this->ch, CURLINFO_REDIRECT_URL); $urlinfo = @vB_String::parseUrl($url); if (!$this->validateUrl($urlinfo)) { $this->closeTempFile(); return VURL_NEXT; } } } //if we are following redirects and still have a redirect code, its because we hit our limit without finding a real page //we want the fallback code to mimic the behavior of curl in this case if ($this->vurl->bitoptions & VURL_FOLLOWLOCATION && in_array(curl_getinfo($this->ch, CURLINFO_HTTP_CODE), $redirectCodes)) { $this->closeTempFile(); return VURL_NEXT; } //close the connection and clean up the file. curl_close($this->ch); $this->closeTempFile(); if ($result !== false or !$this->vurl->options[VURL_DIEONMAXSIZE] and $this->max_limit_reached) { return VURL_HANDLED; } return VURL_NEXT; }
} if ($vb5_config['Misc']['debug'] and vB::getUserContext()->hasAdminPermission('canadmintemplates')) { echo construct_link_code($vbphrase['rebuild_all_styles'], "template.php?" . vB::getCurrentSession()->get('sessionurl') . "do=rebuild&goto=template.php?" . vB::getCurrentSession()->get('sessionurl')); } echo "</p>\n"; } // ############################################################################# // rebuilds all parent lists and id cache lists if ($_REQUEST['do'] == 'rebuild') { if (!vB::getUserContext()->hasAdminPermission('canadmintemplates')) { print_cp_no_permission(); } $vbulletin->input->clean_array_gpc('r', array('renumber' => vB_Cleaner::TYPE_INT, 'install' => vB_Cleaner::TYPE_INT, 'goto' => vB_Cleaner::TYPE_STR)); echo "<p> </p>"; vB_Library::instance('style')->buildAllStyles($vbulletin->GPC['renumber'], $vbulletin->GPC['install']); $execurl = vB_String::parseUrl($vbulletin->GPC['goto']); $pathinfo = pathinfo($execurl['path']); $file = $pathinfo['basename']; parse_str($execurl['query'], $args); print_cp_redirect2($file, $args); } // ############################################################################# // hex convertor if ($_REQUEST['do'] == 'colorconverter') { $vbulletin->input->clean_array_gpc('r', array('hex' => vB_Cleaner::TYPE_NOHTML, 'rgb' => vB_Cleaner::TYPE_NOHTML, 'hexdec' => vB_Cleaner::TYPE_STR, 'dechex' => vB_Cleaner::TYPE_STR)); if ($vbulletin->GPC['dechex']) { $vbulletin->GPC['rgb'] = preg_split('#\\s*,\\s*#si', $vbulletin->GPC['rgb'], -1, PREG_SPLIT_NO_EMPTY); $vbulletin->GPC['hex'] = '#'; foreach ($vbulletin->GPC['rgb'] as $i => $value) { $vbulletin->GPC['hex'] .= strtoupper(str_pad(dechex($value), 2, '0', STR_PAD_LEFT)); }
/** * Handles a [url] tag. Creates a link to another web page. * * @param string If tag has option, the displayable name. Else, the URL. * @param string If tag has option, the URL. * * @return string HTML representation of the tag. */ function handle_bbcode_url($text, $link) { $rightlink = trim($link); if (empty($rightlink)) { // no option -- use param $rightlink = trim($text); } $rightlink = str_replace(array('`', '"', "'", '['), array('`', '"', ''', '['), $this->strip_smilies($rightlink)); // remove double spaces -- fixes issues with wordwrap $rightlink = str_replace(' ', '', $rightlink); if (!preg_match('#^[a-z0-9]+(?<!about|javascript|vbscript|data):#si', $rightlink)) { $rightlink = "http://{$rightlink}"; } if (!trim($link) or str_replace(' ', '', $text) == $rightlink) { $tmp = unhtmlspecialchars($rightlink); if (vbstrlen($tmp) > 55 and $this->is_wysiwyg() == false) { $text = htmlspecialchars_uni(vbchop($tmp, 36) . '...' . substr($tmp, -14)); } else { // under the 55 chars length, don't wordwrap this $text = str_replace(' ', '', $text); } } static $current_url, $current_host, $allowed, $friendlyurls = array(); if (!isset($current_url)) { $current_url = @vB_String::parseUrl($this->registry->options['bburl']); } $is_external = $this->registry->options['url_nofollow']; if ($this->registry->options['url_nofollow']) { if (!isset($current_host)) { $current_host = preg_replace('#:(\\d)+$#', '', VB_HTTP_HOST); $allowed = preg_split('#\\s+#', $this->registry->options['url_nofollow_whitelist'], -1, PREG_SPLIT_NO_EMPTY); $allowed[] = preg_replace('#^www\\.#i', '', $current_host); $allowed[] = preg_replace('#^www\\.#i', '', $current_url['host']); } $target_url = preg_replace('#^([a-z0-9]+:(//)?)#', '', $rightlink); foreach ($allowed as $host) { if (stripos($target_url, $host) !== false) { $is_external = false; } } } // API need to convert link to vb:action/param1=val1/param2=val2... if (defined('VB_API') and VB_API === true) { $current_link = @vB_String::parseUrl($rightlink); if ($current_link !== false) { $current_link['host'] = strtolower($current_link['host']); $current_url['host'] = strtolower($current_url['host']); if (($current_link['host'] == $current_url['host'] or 'www.' . $current_link['host'] == $current_url['host'] or $current_link['host'] == 'www.' . $current_url['host']) and (!$current_url['path'] or stripos($current_link['path'], $current_url['path']) !== false)) { // This is a vB link. if ($current_link['path'] == $current_url['path'] or $current_link['path'] . '/' == $current_url['path'] or $current_link['path'] == $current_url['path'] . '/') { $rightlink = 'vb:index'; } else { // Get a list of declared friendlyurl classes if (!$friendlyurls) { require_once DIR . '/includes/class_friendly_url.php'; $classes = get_declared_classes(); foreach ($classes as $classname) { if (strpos($classname, 'vB_Friendly_Url_') !== false) { $reflect = new ReflectionClass($classname); $props = $reflect->getdefaultProperties(); if ($classname == 'vB_Friendly_Url_vBCms') { $props['idvar'] = $props['ignorelist'][] = $this->registry->options['route_requestvar']; $props['script'] = 'content.php'; $props['rewrite_segment'] = 'content'; } if ($props['idvar']) { $friendlyurls[$classname]['idvar'] = $props['idvar']; $friendlyurls[$classname]['idkey'] = $props['idkey']; $friendlyurls[$classname]['titlekey'] = $props['titlekey']; $friendlyurls[$classname]['ignorelist'] = $props['ignorelist']; $friendlyurls[$classname]['script'] = $props['script']; $friendlyurls[$classname]['rewrite_segment'] = $props['rewrite_segment']; } } $friendlyurls['vB_Friendly_Url_vBCms']['idvar'] = $this->registry->options['route_requestvar']; $friendlyurls['vB_Friendly_Url_vBCms']['ignorelist'][] = $this->registry->options['route_requestvar']; $friendlyurls['vB_Friendly_Url_vBCms']['script'] = 'content.php'; $friendlyurls['vB_Friendly_Url_vBCms']['rewrite_segment'] = 'content'; $friendlyurls['vB_Friendly_Url_vBCms2']['idvar'] = $this->registry->options['route_requestvar']; $friendlyurls['vB_Friendly_Url_vBCms2']['ignorelist'][] = $this->registry->options['route_requestvar']; $friendlyurls['vB_Friendly_Url_vBCms2']['script'] = 'list.php'; $friendlyurls['vB_Friendly_Url_vBCms2']['rewrite_segment'] = 'list'; } } /* * FRIENDLY_URL_OFF * showthread.php?t=1234&p=2 * * FRIENDLY_URL_BASIC * showthread.php?1234-Thread-Title/page2&pp=2 * * FRIENDLY_URL_ADVANCED * showthread.php/1234-Thread-Title/page2?pp=2 * * FRIENDLY_URL_REWRITE * /threads/1234-Thread-Title/page2?pp=2 */ // Try to get the script name // FRIENDLY_URL_OFF, FRIENDLY_URL_BASIC or FRIENDLY_URL_ADVANCED $scriptname = ''; if (preg_match('#([^/]+)\\.php#si', $current_link['path'], $matches)) { $scriptname = $matches[1]; } else { // Build a list of rewrite_segments foreach ($friendlyurls as $v) { $rewritesegments .= "|{$v['rewrite_segment']}"; } $pat = '#/(' . substr($rewritesegments, 1) . ')/#si'; if (preg_match($pat, $current_link['path'], $matches)) { $uri = $matches[1]; } // Decide the type of the url $urltype = null; foreach ($friendlyurls as $v) { if ($v['rewrite_segment'] == $uri) { $urltype = $v; break; } } // Convert $uri back to correct scriptname $scriptname = str_replace('.php', '', $urltype['script']); } if ($scriptname) { $oldrightlink = $rightlink; $rightlink = "vb:{$scriptname}"; // Check if it's FRIENDLY_URL_BASIC or FRIENDLY_URL_ADVANCED if (preg_match('#(?:\\?|/)(\\d+).*?(?:/page(\\d+)|$)#si', $oldrightlink, $matches)) { // Decide the type of the url $urltype = null; foreach ($friendlyurls as $v) { if ($v['script'] == $scriptname . '.php') { $urltype = $v; break; } } if ($urltype) { $rightlink .= "/{$urltype['idvar']}={$matches['1']}"; } if ($matches[2]) { $rightlink .= "/page=2"; } } if (preg_match_all('#([a-z0-9_]+)=([a-z0-9_\\+]+)#si', $current_link['query'], $matches)) { foreach ($matches[0] as $match) { $rightlink .= "/{$match}"; } } } } } } } // standard URL hyperlink return "<a href=\"{$rightlink}\" target=\"_blank\"" . ($is_external ? ' rel="nofollow"' : '') . ">{$text}</a>"; }
/** * Function to convert relative URL to absolute given a base URL * From http://bsd-noobz.com/blog/php-script-for-converting-relative-to-absolute-url * * @param string the relative URL * @param string the base URL * * @return string the absolute URL */ protected function rel2abs($rel, $base) { if (vB_String::parseUrl($rel, PHP_URL_SCHEME) != '') { return $rel; } else { if ($rel[0] == '#' || $rel[0] == '?') { return $base . $rel; } } $parsed_base = vB_String::parseUrl($base); $abs = (($rel[0] == '/' or empty($parsed_base['path'])) ? '' : preg_replace('#/[^/]*$#', '', $parsed_base['path'])) . "/{$rel}"; $re = array('#(/\\.?/)#', '#/(?!\\.\\.)[^/]+/\\.\\./#'); for ($n = 1; $n > 0; $abs = preg_replace($re, '/', $abs, -1, $n)) { } return $parsed_base['scheme'] . '://' . $parsed_base['host'] . str_replace('../', '', $abs); }
protected function resolveRequestUrl() { // Ports which will not be appended to the URL $ignore_ports = array(80, 443); $config = vB::getConfig(); $backend_ports = @$config['Misc']['backendports']; if (!empty($backend_ports)) { $ignore_ports = array_merge($ignore_ports, $backend_ports); } // Numerical port this request came from, may be a backend port $rawport = 80; // Will contain the port portion of the built URL, default empty $port = ''; if (!empty($_SERVER['SERVER_PORT'])) { $rawport = intval($_SERVER['SERVER_PORT']); $port = in_array($rawport, $ignore_ports) ? '' : ':' . $rawport; } // resolve the request scheme $scheme = ($rawport == 443 or !empty($_SERVER['HTTPS']) and $_SERVER['HTTPS'] !== 'off') ? 'https://' : 'http://'; $host = $this->fetchServerValue('HTTP_HOST'); $name = $this->fetchServerValue('SERVER_NAME'); // If host exists use it, otherwise fallback to servername. $host = !empty($host) ? $host : $name; // resolve the query $query = ($query = $this->fetchServerValue('QUERY_STRING')) ? '?' . $query : ''; // resolve the path and query if (!($scriptpath = $this->fetchServerValue('REQUEST_URI'))) { if (!($scriptpath = $this->fetchServerValue('UNENCODED_URL'))) { $scriptpath = $this->fetchServerValue('HTTP_X_REWRITE_URL'); } } if ($scriptpath) { // already have the query if ($scriptpath) { $query = ''; } } else { // server hasn't provided a URI, try to resolve one if (!($scriptpath = $this->fetchServerValue('PATH_INFO'))) { if (!($scriptpath = $this->fetchServerValue('REDIRECT_URL'))) { if (!($scriptpath = $this->fetchServerValue('URL'))) { if (!($scriptpath = $this->fetchServerValue('PHP_SELF'))) { $scriptpath = $this->fetchServerValue('SCRIPT_NAME'); } } } } } // build the URL $url = $scheme . $host . '/' . ltrim($scriptpath, '/\\') . $query; // store a literal version $vbUrl = $url; if (!defined('VB_URL')) { define('VB_URL', $vbUrl); } $vbUrlRelativePath = ''; // Set URL info $url_info = @vB_String::parseUrl($vbUrl); $url_info['path'] = '/' . ltrim($url_info['path'], '/\\'); $url_info['query_raw'] = isset($url_info['query']) ? $url_info['query'] : ''; $url_info['query'] = self::stripSessionhash($url_info['query_raw']); $url_info['query'] = trim($url_info['query'], '?&') ? $url_info['query'] : ''; $url_info['scheme'] = substr($scheme, 0, strlen($scheme) - 3); /* values seen in the wild: CGI+suexec: SCRIPT_NAME: /vb4/admincp/index.php ORIG_SCRIPT_NAME: /cgi-sys/php53-fcgi-starter.fcgi CGI #1: SCRIPT_NAME: /index.php ORIG_SCRIPT_NAME: /search/foo CGI #2: SCRIPT_NAME: /index.php/search/foo ORIG_SCRIPT_NAME: /index.php */ if (substr(PHP_SAPI, -3) == 'cgi' and (isset($_SERVER['ORIG_SCRIPT_NAME']) and !empty($_SERVER['ORIG_SCRIPT_NAME']))) { if (substr($_SERVER['SCRIPT_NAME'], 0, strlen($_SERVER['ORIG_SCRIPT_NAME'])) == $_SERVER['ORIG_SCRIPT_NAME']) { // cgi #2 above $url_info['script'] = $_SERVER['ORIG_SCRIPT_NAME']; } else { // cgi #1 and CGI+suexec above $url_info['script'] = $_SERVER['SCRIPT_NAME']; } } else { $url_info['script'] = (isset($_SERVER['ORIG_SCRIPT_NAME']) and !empty($_SERVER['ORIG_SCRIPT_NAME'])) ? $_SERVER['ORIG_SCRIPT_NAME'] : $_SERVER['SCRIPT_NAME']; } $url_info['script'] = '/' . ltrim($url_info['script'], '/\\'); // define constants $this->vBUrlScheme = $url_info['scheme']; $vBUrlScriptPath = rtrim(dirname($url_info['script']), '/\\') . '/'; $this->vBUrlPath = urldecode($url_info['path']); if (!defined('VB_URL_PATH')) { define('VB_URL_PATH', $this->vBUrlPath); } $this->vBUrlQuery = $url_info['query'] ? $url_info['query'] : ''; if (!defined('VB_URL_QUERY')) { define('VB_URL_QUERY', $this->vBUrlQuery); } $this->vBUrlQueryRaw = $url_info['query_raw']; if (!defined('VB_URL_QUERY_RAW')) { define('VB_URL_QUERY_RAW', $this->vBUrlQueryRaw); } $cleaner = vB::get_cleaner(); $this->vBUrlClean = $cleaner->xssClean(self::stripSessionhash($vbUrl)); if (!defined('VB_URL_CLEAN')) { define('VB_URL_CLEAN', $this->vBUrlClean); } $this->vBUrlWebroot = $cleaner->xssClean($this->vBUrlScheme . '://' . $url_info['host'] . $port); $this->vBUrlBasePath = $cleaner->xssClean($this->vBUrlScheme . '://' . $url_info['host'] . $port . $vBUrlScriptPath . $vbUrlRelativePath); if (!defined('VB_URL_BASE_PATH')) { define('VB_URL_BASE_PATH', $this->vBUrlBasePath); } $this->scriptPath = $cleaner->xssClean($this->addQuery($this->vBUrlPath)); // legacy constants if (!defined('SCRIPT')) { define('SCRIPT', $_SERVER['SCRIPT_NAME']); } if (!defined('SCRIPTPATH')) { define('SCRIPTPATH', $this->scriptPath); } if (!empty($url_info) and !empty($url_info['host'])) { $this->vBHttpHost = $url_info['host']; if (!defined('VB_HTTP_HOST')) { define('VB_HTTP_HOST', $this->vBHttpHost); } } }
break; case 'timeout': define('CSRF_ERROR', 'timeout'); break; default: define('CSRF_ERROR', 'invalid'); } } } } else { if (!defined('CSRF_PROTECTION') and !defined('SKIP_REFERRER_CHECK')) { if (VB_HTTP_HOST and $_SERVER['HTTP_REFERER']) { $host_parts = @vB_String::parseUrl($_SERVER['HTTP_HOST']); $http_host_port = isset($host_parts['port']) ? intval($host_parts['port']) : 0; $http_host = strtolower(VB_HTTP_HOST . ((!empty($http_host_port) and $http_host_port != '80') ? ":{$http_host_port}" : '')); $referrer_parts = @vB_String::parseUrl($_SERVER['HTTP_REFERER']); $ref_port = isset($referrer_parts['port']) ? intval($referrer_parts['port']) : 0; $ref_host = strtolower($referrer_parts['host'] . ((!empty($ref_port) and $ref_port != '80') ? ":{$ref_port}" : '')); if ($http_host == $ref_host) { /* Instant match is good enough no need to check anything further. */ $pass_ref_check = true; } else { $pass_ref_check = false; $allowed = array('.paypal.com'); $allowed[] = '.' . preg_replace('#^www\\.#i', '', $http_host); $whitelist = preg_split('#\\s+#', $vbulletin->options['allowedreferrers'], -1, PREG_SPLIT_NO_EMPTY); // Get whitelist $allowed = array_unique(is_array($whitelist) ? array_merge($allowed, $whitelist) : $allowed); // Merge and de-duplicate. foreach ($allowed as $host) {
function &fetch_file_via_socket($rawurl, $postfields = array()) { $url = @vB_String::parseUrl($rawurl); if (!$url or empty($url['host'])) { return false; //trigger_error('Invalid URL specified to fetch_file_via_socket()', E_USER_ERROR); } if ($url['scheme'] == 'https') { $url['port'] = $url['port'] ? $url['port'] : 443; } else { $url['port'] = $url['port'] ? $url['port'] : 80; } $url['path'] = $url['path'] ? $url['path'] : '/'; if (empty($postfields)) { if ($url['query']) { $url['path'] .= "?{$url['query']}"; } $url['query'] = ''; $method = 'GET'; } else { $fields = array(); foreach ($postfields as $key => $value) { if (!empty($value)) { $fields[] = $key . '=' . urlencode($value); } } $url['query'] = implode('&', $fields); $method = 'POST'; } $communication = false; if (function_exists('curl_init') and $ch = curl_init()) { curl_setopt($ch, CURLOPT_URL, $rawurl); curl_setopt($ch, CURLOPT_TIMEOUT, 5); if ($method == 'POST') { curl_setopt($ch, CURLOPT_POST, true); curl_setopt($ch, CURLOPT_POSTFIELDS, $url['query']); } curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_HEADER, true); curl_setopt($ch, CURLOPT_USERAGENT, 'vBulletin via cURL/PHP'); @curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); // disabled in safe_mode/open_basedir in PHP 5.1.6 @curl_setopt($ch, CURLOPT_ENCODING, 'gzip'); // this will work on versions of cURL after 7.10, though was broken on PHP 4.3.6 $full_result = curl_exec($ch); if ($full_result === false and curl_errno($ch) == '60') { curl_setopt($ch, CURLOPT_CAINFO, DIR . '/includes/paymentapi/ca-bundle.crt'); $full_result = curl_exec($ch); } curl_close($ch); if ($full_result !== false) { $communication = true; } } if (!$communication) { if (VB_AREA == 'AdminCP') { $fp = fsockopen($url['host'], $url['port'], $errno, $errstr, 5); } else { $fp = @fsockopen($url['host'], $url['port'], $errno, $errstr, 5); } if (!$fp) { return false; //trigger_error("Unable to connect to host <i>$url[host]</i>.<br />$errstr", E_USER_ERROR); } socket_set_timeout($fp, 5); $headers = "{$method} {$url['path']} HTTP/1.0\r\n"; $headers .= "Host: {$url['host']}\r\n"; $headers .= "User-Agent: vBulletin RSS Reader\r\n"; if (function_exists('gzinflate')) { $headers .= "Accept-Encoding: gzip\r\n"; } if ($method == 'POST') { $headers .= "Content-Type: application/x-www-form-urlencoded\r\n"; $headers .= "Content-Length: " . strlen($url['query']) . "\r\n"; } $headers .= "\r\n"; fwrite($fp, $headers . $url['query']); $full_result = ''; while (!feof($fp)) { $result = fgets($fp, 1024); $full_result .= $result; } fclose($fp); } preg_match('#^(.*)\\r\\n\\r\\n(.*)$#sU', $full_result, $matches); unset($full_result); // when communication is true we've used cURL so lets check for redirect if ($communication) { while (preg_match("#\r\nLocation: #i", $matches[1])) { preg_match('#^(.*)\\r\\n\\r\\n(.*)$#sU', $matches[2], $matches); } } if (function_exists('gzinflate') and preg_match("#\r\nContent-encoding: gzip\r\n#i", $matches[1])) { if ($inflated = @gzinflate(substr($matches[2], 10))) { $matches[2] =& $inflated; } } return array('headers' => $matches[1], 'body' => $matches[2]); }
/** * Returns a matching route if available for $pathInfo * * @param string $pathInfo * @param string $queryString * @return vB_Frontend_Route */ public function getRoute($pathInfo, $queryString, $anchor = '') { static $closed; // clean the path if necessary $parsed = vB_String::parseUrl($pathInfo); $pathInfo = $parsed['path']; // check for any querystring to append if (!empty($parsed['query'])) { if (!empty($queryString)) { $queryString = $parsed['query'] . '&' . $queryString; } else { $queryString = $parsed['query']; } } if (empty($anchor) and !empty($parsed['anchor'])) { $anchor = $parsed['anchor']; } //Check for standard routes. if (is_string($pathInfo)) { $common = vB5_Route::fetchCommonRoutes(); if (isset($common[$pathInfo])) { //See if we have a match // pattern matching is case-insensitive $pattern = '#^' . $common[$pathInfo]['regex'] . '(?:/)?$#i'; if (preg_match($pattern, $pathInfo, $matches)) { $className = (isset($common[$pathInfo]['class']) and !empty($common[$pathInfo]['class']) and class_exists($common[$pathInfo]['class'])) ? $common[$pathInfo]['class'] : self::DEFAULT_CLASS; if (!empty($common[$pathInfo]['arguments'])) { $common[$pathInfo]['arguments'] = unserialize($common[$pathInfo]['arguments']); } try { $route = new $className($common[$pathInfo], $matches, $queryString, $anchor); } catch (vB_Exception $ex) { return $this->handleRouteExceptions($ex); } } } } if (!isset($route)) { // calculate prefixes set $prefixes = vB5_Route::getPrefixSet($pathInfo); // get matching routes $result = vB::getDbAssertor()->assertQuery('routenew', array('prefix' => $prefixes)); if (in_array($result->db()->errno, $result->db()->getCriticalErrors())) { throw new Exception('no_vb5_database'); } $prefixMatches = array(); foreach ($result as $route) { if (($unserialized = @unserialize($route['arguments'])) !== false) { $route['arguments'] = $unserialized; } else { $route['arguments'] = array(); } $prefixMatches[$route['routeid']] = $route; } unset($route); } // check for banned $bannedInfo = vB_Library::instance('user')->fetchBannedInfo(false); // get best route try { if (!isset($route)) { $route = vB5_Route::selectBestRoute($pathInfo, $queryString, $anchor, $prefixMatches); } if ($route) { // Check if forum is closed $routeInfo = array('routeguid' => $route->getRouteGuid(), 'controller' => $route->getController(), 'action' => $route->getAction(), 'arguments' => $route->getArguments()); $segments = $route->getRouteSegments(); $cleanedRoute = implode('/', $segments); if (in_array($cleanedRoute, $this->GetSpecialRoutes())) { return array('no_permission' => 1); } //Always allow login and access to the admincp, even if closed. if (!in_array($cleanedRoute, $this->whitelistRoute)) { if (!isset($closed)) { if (vB_Cache::instance(vB_Cache::CACHE_FAST)->isLoaded('vB_State_checkBeforeView')) { $closed = vB_Cache::instance(vB_Cache::CACHE_FAST)->read('vB_State_checkBeforeView'); } else { $closed = vB_Api::instanceInternal('state')->checkBeforeView($routeInfo); } } if ($closed !== false) { return array('forum_closed' => $closed['msg']); } } if ($bannedInfo['isbanned']) { return array('banned_info' => $bannedInfo); } if (!vB::getUserContext()->getChannelPermission('forumpermissions', 'canview', 1)) { $prefix = $route->getCanonicalPrefix(); if (!in_array($prefix, $this->whitelistPrefix)) { if ($route->getPrefix() == 'admincp' or $route->getPrefix() == 'modcp') { // do nothing really, just allow passage } else { if ($route->getPrefix() == 'ajax') { $arguments = $route->getArguments(); $allowedOptions = array('/api/contactus/sendMail', '/api/hv/generateToken'); if (!isset($arguments['route']) or !in_array($arguments['route'], $allowedOptions)) { return array('no_permission' => 1); } } else { return array('no_permission' => 1); } } } } if (is_array($route) and (isset($route['no_permission']) or isset($route['internal_error']))) { return $route; } $canonicalUrl = $route->getCanonicalUrl(); $canonicalUrl = str_replace('&', '&', $canonicalUrl); $canonicalPathInfo = $canonicalUrl ? vB_String::parseUrl($canonicalUrl, PHP_URL_PATH) : $pathInfo; $canonicalParam = $route->getCanonicalQueryParameters(); if ($canonicalPathInfo and $canonicalPathInfo[0] == '/') { $canonicalPathInfo = substr($canonicalPathInfo, 1); } $queryParams = $route->getQueryParameters(); $routeId = $route->getRouteId(); // return routeid even for 301 redirects. Certain callers expect // this function to return the routeid in order to write a cache record if ($redirectId = $route->getRedirect301()) { return array('routeid' => $routeId, 'redirect' => vB5_Route::buildUrl($redirectId, $route->getArguments(), $queryParams, $route->getAnchor()), 'redirectRouteId' => $redirectId); } else { if ($pathInfo != $canonicalPathInfo or $canonicalParam !== false and $queryParams != $canonicalParam) { $hashtag = ''; if (isset($queryParams['p'])) { $hashtag = '#post' . $queryParams['p']; // some browers do not preserve fragment during redirects, VBV-10255 } return array('routeid' => $routeId, 'redirect' => $canonicalUrl . $hashtag, 'redirectRouteId' => $routeId); } else { return array('routeid' => $routeId, 'routeguid' => $route->getRouteGuid(), 'controller' => $route->getController(), 'action' => $route->getAction(), 'template' => $route->getTemplate(), 'arguments' => $route->getArguments(), 'queryParameters' => $queryParams, 'pageKey' => $route->getPageKey(), 'userAction' => $route->getUserAction(), 'breadcrumbs' => $route->getBreadcrumbs(), 'headlinks' => $route->getHeadLinks()); } } } else { return false; } } catch (vB_Exception $ex) { return $this->handleRouteExceptions($ex); } }
/** * Handles a [url] tag. Creates a link to another web page. * * @param string If tag has option, the displayable name. Else, the URL. * @param string If tag has option, the URL. * * @return string HTML representation of the tag. */ function handle_bbcode_url($text, $link) { $rightlink = trim($link); if (empty($rightlink)) { // no option -- use param $rightlink = trim($text); } $rightlink = str_replace(array('`', '"', "'", '['), array('`', '"', ''', '['), $this->stripSmilies($rightlink)); // remove double spaces -- fixes issues with wordwrap $rightlink = str_replace(' ', '', $rightlink); if (!preg_match('#^[a-z0-9]+(?<!about|javascript|vbscript|data):#si', $rightlink)) { $rightlink = "http://{$rightlink}"; } if (!trim($link) or str_replace(' ', '', $text) == $rightlink) { $tmp = vB_String::unHtmlSpecialChars($rightlink); if (vB_String::vbStrlen($tmp) > 55 and $this->isWysiwyg() == false) { $text = vB_String::htmlSpecialCharsUni(vB_String::vbChop($tmp, 36) . '...' . substr($tmp, -14)); } else { // under the 55 chars length, don't wordwrap this $text = str_replace(' ', '', $text); } } static $current_url, $current_host, $allowed, $friendlyurls = array(); if (!isset($current_url)) { $current_url = @vB_String::parseUrl(self::$bbUrl); } $is_external = self::$urlNoFollow; if (self::$urlNoFollow) { if (!isset($current_host)) { $current_host = preg_replace('#:(\\d)+$#', '', self::$vBHttpHost); $allowed = preg_split('#\\s+#', self::$urlNoFollowWhiteList, -1, PREG_SPLIT_NO_EMPTY); $allowed[] = preg_replace('#^www\\.#i', '', $current_host); $allowed[] = preg_replace('#^www\\.#i', '', $current_url['host']); } $target_url = preg_replace('#^([a-z0-9]+:(//)?)#', '', $rightlink); foreach ($allowed as $host) { if (vB_String::stripos($target_url, $host) !== false) { $is_external = false; } } } // standard URL hyperlink return "<a href=\"{$rightlink}\" target=\"_blank\"" . ($is_external ? ' rel="nofollow"' : '') . ">{$text}</a>"; }
if (defined($define_name) and constant($define_name) !== '') { $product['version'] = constant($define_name); } $i++; print_cells_row(array($title, htmlspecialchars_uni($product['version']), htmlspecialchars_uni($product['description']), "<div align=\"" . vB_Template_Runtime::fetchStyleVar('right') . "\">\n\t\t\t\t<select name=\"s{$product['productid']}\" id=\"prodsel{$i}\" onchange=\"js_page_jump({$i}, '{$product['productid']}')\" class=\"bginput\">\n\t\t\t\t\t" . construct_select_options($options) . "\n\t\t\t\t</select> <input type=\"button\" class=\"button\" value=\"" . $vbphrase['go'] . "\" onclick=\"js_page_jump({$i}, '{$product['productid']}');\" />\n\t\t\t</div>"), false, '', -2); } print_table_footer(); echo '<p align="center">' . construct_link_code($vbphrase['add_import_product'], "product.php?" . vB::getCurrentSession()->get('sessionurl') . "do=productadd") . '</p>'; } // ############################################################################# if ($_REQUEST['do'] == 'productversioncheck') { $product = $assertor->getRow('product', array('productid' => $vbulletin->GPC['productid'])); if (!$product or empty($product['versioncheckurl'])) { print_stop_message2('invalid_product_specified'); } $version_url = @vB_String::parseUrl($product['versioncheckurl']); if (!$version_url) { print_stop_message2('invalid_version_check_url_specified'); } if (!$version_url['port']) { $version_url['port'] = 80; } if (!$version_url['path']) { $version_url['path'] = '/'; } $fp = @fsockopen($version_url['host'], $version_url['port'] ? $version_url['port'] : 80, $errno, $errstr, 10); if (!$fp) { print_stop_message2(array('version_check_connect_failed_host_x_error_y', htmlspecialchars_uni($version_url['host']), htmlspecialchars_uni($errstr))); } $send_headers = "POST {$version_url['path']} HTTP/1.0\r\n"; $send_headers .= "Host: {$version_url['host']}\r\n";
if ($vbulletin->GPC['address']) { // chosen to address the issue -- redirect to the appropriate page $adminmessageid = intval($vbulletin->GPC['address'][0]); $adminmessage = vB::getDbAssertor()->getRow('adminmessage', array('adminmessageid' => $adminmessageid)); if (!empty($adminmessage)) { // set the issue as addressed vB::getDbAssertor()->update('adminmessage', array('status' => 'done', 'statususerid' => $vbulletin->userinfo['userid']), array('adminmessageid' => $adminmessageid)); } if (!empty($adminmessage) and !empty($adminmessage['execurl'])) { if ($adminmessage['method'] == 'get') { // get redirect -- can use the url basically as is if (!strpos($adminmessage['execurl'], '?')) { $adminmessage['execurl'] .= '?'; } $args = array(); $execurl = vB_String::parseUrl($adminmessage['execurl'] . vB::getCurrentSession()->get('sessionurl_js')); $pathinfo = pathinfo($execurl['path']); $file = $pathinfo['basename']; parse_str($execurl['query'], $args); print_cp_redirect2($file, $args); } else { // post redirect -- need to seperate into <file>?<querystring> first if (preg_match('#^(.+)\\?(.*)$#siU', $adminmessage['execurl'], $match)) { $script = $match[1]; $arguments = explode('&', $match[2]); } else { $script = $adminmessage['execurl']; $arguments = array(); } echo ' <form action="' . htmlspecialchars($script) . '" method="post" id="postform">
/** * Removes HTML characters and potentially unsafe scripting words from a URL * Note: The query string is preserved. * * @param string The url to clean * @return string */ public function xssCleanUrl($url) { if ($query = vB_String::parseUrl($url, PHP_URL_QUERY)) { $url = substr($url, 0, strpos($url, '?')); $url = $this->xssClean($url); return $url . '?' . $query; } return $this->xssClean($url); }
/** * Fetches the path for the current request relative to the basepath. * This is useful for local anchors (<a href="{vb:raw relpath}#post">). * * Substracts any overlap between basepath and path with the following results: * * base: http://www.example.com/forums/ * path: /forums/content.php * result: content.php * * base: http://www.example.com/forums/admincp * path: /forums/content/1-Article * result: ../content/1-Article * * @return string */ function fetch_relpath($path = false) { if (!$path and (isset($this->registry->relpath) and $this->registry->relpath != '')) { return $this->registry->relpath; } // if no path specified, use the request path if (!$path) { if ($_SERVER['REQUEST_METHOD'] == 'POST' and isset($_SERVER['HTTP_X_REQUESTED_WITH']) and $_SERVER['HTTP_X_REQUESTED_WITH'] == 'XMLHttpRequest' and !empty($_POST['relpath'])) { $relpath = $_POST['relpath']; $query = ''; } else { $relpath = VB_URL_PATH; $query = VB_URL_QUERY; $fragment = ""; } } else { // if the path is already absolute there's nothing to do if (strpos($path, '://')) { return $path; } if (!$path) { return $path; } $relpath = vB_String::parseUrl($path, PHP_URL_PATH); $query = vB_String::parseUrl($path, PHP_URL_QUERY); $fragment = vB_String::parseUrl($path, PHP_URL_FRAGMENT); } $relpath = ltrim($relpath, '/'); $basepath = @vB_String::parseUrl($this->fetch_basepath(), PHP_URL_PATH); $basepath = trim($basepath, '/'); // get path segments for comparison $relpath = explode('/', $relpath); $basepath = explode('/', $basepath); // remove segments that basepath and relpath share foreach ($basepath as $segment) { if ($segment == current($relpath)) { array_shift($basepath); array_shift($relpath); } else { break; } } // rebuild the relpath $relpath = implode('/', $relpath); // add the query string if the current path is being used if ($query) { $relpath = $this->add_query($relpath, $query); } // add the fragment back if ($fragment) { $relpath = $this->add_fragment($relpath, $fragment); } return $relpath; }
{ $('[name="allbox"]').prop('checked', false); } } $('.rssenabled').click(verifyAllChecked); verifyAllChecked(); }); </script> <?php print_form_header('rssposter', 'updatestatus'); print_table_header($vbphrase['rss_feed_manager'], 5); print_cells_row(array('<input type="checkbox" name="allbox" title="' . $vbphrase['check_all'] . '" onclick="js_check_all(this.form);" />', $vbphrase['rss_feed_gcron'], $vbphrase['forum'] . ' / ' . $vbphrase['username'], $vbphrase['last_checked'], $vbphrase['controls']), true, '', -4); foreach ($feeds as $rssfeedid => $feed) { $x = @vB_String::parseUrl($feed['url']); if ($feed['lastrun'] > 0) { $date = vbdate($vbulletin->options['dateformat'], $feed['lastrun'], true); $time = vbdate($vbulletin->options['timeformat'], $feed['lastrun']); $datestring = $date . ($vbulletin->options['yestoday'] == 2 ? '' : ", {$time}"); } else { $datestring = '-'; } print_cells_row(array("<input type=\"checkbox\" class=\"rssenabled\" name=\"enabled[{$rssfeedid}]\" value=\"{$rssfeedid}\" title=\"{$vbphrase['enabled']}\"" . ($feed['options'] & $vbulletin->bf_misc_feedoptions['enabled'] ? ' checked="checked"' : '') . " />", "<div><a href=\"rssposter.php?" . vB::getCurrentSession()->get('sessionurl') . "do=edit&rssfeedid={$feed['rssfeedid']}\" title=\"" . htmlspecialchars_uni($feed['url']) . "\"><strong>{$feed['title']}</strong></a></div>\n\t\t\t\t<div class=\"smallfont\"><a href=\"" . htmlspecialchars_uni($feed['url']) . "\" target=\"feed\">{$x['host']}</a></div>", "<div><a href=\"forum.php?" . vB::getCurrentSession()->get('sessionurl') . "do=edit&nodeid={$feed['nodeid']}\">{$feed['channeltitle']}</a></div>\n\t\t\t\t<div class=\"smallfont\"><a href=\"user.php?" . vB::getCurrentSession()->get('sessionurl') . "do=edit&userid={$feed['userid']}\">{$feed['username']}</a></div>", "<span class=\"smallfont\">{$datestring}</span>", construct_link_code($vbphrase['edit'], "rssposter.php?" . vB::getCurrentSession()->get('sessionurl') . "do=edit&rssfeedid={$feed['rssfeedid']}") . construct_link_code($vbphrase['delete'], "rssposter.php?" . vB::getCurrentSession()->get('sessionurl') . "do=delete&rssfeedid={$feed['rssfeedid']}")), false, '', -4); } if (vB::getUserContext()->hasAdminPermission('canadmincron')) { $runNow = "<input type=\"button\" class=\"button\" value=\"{$vbphrase['run_scheduled_task_now']}\" onclick=\"window.location='cronadmin.php?" . vB::getCurrentSession()->get('sessionurl') . "do=runcron&varname=rssposter'\" />"; } else { $runNow = ''; } print_submit_row($vbphrase['save_enabled_status'], false, 5, '', $runNow . "\n\t\t\t\t<input type=\"button\" class=\"button\" value=\"{$vbphrase['add_new_rss_feed']}\" onclick=\"window.location='rssposter.php?" . vB::getCurrentSession()->get('sessionurl') . "do=edit'\" />\n\t\t\t");
/** * Prepares data for generating the navbar display, decides which navbar tab to * highlight. The passed $data array is modified. * * @param array Array of navigation items, for the header or the footer * @param string The current URL * @param bool True if editing the page, false if not * @param int Channel Node ID * * @return bool Whether the current navbar item was found or not */ protected function prepareNavbarData(array &$data, $url = false, $edit = false, $channelId = 0) { $baseurl_short = vB_String::parseUrl(vB::getDatastore()->getOption('frontendurl'), PHP_URL_PATH); $found_current = false; $found_sub_parent = false; $possibleCurrentItems = array(); $removed_element = false; $userinfo = vB_Api::instanceInternal('user')->fetchCurrentUserInfo(); $phraseApi = vB_Api::instance('phrase'); foreach ($data as $k => &$item) { if (is_array($item) and isset($item['url'])) { $item['phrase'] = $item['title']; $this->requiredPhrases[] = $item['title']; $additionalGrp = false; if ($userinfo['membergroupids'] and !empty($item['usergroups'])) { $memberGroups = explode(',', $userinfo['membergroupids']); foreach ($memberGroups as $memberGroup) { if (in_array($memberGroup, $item['usergroups'])) { $additionalGrp = true; break; } } } if ((!$edit or !vB::getUserContext()->hasAdminPermission('canusesitebuilder')) and (!empty($item['usergroups']) and (!in_array($userinfo['usergroupid'], $item['usergroups']) and !$additionalGrp))) { unset($data[$k]); $removed_element = true; continue; } $item['isAbsoluteUrl'] = (bool) preg_match('#^https?://#i', $item['url']); $item['normalizedUrl'] = ltrim($item['url'], '/'); $item['newWindow'] = $item['newWindow'] ? 1 : 0; if (!empty($item['subnav']) and is_array($item['subnav'])) { $found_sub = $this->prepareNavbarData($item['subnav'], $url, $edit, $channelId); if (!$found_current and $found_sub) { $found_sub_parent =& $item; $item['current_sub'] = true; } } if (!$found_current and !empty($url)) { if ($item['isAbsoluteUrl']) { $itemUrl = vB_String::parseUrl($item['normalizedUrl'], PHP_URL_PATH); } else { $itemUrl = $baseurl_short . '/' . $item['normalizedUrl']; } if (strtolower($url) == strtolower($itemUrl) || strlen($url) > strlen($itemUrl) && strtolower(substr($url, 0, -(strlen($url) - strlen($itemUrl)))) == strtolower($itemUrl)) { // found an item that might be the current item $possibleCurrentItems[] = array('length' => strlen($itemUrl), 'item' => &$item); } } } } // Reset the keys of the array, because in js it will be considered as an object if ($removed_element) { $data = array_values($data); } // test some special cases where we have non-conforming routes (routes // which don't begin with the same text as the navbar tab they are // supposed to be in. // @TODO consider renaming the /blogadmin route to /blogs/admin // and the /sgadmin route to /social-groups/admin if (!$found_current) { $setCurrentTab = ''; // special case: the create content pages $channelId = (int) $channelId; if (strpos($url, $baseurl_short . '/new-content') === 0 and $channelId > 0) { switch ($this->getChannelType($channelId)) { case 'blog': $setCurrentTab = 'blogs'; break; case 'group': $setCurrentTab = 'social-groups'; break; case 'article': $setCurrentTab = 'articles'; break; default: break; } } else { if (strpos($url, $baseurl_short . '/blogadmin') === 0) { $setCurrentTab = 'blogs'; } else { if (strpos($url, $baseurl_short . '/sgadmin') === 0) { $setCurrentTab = 'social-groups'; } else { if ($channelId > 0) { // special case: social groups, categories & topics // social group routes do not maintain the 'social-groups' bit in the URL if ($this->getChannelType($channelId) == 'group') { $setCurrentTab = 'social-groups'; } } } } } // set the special-cased tab to current if ($setCurrentTab) { foreach ($data as $k => $v) { if ($v['normalizedUrl'] == $setCurrentTab) { $data[$k]['current'] = true; $found_current = true; break; } } } } // test the possible current items-- the longest URL is the best match if (!$found_current and !empty($possibleCurrentItems)) { $longestKey = 0; foreach ($possibleCurrentItems as $k => $possibleCurrentItem) { if ($possibleCurrentItem['length'] > $possibleCurrentItems[$longestKey]['length']) { $longestKey = $k; } } $possibleCurrentItems[$longestKey]['item']['current'] = true; $found_current = true; } unset($possibleCurrentItems); if (!$found_current and !empty($found_sub_parent)) { $found_sub_parent['current'] = true; } return $found_current; }
/** * Validates the data for update or add * @param array $data -- The data to be validated. * @param string $function -- The function we are validating for, so we can log that with the error message * @return none -- will throw an execption if there is an error. Will not if everything is valid */ private function validateLinkData($data, $function) { if (!empty($data['url'])) { $urlInfo = vB_String::parseUrl($data['url']); if (empty($urlInfo) or !empty($urlInfo['scheme']) and $urlInfo['scheme'] != 'http' and $urlInfo['scheme'] != 'https') { throw new vB_Exception_Api('invalid_data_w_x_y_z', array($data['url'], '$data[\'url\']', __CLASS__, $function)); } } }