function _EscapeSpecialChars($text)
{
    global $g_escape_table;
    $tokens = _TokenizeHTML($text);
    $text = '';
    # rebuild $text from the tokens
    $in_pre = 0;
    # Keep track of when we're inside <pre> or <code> tags.
    $tags_to_skip = "!<(/?)(?:pre|code|kbd|script)[\\s>]!";
    foreach ($tokens as $cur_token) {
        if ($cur_token[0] == 'tag') {
            $cur_token[1] = str_replace(array('*', '_'), array($g_escape_table['*'], $g_escape_table['_']), $cur_token[1]);
            $text .= $cur_token[1];
        } else {
            $t = $cur_token[1];
            if (!$in_pre) {
                $t = _EncodeBackslashEscapes($t);
                # $t =~ s{([a-z])/([a-z])}{$1&thinsp;/&thinsp;$2}ig;
            }
            $text .= $t;
        }
    }
    return $text;
}
function _EscapeSpecialChars($text)
{
    global $md_escape_table;
    $tokens = _TokenizeHTML($text);
    $text = '';
    # rebuild $text from the tokens
    #	$in_pre = 0;  # Keep track of when we're inside <pre> or <code> tags.
    #	$tags_to_skip = "!<(/?)(?:pre|code|kbd|script|math)[\s>]!";
    foreach ($tokens as $cur_token) {
        if ($cur_token[0] == 'tag') {
            # Within tags, encode * and _ so they don't conflict
            # with their use in Markdown for italics and strong.
            # We're replacing each such character with its
            # corresponding MD5 checksum value; this is likely
            # overkill, but it should prevent us from colliding
            # with the escape values by accident.
            $cur_token[1] = str_replace(array('*', '_'), array($md_escape_table['*'], $md_escape_table['_']), $cur_token[1]);
            $text .= $cur_token[1];
        } else {
            $t = $cur_token[1];
            $t = _EncodeBackslashEscapes($t);
            $text .= $t;
        }
    }
    return $text;
}