All pastes #614221 Raw Edit

stefys

public php v1 · immutable
·published 2007-07-11 12:59 UTC
rendered paste body
<?php/*    Mircparser, parses mirc code    Copyright (C) <year>  <name of author>    This program is free software: you can redistribute it and/or modify    it under the terms of the GNU General Public License as published by    the Free Software Foundation, either version 3 of the License, or    (at your option) any later version.    This program is distributed in the hope that it will be useful,    but WITHOUT ANY WARRANTY; without even the implied warranty of    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the    GNU General Public License for more details.    You should have received a copy of the GNU General Public License    along with this program.  If not, see <http://www.gnu.org/licenses/>. *//** * Parses mirc code * * @author stefys <stefys@gmail.com> *///due to no static in PHP4 OOP, i'm gonna have to put some variables outside the class//Uncomment to have debug turned on//define('WITH_DEBUG', 1);//pattern to match identifiers with parameters//\x28 = '('//\x29 = ')' //those are used so they don't break my syntax highlighting ;)//$1 = identifier name//$2 = parameters list//$3 = optional prop$_mircparser_identfier_regexp  =    '@'                                 .        '(\$[^\s\x28]+)'                . // identifier name        '\x28'                          . // identifier open paranthesis        '((?:[^\x29]*,)*'               . // all parameters but last        '[^\x29]*)'                     . // last parameter        '\x29'                          . //identifier close paranthesis        '(?:(\.[^\s]+)|())'             . // optional prop    '@i';$_mircparser_directory_tree = array(    //d: = directory    //f: = file    //every directory name and file name has to be lowercase    //for case insensitivity    'C' => array(        'd:windows' => array(            'd:system32' => array(                'f:winsock32.dll'            ),            'd:system'        ),        'd:documents and settings' => array(            'd:administrator' => array(                'd:desktop' => 'f:secret.txt'            )        ),        'd:program files',        'd:mirc' => array(            'd:downloads',            'd:sounds',            'd:logs',            'f:mirc.ini',            'f:mirc.exe',            'f:script.ini'            ),        'f:ntdetect.com',        'f:msdos.sys',        'f:io.sys',        'f:command.com'    ),    'D' => array(        'd:games' => array('d:solitaire' => array('f:solitaire.exe'))        ));$_mircparser_partition_info = array(    'C' => array(        'type' => 'ntfs',        'free' => 1024*1024*1024*3.1, // 3.1 GB        'label' => 'local',        'size' => 4.5*1024*1024*1024 //4.5 GB (used 1.4GB)    ),    'D' => array(        'type' => 'fat32',        'free' => 1024*1024*200,  // 200mb free        'label' => 'other',        'size' => 1024*1024*512 //512 mb total    ));$_mircparser_mirc_dir = "C:\\mirc\\";/** * Public functions of the class: * constructor (string $code_to_evaluate, array $variables_to_use, *                  string $nick, string $addr, string $addr_server, *                  string $chan, string $name, string $me, *                  int $port, string $s_string, string $mirc_version) *  bool iswm (string wildcard, string string) *  string get_parsed_string() *  array get_used_commands()  *      ** returns an array where each value *      ** is a command used with $findfile or $finddir */class Mircparser {    var $_str, $_info, $_used_commands, $_used_identifiers, $_variables;    /**     * Class constructor     */    function Mircparser ($mirc_code, $variables, $nick, $addr, $addr_server, $chan, $name, $me, $port, $s_string, $version) {        // constructor               $this->_str = $mirc_code;        $this->_info = array(            'nick'        => $nick,            'addr'        => $addr,            'addr_server' => $addr_server,            'chan'        => $chan,            'name'        => $name,            'me'          => $me,            'port'        => $port,            's_string'    => $s_string,            'version'     => $version        );        $this->_used_commands    = array();        $this->_used_identifiers = array();        $this->_variables = $variables;                //if the mirc code to parse starts wtih $ or %, we prepend a space        if (substr($this->_str,0,1) == '$' ||            substr($this->_str,0,1) == '%')                $this->_str = ' '. $this->_str;                    $this->_str = &$this->_eval($this->_str);                $this->_str = &$this->_tomirc($this->_str);    }            // no double spaces, no spaces at beginning, no spaces at the end    function _tomirc ($str) {        $str = str_replace(array("\r", "\n"), "", $str);        $str = str_replace('  ', ' ', $str);        $str = preg_replace('@^\s+@', '', $str);        $str = preg_replace('@\s+$@', '', $str);        return $str;    }        function _eval ($mirc_code) {                global $_mircparser_identfier_regexp;            $str = $mirc_code;                //first we replace identifiers with parameters in the following way        //$id(param1,param2,...,paramN) becomes        //$id( param1 , param2 , param3 , ... , paramN)        //we add spaces so we can then do the basic replace               if (defined('WITH_DEBUG')) echo "_eval($str)<br />";               $str = preg_replace($_mircparser_identfier_regexp."e", "'$1( ' . str_replace(',', ' , ', '$2') . ' )$3'", $str);               if (defined('WITH_DEBUG')) echo "added spaces to identifiers: $str<br />";               // we did add spaces between parameters of identifiers, we now do the basic replace        $str = $this->_basic($str);                if (defined('WITH_DEBUG')) echo "after basic parse: $str<br />";                //we replace all the variables        //first, we replace the one that exist with their corresponding values        foreach ($this->_variables as $var => $val)            $str = str_replace(' %'.$var, ' '.$val, $str);                    if (defined('WITH_DEBUG')) echo "after variables replacement[1]: $str<br />";        //then we replace the ones that do not exist with null        $str = preg_replace('@%(?:[^ ]+)@', ' ', $str);        if (defined('WITH_DEBUG')) echo "[2]: $str<br />";                        //we've done basic replace, now we do replace for identifiers that have parameters        //we do so by calling the _adv_replacel function for each identifier        $str = preg_replace($_mircparser_identfier_regexp."e", '$this->_adv_replace(\'$0\')', $str);        if (defined('WITH_DEBUG')) echo "finally, the result: $str<br />";        return $str;            }        function _adv_replace ($str) {        $id_name = substr($str, 1, strpos($str, '(')-1); // everything after $ until (        $id_params = substr($str, ($s = strpos($str, '(') +1), strpos($str,')')-$s);                $id_params_a = array();        $id_params_arr = explode(',', $id_params);        foreach ($id_params_arr as $param)            $id_params_a[] = $this->_tomirc($param);                if (($s=strpos($str, ').')) !== false)            //we have a prop            $id_prop = substr($str, $s+2);        else $id_prop = '';        return $this->_adv_replace_call($id_name, $id_params_a, $id_prop);    }        //called when we have an identifier with parameters    function _adv_replace_call ($id_name, $id_params, $prop) {            if (count($id_params) < 1)            return '';                    global $_mircparser_partition_info;                    switch ($id_name) {        case 'chr':            return chr( (int)$id_params[0] );            break;        case 'asc':            return ord( substr($id_params[0],0,1) );            break;        case 'disk':            $exists =      isset($_mircparser_partition_info[strtoupper(substr($id_params[0],0,1))]);                        if ($exists) $ref = &$_mircparser_partition_info[strtoupper(substr($id_params[0],0,1))];            else $ref = null;                        if ($prop == null) return $exists?'$true':'$false';            elseif (isset($ref[$prop])) return $ref[$prop];            else return '';            break;        case 'len':            return strlen($id_params[0]);            break;        case 'calc':            //simple calc only            $m = array();            //$1 = first number            //$2 = sign            //$3 = second number            if (!preg_match('@(\d+)\s*([+*/-^])\s*(\d+)@', $id_params[0], $m))                return 0;            elseif ($m[2] == '+') return $m[1]+$m[3];            elseif ($m[2] == '-') return $m[1]-$m[3];            elseif ($m[2] == '*') return $m[1]*$m[3];            elseif ($m[2] == '/' && $m[3] == 0) return 0;            elseif ($m[2] == '/') return $m[1]/$m[3];            elseif ($m[2] == '^') return pow($m[1],$m[2]);            break;        case 'findfile':            return $this->_find($id_params, 'f:');            break;        case 'finddir':            return $this->_find($id_params, 'd:');            break;        case 'abs':            return abs((float)$id_params[0]);            break;        case 'and':            if (count($id_params) < 2) return '';            return (int)$id_params[0] & (int)$id_params[1];            break;        case 'base':            if (count($id_params) < 3) return '';            $d = base_convert((float)$id_params[0], (int)$id_params[1], (int)$id_params[2]);            if (isset($id_params[3]) &&                intval($id_params[3]) == $id_params[3] &&                ( $to_add=$id_params[3]-strlen($d) ) > 0)                $d = str_repeat('0', $to_add) . $d;            return $d;            break;        case 'ceil':            return ceil((float)$id_params[3]);        case 'encode':            if (count($id_params) != 2) return '';            if ($id_params[1] != 'm') return '';            return base64_encode($id_params[0]);            break;        case 'decode':            if (count($id_params) != 2) return '';            if ($id_params[1] != 'm') return '';            return base64_decode($id_params[0]);            break;        case 'int':            return (int)$id_params[0];            break;        case 'lower':            return strtolower($id_params[0]);            break;        case 'upper':            return strtoupper($id_params[0]);            break;        case 'mid':            return substr($id_params[0], (int)$id_params[1], (int)$id_params[2]);            break;        case 'left':            return substr($id_params[0], 0, (int)$id_params[1]);            break;        case 'right':            return substr($id_params[0], strlen($id_params[0])-(int)$id_params[1], (int)$id_params[1]);            break;        default:            return '';        }    }    function iswm ($wildcard, $string) {        $regex = '@^';        for ($i=0; $i<strlen($wildcard); $i++) {            $c = $wildcard{$i};            if ($c == '*') $regex .= '.*';            elseif ($c == '?') $regex .= '.';            else $regex .= preg_quote($c, '@');        }        $regex .= '$@i';        return (bool)preg_match($regex, $string);    }    function _find ($id_params, $start_with) {        global $_mircparser_mirc_dir, $_mircparser_directory_tree;        if (!isset($id_params[0])) return '';        $path     = strtolower($id_params[0]);        if (!isset($id_params[1])) return '';        $wildcard = strtolower($id_params[1]);        if (!isset($id_params[2])) return '';        $nth      = $id_params[2];        if (!isset($id_params[3])) { $depth = 0; $cmd_or_win = ''; }        elseif (isset($id_params[3]) && ctype_digit($id_params[3])) {            $depth = $id_params[3];            if (isset($id_params[4])) $cmd_or_win = $id_params[4];            else $cmd_or_win = '';        } else { $depth = 0; $cmd_or_win = $id_params[3]; }        $path = str_replace('/', '\\', $path);        if ($path{1} != ':')            $path = $_mircparser_mirc_dir . ($path{0}=='.'?substr($path,1):$path);        $partition = strtoupper($path{0});        if (!isset($_mircparser_directory_tree[$partition])) return '';        $crt = &$_mircparser_directory_tree[$partition];        //explode everything after first \\        //e.x.: c:\a\b\c makes:        //array("a", "b", "c")        $dirlist = explode('\\', substr($path,strpos($path,'\\')+1) );        foreach ($dirlist as $dir) {            if ($dir == '') continue;            if (!isset($crt['d:'.$dir])) return '';            else $crt = &$crt['d:'.$dir];        }        //now $crt points to the structure of the current directory        if (!is_array($crt)) return '';        $to_find = $start_with . $wildcard;        $matches = 0;        //we won't really use a depth, that would be just complicating        //for no reason and making the find slower and possible DoS-able        //so it would use a depth of 1        foreach ($crt as $i => $v) {            if (is_array($v)) $item_name = $i;            else $item_name = $v;            if ($this->iswm($to_find, $item_name)) {                $matches++;                if ( ($cmd_or_win != '' && $cmd_or_win{0}!='@') &&                    ($matches == $nth || $nth == 0) ) {                    $this->_used_commands[] = $cmd_or_win;                }                if ($matches == $nth)                    return $path . substr($item_name,strlen($start_with));            }        }        if ($nth == 0) return $matches;        return '';    }            //by weekend    function _basic ($str)    {        //function to convert sertant mirc stuffs        //its just a replace...        //NOTE: this WILL do newline and whatnot so remove that if needed!        global $_mircparser_mirc_dir;        $from = array();        $to = array();        $nick        = &$this->_info['nick'];        $addr        = &$this->_info['addr'];        $addr_server = &$this->_info['addr_server'];        $chan        = &$this->_info['chan'];        $name        = &$this->_info['name'];        $me          = &$this->_info['me'];        $port        = &$this->_info['port'];        $s_string    = &$this->_info['s_string'];        $version     = &$this->_info['version'];                        //stefys:        //would have been nicer to store them only once instead of initializing array everytime the function is called        $from[] = ' $address';          $to[] = $addr;        $from[] = ' $nick';             $to[] = $nick;        $from[] = ' $server';           $to[] = $addr_server;        $from[] = ' $serverip';         $to[] = '127.0.0.1';        $from[] = ' $status';           $to[] = 'connected';        $from[] = ' $show';             $to[] = '$true';        $from[] = ' $ulevel';           $to[] = '1';        $from[] = ' $snicks';           $to[] = '';        $from[] = ' $snotify';          $to[] = '';        $from[] = ' $sreq';             $to[] = 'ask';        $from[] = ' $ssl';              $to[] = '$true';        $from[] = ' $sslready';         $to[] = '$true';        $from[] = ' $ticks';            $to[] = '42569'.rand(111,999);        $from[] = ' $time';             $to[] = date("H:i:s");        $from[] =  '$timestamp';        $to[] = date("[H:i:s]");        $from[] =  '$timestampfmt';     $to[] = '[HH:nn:ss]';        $from[] =  '$timezone';         $to[] = '25200';        $from[] = ' $titlebar';         $to[] = '';        $from[] = ' $url';              $to[] = 'http://www.hackthissite.org';        $from[] = ' $usermode';         $to[] = '+iwghrsOxqBzt';        $from[] = ' $vcmdver';          $to[] = '$null';        $from[] = ' $vcmdstat';         $to[] = '0';        $from[] = ' $version';          $to[] = $version;        $from[] = ' $wid';              $to[] = '6';        $from[] = ' $site';             $to[] = '';        $from[] = ' $wildsite';         $to[] = '';        $from[] = ' $active';           $to[] = $chan;        $from[] = ' $activecid';        $to[] = '1';        $from[] = ' $cid';              $to[] = '1';        $from[] = ' $activewid';        $to[] = '7';        $from[] = ' $agentname';        $to[] = '';        $from[] = ' $anick';            $to[] = 'altnick';        $from[] = ' $aop';              $to[] = '$false';        $from[] = ' $appactive';        $to[] = '$true';        $from[] = ' $appstate';         $to[] = 'maximized';        $from[] = ' $avoice';           $to[] = '$false';        $from[] = ' $away';             $to[] = '$false';        $from[] = ' $cb';               $to[] = '';        $from[] = ' $cr';               $to[] = "\r";        $from[] = ' $crlf';             $to[] = "\r\n";        $from[] = ' $chan';             $to[] = $chan;        $from[] = ' $chanmodes';        $to[] = 'beI,kfL,lj,psmntirRcOAQKVCuzNSMTG';        $from[] = ' $chantypes';        $to[] = '#';        $from[] = ' $cid';              $to[] = '1';        $from[] = ' $cmdbox';           $to[] = '$false';        $from[] = ' $creq';             $to[] = 'ask';        $from[] = ' $ctime';            $to[] = time();        $from[] = ' $date';             $to[] = date("d/m/Y");        $from[] = ' $adate';            $to[] = date("m/d/Y");        $from[] = ' $day';              $to[] = date("l");        $from[] = ' $daylight';         $to[] = ((date("I") == 1) ? "3600" : "0");        $from[] = ' $dccignore';        $to[] = '$false';        $from[] = ' $dccport';          $to[] = '59';        $from[] = ' $dlevel';           $to[] = '1';        $from[] = ' $emailaddr';        $to[] = 'moo@cowland.com';        $from[] = ' $ferr';             $to[] = '0';        $from[] = ' $filtered';         $to[] = '0';        $from[] = ' $fulladdress';      $to[] = $addr;        $from[] = ' $fulldate';         $to[] = date("D M j G:i:s Y");        $from[] = ' $fullname';         $to[] = $name;        $from[] = ' $gmt';              $to[] = time();        $from[] = ' $highlight';        $to[] = '$false';        $from[] = ' $host';             $to[] = 'www.hackthissite.org';        $from[] = ' $idle';             $to[] = '0';        $from[] = ' $ip';               $to[] = '127.0.0.1';        $from[] = ' $lf';               $to[] = "\n";        $from[] = ' $locked';           $to[] = '$false';        $from[] = ' $logdir';           $to[] = $_mircparser_mirc_dir.'logs\\';        $from[] = ' $logstamp';         $to[] = date("[H:i:s]");        $from[] = ' $logstampfnt';      $to[] = '[HH:nn:ss]';        $from[] = ' $ltimer';           $to[] = '4';        $from[] = ' $me';               $to[] = $me;        $from[] = ' $mididir';          $to[] = $_mircparser_mirc_dir.'sounds\\';        $from[] = ' $mircdir';          $to[] = $_mircparser_mirc_dir;        $from[] = ' $mircexe';          $to[] = $_mircparser_mirc_dir.'mirc.exe';        $from[] = ' $mircini';          $to[] = $_mircparser_mirc_dir.'mirc.ini';        $from[] = ' $mnick';            $to[] = $me;        $from[] = ' $network';          $to[] = 'HackThisSite';        $from[] = ' $os';               $to[] = 'XP';        $from[] = ' $passivedcc';       $to[] = '$false';        $from[] = ' $port';             $to[] = $port;        $from[] = ' $portable';         $to[] = '$false';        $from[] = ' $prefix';           $to[] = '~&@%+';        $from[] = ' $rawline';          $to[] = $s_string;        $from[] = ' $script';           $to[] = 'script.mrc';        $from[] = ' $scriptdir';        $to[] = $_mircparser_mirc_dir;        $from[] = ' $scriptline';       $to[] = '40';        //that should do..        return str_replace($from, $to, $str);    }        function get_parsed_string () {        return $this->_str;    }        //the one replaced by _basic() are not shown here    function get_used_identifiers () {        return $this->_used_identifiers;    }        // an array with commands executed with $finddir() or $findfile    function get_used_commands () {        return $this->_used_commands;    }}/* Usage$code = '$findfile(.,*,1,lol) $finddir(c:/,*w*,1,echo -a found!) $right(abcdef,2)';$vars = array('d' => 'omg var worked', 'a' => 5, 'b' => 6);//function Mircparser ($mirc_code, $variables, $nick, $addr, $addr_server, $chan, $name, $me, $port, $s_string, $version)$mircparser = new Mircparser($code, $vars, 'YourNick', 'Addr', 'AddrServer', '#Chan', 'Name', 'MyNick', '12345', 'S_string', 4);echo $mircparser->get_parsed_string();print_r($mircparser->get_used_commands()); */?>