scan.ctrl.php 7.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213
  1. <?php
  2. /**
  3. * [WeEngine System] Copyright (c) 2014 WE7.CC
  4. * WeEngine is NOT a free software, it under the license terms, visited http://www.we7.cc/ for more details.
  5. */
  6. defined('IN_IA') or exit('Access Denied');
  7. set_time_limit(0);
  8. load()->func('file');
  9. $dos = array('post', 'count', 'filter_func', 'filter_code', 'encode', 'display','view');
  10. $do = in_array($do, $dos) ? $do : 'post';
  11. $_W['page']['title'] = '木马查杀 - 常用系统工具 - 系统管理';
  12. if ($do == 'post') {
  13. $config = iunserializer(cache_read('scan:config'));
  14. $list = glob(IA_ROOT.'/*', GLOB_NOSORT);
  15. $ignore = array('data','attachment');
  16. foreach ($list as $key => $li) {
  17. if (in_array(basename($li), $ignore)) {
  18. unset($list[$key]);
  19. }
  20. }
  21. $safe = array (
  22. 'file_type' => 'php|js',
  23. 'code' => 'weidongli|sinaapp|safedog',
  24. 'func' => 'com|system|exec|eval|escapeshell|cmd|passthru|base64_decode|gzuncompress',
  25. 'dir' => '',
  26. );
  27. if (checksubmit('submit')) {
  28. if (empty($_GPC['dir'])) {
  29. itoast('请选择要扫描的目录', referer(), 'success');
  30. }
  31. foreach ($_GPC['dir'] as $k => $v) {
  32. if (in_array(basename($v), $ignore)) {
  33. unset($_GPC['dir'][$k]);
  34. }
  35. }
  36. $info['file_type'] = 'php|js';
  37. $info['func'] = trim($_GPC['func']) ? trim($_GPC['func']) : 'com|system|exec|eval|escapeshell|cmd|passthru|base64_decode|gzuncompress';
  38. $info['code'] = trim($_GPC['code']) ? trim($_GPC['code']) : 'weidongli|sinaapp';
  39. $info['md5_file'] = trim($_GPC['md5_file']);
  40. $info['dir'] = $_GPC['dir'];
  41. cache_delete('scan:config');
  42. cache_delete('scan:file');
  43. cache_delete('scan:badfile');
  44. cache_write('scan:config', iserializer($info));
  45. itoast("配置保存完成,开始文件统计。。。", url('system/scan', array('do' => 'count')), 'success');
  46. }
  47. }
  48. if ($do == 'count') {
  49. $files = array();
  50. $config = iunserializer(cache_read('scan:config'));
  51. if (empty($config)) {
  52. itoast('获取扫描配置失败', url('system/scan'), 'error');
  53. }
  54. $config['file_type'] = explode('|', $config['file_type']);
  55. $list_arr = array();
  56. foreach ($config['dir'] as $v) {
  57. if (is_dir($v)) {
  58. if (!empty($config['file_type'])) {
  59. foreach ($config['file_type'] as $k) {
  60. $list_arr = array_merge($list_arr, file_lists($v . '/', 1, $k, 0, 1, 1));
  61. }
  62. }
  63. } else {
  64. $list_arr = array_merge($list_arr, array(str_replace(IA_ROOT . '/', '', $v) => md5_file($v)));
  65. }
  66. }
  67. unset($list_arr['data/config.php']);
  68. $list_arr = iserializer($list_arr);
  69. cache_write('scan:file', $list_arr);
  70. itoast("文件统计完成,进行特征函数过滤。。。", url('system/scan', array('do' => 'filter_func')), 'success');
  71. }
  72. if ($do == 'filter_func') {
  73. $config = iunserializer(cache_read('scan:config'));
  74. $file = iunserializer(cache_read('scan:file'));
  75. if (isset($config['func']) && !empty($config['func'])) {
  76. foreach ($file as $key => $val) {
  77. $html = file_get_contents(IA_ROOT . '/' . $key);
  78. if (stristr($key, '.php.') != false || preg_match_all('/[^a-z]?('.$config['func'].')\s*\(/i', $html, $state, PREG_SET_ORDER)) {
  79. $badfiles[$key]['func'] = $state;
  80. }
  81. }
  82. }
  83. if (!isset($badfiles)) $badfiles = array();
  84. cache_write('scan:badfile', iserializer($badfiles));
  85. itoast("特征函数过滤完成,进行特征代码过滤。。。", url('system/scan', array('do' => 'filter_code')), 'success');
  86. }
  87. if ($do == 'filter_code') {
  88. $config = iunserializer(cache_read('scan:config'));
  89. $file = iunserializer(cache_read('scan:file'));
  90. $badfiles = unserialize(cache_read('scan:badfile'));
  91. if (isset($config['code']) && !empty($config['code'])) {
  92. foreach ($file as $key => $val) {
  93. if (!empty($config['code'])) {
  94. $html = file_get_contents(IA_ROOT . '/' . $key);
  95. if (stristr($key, '.php.') != false || preg_match_all('/[^a-z]?('.$config['code'].')/i', $html, $state, PREG_SET_ORDER)) {
  96. $badfiles[$key]['code'] = $state;
  97. }
  98. }
  99. if (strtolower(substr($key, -4)) == '.php' && function_exists('zend_loader_file_encoded') && zend_loader_file_encoded(IA_ROOT . '/' . $key)) {
  100. $badfiles[$key]['zend'] = 'zend encoded';
  101. }
  102. $html = '';
  103. }
  104. }
  105. cache_write('scan:badfile', iserializer($badfiles));
  106. itoast("特征代码过滤完成,进行加密文件过滤。。。", url('system/scan', array('do' => 'encode')), 'success');
  107. }
  108. if ($do == 'encode') {
  109. $file = iunserializer(cache_read('scan:file'));
  110. $badfiles = iunserializer(cache_read('scan:badfile'));
  111. foreach ($file as $key => $val) {
  112. if (strtolower(substr($key, -4)) == '.php') {
  113. $html = file_get_contents(IA_ROOT . '/' . $key);
  114. $token = token_get_all($html);
  115. $html = '';
  116. foreach ($token as $to) {
  117. if (is_array($to) && $to[0] == T_VARIABLE) {
  118. $pre = preg_match("/([".chr(0xb0)."-".chr(0xf7)."])+/", $to[1]);
  119. if (!empty($pre)) {
  120. $badfiles[$key]['danger'] = 'danger';
  121. break;
  122. }
  123. }
  124. }
  125. }
  126. }
  127. cache_write('scan:badfile', iserializer($badfiles));
  128. itoast("扫描完成。。。", url('system/scan', array('do' => 'display')), 'success');
  129. }
  130. if ($do == 'display') {
  131. $badfiles = iunserializer(cache_read('scan:badfile'));
  132. if (empty($badfiles)) {
  133. itoast('没有找到扫描结果,请重新扫描', url('system/scan'), 'error');
  134. }
  135. unset($badfiles['data/config.php']);
  136. foreach ($badfiles as $k => &$v) {
  137. $v['func_count'] = 0;
  138. if (isset($v['func'])) {
  139. $v['func_count'] = count($v['func']);
  140. foreach ($v['func'] as $k1 => $v1) {
  141. $d[$k1] = strtolower($v1[1]);
  142. }
  143. $d = array_unique($d);
  144. $v['func_str'] = implode(', ', $d);
  145. }
  146. $v['code_count'] = 0;
  147. if (isset($v['code'])) {
  148. $v['code_count'] = count($v['code']);
  149. foreach ($v['code'] as $k2 => $v2) {
  150. $d1[$k2] = strtolower($v2[1]);
  151. }
  152. $d1 = array_unique($d1);
  153. $v['code_str'] = implode(', ', $d1);
  154. }
  155. }
  156. }
  157. if ($do == 'view') {
  158. $file = authcode(trim($_GPC['file'], 'DECODE'));
  159. $file_tmp = $file;
  160. $file = str_replace('//','',$file);
  161. if (empty($file) || ! parse_path($file) || $file == 'data/config.php') {
  162. itoast('文件不存在', referer(), 'error');
  163. }
  164. $file_arr = explode('/', $file);
  165. $ignore = array('payment');
  166. if (is_array($file_arr) && in_array($file_arr[0], $ignore)) {
  167. itoast('系统不允许查看当前文件', referer(), 'error');
  168. }
  169. $file = IA_ROOT . '/' . $file;
  170. if (!is_file($file)) {
  171. itoast('文件不存在', referer(), 'error');
  172. }
  173. $badfiles = iunserializer(cache_read('scan:badfile'));
  174. $info = $badfiles[$file_tmp];
  175. unset($badfiles);
  176. if (!empty($info)) {
  177. $info['func_count'] = 0;
  178. if (isset($info['func'])) {
  179. $info['func_count'] = count($info['func']);
  180. foreach ($info['func'] as $k1 => $v1) {
  181. $d[$k1] = strtolower($v1[1]);
  182. }
  183. $d = array_unique($d);
  184. $info['func_str'] = implode(', ', $d);
  185. }
  186. $info['code_count'] = 0;
  187. if (isset($info['code'])) {
  188. $info['code_count'] = count($info['code']);
  189. foreach ($info['code'] as $k2 => $v2) {
  190. $d1[$k2] = strtolower($v2[1]);
  191. }
  192. $d1 = array_unique($d1);
  193. $info['code_str'] = implode(', ', $d1);
  194. }
  195. }
  196. $data = file_get_contents($file);
  197. }
  198. template('system/scan');