做淘宝优惠券的时候,搞了一套网站的源码,不过是加密的,现在来尝试解密来熟悉正则表达式
[], '$_GET' => [], '$GLOBALS' => [], ]; foreach ($GLOBALS as $key => $value) { $encode = mb_detect_encoding($key, array("ASCII")); if ($encode !== 'ASCII') { //$CommonVar['$GLOBALS'][$key] = $value; } } foreach ($_GET as $key => $value) { $encode = mb_detect_encoding($key, array("ASCII")); if ($encode !== 'ASCII') { //$CommonVar['$_GET'][$key] = $value; } } foreach ($_SERVER as $key => $value) { $encode = mb_detect_encoding($key, array("ASCII")); if ($encode !== 'ASCII') { //$CommonVar['$_SERVER'][$key] = $value; } } //halt(get_defined_constants()); header('Content-type:text/html;Charset=utf-8'); $filePath = 'application/index/controller/Goods.php'; $output = file_get_contents($filePath); //dump($output); $allVar = []; getphpCode($output, $allVar, $ErrString); $pat_array = []; $this->replace_all_isset_global($output, $CommonVar); //最后的文本将$this->request->{'param'}类似的转化 $pattner = '/\{\'([a-zA-Z_]*?)\'\}/'; preg_match_all($pattner, $output, $pat_array); foreach ($pat_array[0] as $key => $value) { $output = str_replace($value, $pat_array[1][$key], $output); } //将最后的文本 defind(xx,xxx); 删掉 $pattner = '/define\([\s\S]*?\)\;/'; preg_match_all($pattner, $output, $pat_array); foreach ($pat_array[0] as $key => $value) { $output = str_replace($value, '', $output); } //将最后的文本中 return $this->success( -> $this->success( //将最后的文本中 return $this->error( -> $this->error( $output = str_replace('return $this->success(', '$this->success(', $output); $output = str_replace('return $this->error(', '$this->error(', $output); dump($pat_array); dump($CommonVar); dump($output); put_stop($output); die; } /** info:替换所有的已经定义的变量 * @param $output * @param $CommonVar */ public function replace_all_isset_global(&$output,&$CommonVar){ //先匹配是否有$Ser[xxx] = explode(xxx)格式的,将如$CommonVar //匹配是否有explode的数据 $pattern = '/(\$_SERVER|\$_GET|\$GLOBALS)(\{(.*?)\}|\[(.*?)\])[\s]?\=[\s]?explode\(\'(.*?)\',[\s]*([\s\S]*?)\)\;/'; $result = preg_match($pattern, $output, $pat_array); if($result){ //explode\('([\s\S]*?)',[\s]*(gzinflate\(substr\('([\s\S]*?)',[\s\S]*?,[\s\S]*?\)\))\)\; $pattern = '/(\$_SERVER|\$_GET|\$GLOBALS)(\{(.*?)\}|\[(.*?)\])[\s]?\=[\s]?(explode\(\'(.*?)\',[\s]?(gzinflate\(substr\(\'([\s\S]*?)\',[\s\S]*?,[\s\S]*?\)\))\))\;/'; $result = preg_match($pattern, $output, $pat_array_li); if($result){ //匹配gzinflate 需要解压缩 $pat_array = $pat_array_li; $explode_result = return_explode($pat_array[5]); if(empty($explode_result[0])){ $explode_result = explode($pat_array[6],gzinflate_decode($pat_array[8])); if(empty($explode_result[0])){ getphpCode($output, $allVar, $gzinflateStr); dump('错误!'); halt($gzinflateStr); } } dump('解析出数组'); dump($explode_result); $variable_name = $pat_array[1]; if(!empty($pat_array[3])){ $key_name = $pat_array[3]; }else{ $key_name = $pat_array[4]; } $CommonVar[$variable_name][$key_name] = $explode_result; $str = PHP_EOL . $variable_name . '[' . $key_name . '] = ' . array_format_echo($explode_result) . ';' . PHP_EOL; //如果匹配上了的话,将字符串格式话成数组拼接转化 $output = str_replace($pat_array[0], $str, $output); $this->replace_all_global_variable($output,$CommonVar); //put_stop($output); //转换之后 删除第一次匹配 $output = str_replace($str, PHP_EOL, $output); }else{ ob_clean(); //没有匹配到需要gzinflate解码的数据 //不需要解压缩,直接获得explode之后的数据 //$pattern = '/(\$_SERVER|\$_GET|\$GLOBALS)(\{([\s\S]*?)\}|\[([\s\S]*?)\])[\s]?\=[\s]?explode\(\'([\s\S]*?)\',[\s]?\'(.*?)\'\)\;/'; //注意: 由于正则表达式中 . 表示出换行符以外的所有单个字符,所以需要用到[\s\S] $pattern = '/(\$_SERVER|\$_GET|\$GLOBALS)(\{(.*?)\}|\[(.*?)\])[\s]?\=[\s]?explode\(\'(.*?)\',[\s]?\'([\s\S]*?)\'\)\;/'; $result = preg_match($pattern, $output, $pat_array); dump('66'); if($result){ $variable_name = $pat_array[1]; //如果匹配到第三个、第四个有一个OK if(!empty($pat_array[3])){ $key_name = $pat_array[3]; }else{ $key_name = $pat_array[4]; } //explode爆裂后的数据 $explode_result = explode($pat_array[5],stripcslashes($pat_array[6])); if(count($explode_result)>1){ //加入全局数组 $CommonVar[$variable_name][$key_name] = $explode_result; }else{ $explode_result = explode($pat_array[5],$pat_array[6]); //加入全局数组 $CommonVar[$variable_name][$key_name] = $explode_result; } //将匹配到的explode格式话成数组格式 $str = PHP_EOL . $variable_name . '[' . $key_name . '] = ' . array_format_echo($explode_result) . ';' . PHP_EOL; $output = str_replace($pat_array[0], $str, $output); //替换所有变量 $this->replace_all_global_variable($output,$CommonVar); //转换之后 删除第一次匹配 $output = str_replace($str, PHP_EOL, $output); } } dump($output); //替换文中引用全局变量的变量 $this->replace_yinyong_variables($output,$CommonVar); dump($CommonVar); //持续替换已定义的变量 $this->replace_all_isset_global($output,$CommonVar); } else{ //ob_clean(); //halt($CommonVar); //替换文中引用全局变量的变量 //$this->replace_yinyong_variables($output,$CommonVar); //替换所有变量 $this->replace_all_global_variable($output,$CommonVar); } } //替换所有的全局变量 public function replace_all_global_variable(&$output,&$CommonVar){ $End = 0; foreach($CommonVar as $variable_name=>$variable_value){ $break = 0; foreach($variable_value as $key=>$value){ $explode_result = $CommonVar[$variable_name][$key]; dump($variable_name); dump($key); $key = trim($key,'\''); //四种 $variable_name[$value] //四种 $variable_name['\''.$value.'\''] //四种 $variable_name{$value} //四种 $variable_name{'\''.$value.'\''} $i=0; $pattern[1] = '/'.preg_quote($variable_name.'['.$key.']').'(\{([^\{^\[]*?)\}|\[([^\[^\{]*?)\])/'; $pattern[2] = '/'.preg_quote($variable_name.'[\''.$key.'\']').'(\{([^\{^\[]*?)\}|\[([^\[^\{]*?)\])/'; $pattern[3] = '/'.preg_quote($variable_name.'{'.$key.'}').'(\{([^\{^\[]*?)\}|\[([^\[^\{]*?)\])/'; $pattern[4] = '/'.preg_quote($variable_name.'{\''.$key.'\'}').'(\{([^\{^\[]*?)\}|\[([^\[^\{]*?)\])/'; foreach($pattern as $k=>$v){ preg_match_all($v,$output,$pat_array); dump($pat_array); if(count($pat_array[0])>0){ $this->replace_global_variable($output,$pat_array,$explode_result); }else{ $i++; } } if($i==4){ //如果四种模式都没有匹配,父级foreach跳出 $break=1; continue; } } if($break==1){ $End = 1; continue; } } if($End !== 1){ $this->replace_all_global_variable($output,$CommonVar); } } public function replace_global_variable(&$output, $pat_array, $explode_result) { foreach ($pat_array[0] as $key => $value) { $index = $pat_array[2][$key]; if ($index !== '') { //dump($index); if (isset($explode_result[$index])) { $relace_str = $explode_result[$index]; //dump('有-'.$relace_str); if (!function_exists($relace_str)) { $relace_str = array_format_echo($relace_str); } //dump($value);dump('=>');dump($relace_str); $output = str_replace($value, $relace_str, $output); }else{ //dump('没有'); } } } //一个是字符串 foreach ($pat_array[0] as $key => $value) { $index = $pat_array[3][$key]; if ($index !== '') { if (isset($explode_result[$index])) { $relace_str = $explode_result[$index]; //dump('有-'.$relace_str); if (!function_exists($relace_str)) { $relace_str = array_format_echo($relace_str); } //dump($value);dump('=>');dump($relace_str); $output = str_replace($value, $relace_str, $output); }else{ //dump('没有'); } } } } /** 匹配到 $var_xx = &$Goll[xx]; * @param $output * @param $CommonVar */ public function replace_yinyong_variables(&$output,&$CommonVar){ $pattern = '/(\$var_[0-9]*?)+[\s]?\=[\s]?[\&]?[\s]?((\$_SERVER|\$_GET|\$GLOBALS)(\{([^\[^\{]+?)\}|\[([^\[^\{]+?)\]+?))\;/'; preg_match_all($pattern, $output, $pat_array); //匹配所有经引用的变量 dump('匹配所有经引用的变量'); dump($pat_array); if (count($pat_array[0])>0) { foreach ($pat_array[5] as $key => $value) { $replcae_var = $pat_array[1][$key]; $variable_name = $pat_array[3][$key]; $key_name = $value; if(isset($CommonVar[$variable_name][$key_name])){ $decode_result = $CommonVar[$variable_name][$key_name]; }else{ $decode_result = $CommonVar[$variable_name]['\''.$key_name.'\'']; } $CommonVar[$replcae_var] = $CommonVar[$variable_name]; if(!empty($decode_result)){ $pattern = '/' . preg_quote($replcae_var) . '(\{([^\[]+?)\}|\[([^\}]+?)\]+?)/'; preg_match_all($pattern, $output, $pat_array_li); $this->replace_global_variable($output,$pat_array_li,$decode_result); //清除无效的 $output = str_replace($pat_array[0][$key], PHP_EOL, $output); } } //开始替换: 方法里面重新定义变量,引用了全局变量 } }}