function _stripos($haystack, $needle) { if ($this->_charset == 'utf-8') { if (MBYTE_strlen($needle) > 0) { $haystack = MBYTE_strtolower($haystack); return MBYTE_strpos($haystack, $needle); } else { return false; } } if (function_exists('stripos')) { return stripos($haystack, $needle); } else { return strpos(strtolower($haystack), strtolower($needle)); } }
/** * Unescapes certain HTML for editing again. * * @access Private * @param string $in Text escaped to unescape for editing * @return string Unescaped string */ function _editUnescape($in) { if ($this->_postmode == 'html' || $this->_postmode == 'wikitext') { /* Raw and code blocks need entity decoding. Other areas do not. * otherwise, annoyingly, < will end up as < on preview 1, on * preview 2 it'll be stripped by KSES. Can't beleive I missed that * in rewrite phase 1. * * First, raw */ $inlower = MBYTE_strtolower($in); $buffer = $in; $start_pos = MBYTE_strpos($inlower, '[raw]'); if ($start_pos !== false) { $out = ''; while ($start_pos !== false) { /* Copy in to start to out */ $out .= MBYTE_substr($buffer, 0, $start_pos); /* Find end */ $end_pos = MBYTE_strpos($inlower, '[/raw]'); if ($end_pos !== false) { /* Encode body and append to out */ $encoded = html_entity_decode(MBYTE_substr($buffer, $start_pos, $end_pos - $start_pos)); $out .= $encoded . '[/raw]'; /* Nibble in */ $inlower = MBYTE_substr($inlower, $end_pos + 6); $buffer = MBYTE_substr($buffer, $end_pos + 6); } else { // missing [/raw] // Treat the remainder as code, but this should have been // checked prior to calling: $out .= html_entity_decode(MBYTE_substr($buffer, $start_pos + 5)); $inlower = ''; } $start_pos = MBYTE_strpos($inlower, '[raw]'); } // Append remainder: if ($buffer != '') { $out .= $buffer; } $in = $out; } /* * Then, code */ $inlower = MBYTE_strtolower($in); $buffer = $in; $start_pos = MBYTE_strpos($inlower, '[code]'); if ($start_pos !== false) { $out = ''; while ($start_pos !== false) { /* Copy in to start to out */ $out .= MBYTE_substr($buffer, 0, $start_pos); /* Find end */ $end_pos = MBYTE_strpos($inlower, '[/code]'); if ($end_pos !== false) { /* Encode body and append to out */ $encoded = html_entity_decode(MBYTE_substr($buffer, $start_pos, $end_pos - $start_pos)); $out .= $encoded . '[/code]'; /* Nibble in */ $inlower = MBYTE_substr($inlower, $end_pos + 7); $buffer = MBYTE_substr($buffer, $end_pos + 7); } else { // missing [/code] // Treat the remainder as code, but this should have been // checked prior to calling: $out .= html_entity_decode(MBYTE_substr($buffer, $start_pos + 6)); $inlower = ''; } $start_pos = MBYTE_strpos($inlower, '[code]'); } // Append remainder: if ($buffer != '') { $out .= $buffer; } $in = $out; } return $in; } else { // advanced editor or plaintext can handle themselves... return $in; } }
private static function _unescapeSpecialTag($in, $tags) { $inlower = MBYTE_strtolower($in); $start_pos = MBYTE_strpos($inlower, $tags[0]); if ($start_pos === false) { return $in; } $buffer = $in; $out = ''; while ($start_pos !== false) { // Copy in to start to out $out .= MBYTE_substr($buffer, 0, $start_pos); // Find end $end_pos = MBYTE_strpos($inlower, $tags[1]); if ($end_pos !== false) { // Encode body and append to out $encoded = html_entity_decode(MBYTE_substr($buffer, $start_pos, $end_pos - $start_pos)); $out .= $encoded . $tags[1]; $len_end = strlen($tags[1]); // Nibble in $inlower = MBYTE_substr($inlower, $end_pos + $len_end); $buffer = MBYTE_substr($buffer, $end_pos + $len_end); } else { // missing end $len_start = strlen($tags[0]); // Treat the remainder as code, but this should have been // checked prior to calling: $out .= html_entity_decode(MBYTE_substr($buffer, $start_pos + $len_start)); $inlower = ''; } $start_pos = MBYTE_strpos($inlower, $tags[0]); } // Append remainder: if ($buffer != '') { $out .= $buffer; } return $out; }
/** * This function will allow plugins to support the use of custom autolinks * in other site content. Plugins can now use this API when saving content * and have the content checked for any autolinks before saving. * The autolink would be like: [story:20040101093000103 here] * * @param string $content Content that should be parsed for autolinks * @param string $plugin Optional if you only want to parse using a specific plugin * @param string $remove Optional if you want to remove the autotag from the content * */ function PLG_replaceTags($content, $plugin = '', $remove = false) { global $_CONF, $_TABLES, $LANG32; if (isset($_CONF['disable_autolinks']) && $_CONF['disable_autolinks'] == 1) { // autolinks are disabled - return $content unchanged return $content; } if ($remove) { $autolinkModules = PLG_collectTags('nopermission'); if (!is_array($autolinkModules)) { // a permission check may not return any data so no point parsing content return $content; } } else { $autolinkModules = PLG_collectTags(); } for ($i = 1; $i <= 5; $i++) { // For each supported module, scan the content looking for any AutoLink tags $tags = array(); $contentlen = MBYTE_strlen($content); $content_lower = MBYTE_strtolower($content); foreach ($autolinkModules as $moduletag => $module) { $autotag_prefix = '[' . $moduletag . ':'; $offset = 0; $prev_offset = 0; while ($offset < $contentlen) { $start_pos = MBYTE_strpos($content_lower, $autotag_prefix, $offset); if ($start_pos === false) { break; } else { $end_pos = MBYTE_strpos($content_lower, ']', $start_pos); $next_tag = MBYTE_strpos($content_lower, '[', $start_pos + 1); if ($end_pos > $start_pos and ($next_tag === false or $end_pos < $next_tag)) { $taglength = $end_pos - $start_pos + 1; $tag = MBYTE_substr($content, $start_pos, $taglength); $parms = explode(' ', $tag); // Extra test to see if autotag was entered with a space // after the module name if (MBYTE_substr($parms[0], -1) == ':') { $startpos = MBYTE_strlen($parms[0]) + MBYTE_strlen($parms[1]) + 2; $label = str_replace(']', '', MBYTE_substr($tag, $startpos)); $tagid = $parms[1]; } else { $label = str_replace(']', '', MBYTE_substr($tag, MBYTE_strlen($parms[0]) + 1)); $parms = explode(':', $parms[0]); if (count($parms) > 2) { // whoops, there was a ':' in the tag id ... array_shift($parms); $tagid = implode(':', $parms); } else { $tagid = $parms[1]; } } $newtag = array('module' => $module, 'tag' => $moduletag, 'tagstr' => $tag, 'startpos' => $start_pos, 'length' => $taglength, 'parm1' => str_replace(']', '', $tagid), 'parm2' => $label); $tags[] = $newtag; } else { // Error: tags do not match - return with no changes return $content . $LANG32[32]; } $prev_offset = $offset; $offset = $end_pos; } } } // If we have found 1 or more AutoLink tag if (count($tags) > 0) { // Found the [tag] - Now process them all foreach ($tags as $autotag) { if ($remove) { $content = str_replace($autotag['tagstr'], '', $content); } else { $function = 'plugin_autotags_' . $autotag['module']; if (function_exists($function) and (empty($plugin) or $plugin == $autotag['module'])) { $content = $function('parse', $content, $autotag); } } } } else { break; } } return $content; }
public function testMBYTE_strtolower() { $this->assertEquals(utf8_encode('användare'), MBYTE_strtolower(utf8_encode('ANvändare'))); }
/** * This function checks html tags. * * Checks to see that the HTML tags are on the approved list and * removes them if not. * * @param string $str HTML to check * @param string $permissions comma-separated list of rights which identify the current user as an "Admin" * @return string Filtered HTML * */ function COM_checkHTML($str, $permissions = 'story.edit') { global $_CONF, $_USER; // replace any \ with \ (HTML equiv) $str = str_replace('\\', '\', COM_stripslashes($str)); // Get rid of any newline characters $str = preg_replace("/\n/", '', $str); // Replace any $ with $ (HTML equiv) $str = str_replace('$', '$', $str); // handle [code] ... [/code] do { $start_pos = MBYTE_strpos(MBYTE_strtolower($str), '[code]'); if ($start_pos !== false) { $end_pos = MBYTE_strpos(MBYTE_strtolower($str), '[/code]'); if ($end_pos !== false) { $encoded = COM_handleCode(MBYTE_substr($str, $start_pos + 6, $end_pos - ($start_pos + 6))); $encoded = '<pre><code>' . $encoded . '</code></pre>'; $str = MBYTE_substr($str, 0, $start_pos) . $encoded . MBYTE_substr($str, $end_pos + 7); } else { // Treat the rest of the text as code (so as not to lose any // special characters). However, the calling entity should // better be checking for missing [/code] before calling this // function ... $encoded = COM_handleCode(MBYTE_substr($str, $start_pos + 6)); $encoded = '<pre><code>' . $encoded . '</code></pre>'; $str = MBYTE_substr($str, 0, $start_pos) . $encoded; } } } while ($start_pos !== false); // handle [raw] ... [/raw] do { $start_pos = MBYTE_strpos(MBYTE_strtolower($str), '[raw]'); if ($start_pos !== false) { $end_pos = MBYTE_strpos(MBYTE_strtolower($str), '[/raw]'); if ($end_pos !== false) { $encoded = COM_handleCode(MBYTE_substr($str, $start_pos + 5, $end_pos - ($start_pos + 5))); // [raw2] to avoid infinite loop. Not HTML comment as we strip // them later. $encoded = '[raw2]' . $encoded . '[/raw2]'; $str = MBYTE_substr($str, 0, $start_pos) . $encoded . MBYTE_substr($str, $end_pos + 6); } else { // Treat the rest of the text as raw (so as not to lose any // special characters). However, the calling entity should // better be checking for missing [/raw] before calling this // function ... $encoded = COM_handleCode(MBYTE_substr($str, $start_pos + 5)); // [raw2] to avoid infinite loop. Not HTML comment as we strip // them later. $encoded = '[raw2]' . $encoded . '[/raw2]'; $str = MBYTE_substr($str, 0, $start_pos) . $encoded; } } } while ($start_pos !== false); $has_skiphtmlfilterPermissions = SEC_hasRights('htmlfilter.skip'); if ($has_skiphtmlfilterPermissions || isset($_CONF['skip_html_filter_for_root']) && $_CONF['skip_html_filter_for_root'] == 1 && SEC_inGroup('Root')) { return $str; } // strip_tags() gets confused by HTML comments ... $str = preg_replace('/<!--.+?-->/', '', $str); $filter = new kses4(); if (isset($_CONF['allowed_protocols']) && is_array($_CONF['allowed_protocols']) && count($_CONF['allowed_protocols']) > 0) { $filter->SetProtocols($_CONF['allowed_protocols']); } else { $filter->SetProtocols(array('http:', 'https:', 'ftp:')); } if (empty($permissions) || !SEC_hasRights($permissions) || empty($_CONF['admin_html'])) { $html = $_CONF['user_html']; } else { if ($_CONF['advanced_editor'] && $_USER['advanced_editor']) { $html = array_merge_recursive($_CONF['user_html'], $_CONF['admin_html'], $_CONF['advanced_html']); } else { $html = array_merge_recursive($_CONF['user_html'], $_CONF['admin_html']); } } foreach ($html as $tag => $attr) { $filter->AddHTML($tag, $attr); } /* Replace [raw][/raw] with <!--raw--><!--/raw-->, note done "late" because * of the above noted // strip_tags() gets confused by HTML comments ... */ $str = $filter->Parse($str); $str = str_replace('[raw2]', '<!--raw--><span class="raw">', $str); $str = str_replace('[/raw2]', '</span><!--/raw-->', $str); return $str; }
/** * This function will allow plugins to support the use of custom autolinks * in other site content. Plugins can now use this API when saving content * and have the content checked for any autolinks before saving. * The autolink would be like: [story:20040101093000103 here] * * @param string $content Content that should be parsed for autolinks * @param string $plugin Optional if you only want to parse using a specific plugin * */ function PLG_replaceTags($content, $plugin = '') { global $_CONF, $_TABLES, $LANG32; if (isset($_CONF['disable_autolinks']) && $_CONF['disable_autolinks'] == 1) { // autolinks are disabled - return $content unchanged return $content; } $autolinkModules = PLG_collectTags(); // For each supported module, scan the content looking for any AutoLink tags $tags = array(); $contentlen = MBYTE_strlen($content); $content_lower = MBYTE_strtolower($content); foreach ($autolinkModules as $moduletag => $module) { $autotag_prefix = '[' . $moduletag . ':'; $offset = 0; $prev_offset = 0; while ($offset < $contentlen) { $start_pos = MBYTE_strpos($content_lower, $autotag_prefix, $offset); if ($start_pos === false) { break; } else { $end_pos = MBYTE_strpos($content_lower, ']', $start_pos); $next_tag = MBYTE_strpos($content_lower, '[', $start_pos + 1); if ($end_pos > $start_pos and ($next_tag === false or $end_pos < $next_tag)) { $taglength = $end_pos - $start_pos + 1; $tag = MBYTE_substr($content, $start_pos, $taglength); $parms = explode(' ', $tag); // Extra test to see if autotag was entered with a space // after the module name if (MBYTE_substr($parms[0], -1) == ':') { $startpos = MBYTE_strlen($parms[0]) + MBYTE_strlen($parms[1]) + 2; $label = str_replace(']', '', MBYTE_substr($tag, $startpos)); $tagid = $parms[1]; } else { $label = str_replace(']', '', MBYTE_substr($tag, MBYTE_strlen($parms[0]) + 1)); $parms = explode(':', $parms[0]); if (count($parms) > 2) { // whoops, there was a ':' in the tag id ... array_shift($parms); $tagid = implode(':', $parms); } else { $tagid = $parms[1]; } } $newtag = array('module' => $module, 'tag' => $moduletag, 'tagstr' => $tag, 'startpos' => $start_pos, 'length' => $taglength, 'parm1' => str_replace(']', '', $tagid), 'parm2' => $label); $tags[] = $newtag; } else { // Error: tags do not match - return with no changes return $content . $LANG32[32]; } $prev_offset = $offset; $offset = $end_pos; } } } // If we have found 1 or more AutoLink tag if (count($tags) > 0) { // Found the [tag] - Now process them all foreach ($tags as $autotag) { $function = 'plugin_autotags_' . $autotag['module']; if ($autotag['module'] == 'geeklog' and (empty($plugin) or $plugin == 'geeklog')) { $url = ''; $linktext = $autotag['parm2']; if ($autotag['tag'] == 'story') { $autotag['parm1'] = COM_applyFilter($autotag['parm1']); if (!empty($autotag['parm1'])) { $url = COM_buildUrl($_CONF['site_url'] . '/article.php?story=' . $autotag['parm1']); if (empty($linktext)) { $linktext = stripslashes(DB_getItem($_TABLES['stories'], 'title', "sid = '{$autotag['parm1']}'")); } } } if (!empty($url)) { $filelink = COM_createLink($linktext, $url); $content = str_replace($autotag['tagstr'], $filelink, $content); } } elseif (function_exists($function) and (empty($plugin) or $plugin == $autotag['module'])) { $content = $function('parse', $content, $autotag); } } } return $content; }
public function testMBYTE_strtolower() { $this->assertEquals('lowercase', MBYTE_strtolower('LoWErCaSE')); }