您的位置:首页 > 编程语言 > PHP开发

利用Sulley测试easyftp服务器

2017-11-07 23:46 162 查看

测试easyftp

这次的目标就是easyftp。直接运行easyftp.exe就能启动FTP服务了。让我们先了解下FTP协议的工作流程。

1、FTP

FTP是一个简单轻便的文件传输协议,被广泛的使用于各种环境中,从Web服务器到网络打印机。FTP服务器默认在端口21上监听客户端发送的命令。现在我们要冒充成FTP客户端,向服务器发送变形过的命令数据,尝试获得服务器的权限。一个FTP服务器既可以设置成不需要密码的匿名访问或者是需要密码的认证访问。FTP认证命令的格式如下:

USER <USERNAME>
PASS <PASSWORD>


一旦客户端传入了有效的用户名和密码后,服务器就会赋予客户端,传输文件,改变目录,查询文件等各种权限。当然USER和PASS命令只是FTP服务器提供的功能中的一个子集,在认证成功后还有很多别的功能,如下。这些新的命令都要加入到我们程序的协议框架(protocol skeleton)中。FTP协议详细的命令,请看rfc959。

CWD - change working directory to DIRECTORY

DELE - delete a remote file FILENAME

MDTM - return last modified time for file FILENAME

MKD - create directory DIRECTORY

2、创建FTP协议框架

#ftp.py
from sulley import *
s_initialize("user")
s_static("USER")
s_delim(" ")
s_string("justin")
s_static("\r\n")
s_initialize("pass")
s_static("PASS")
s_delim(" ")
s_string("justin")
s_static("\r\n")
s_initialize("cwd")
s_static("CWD")
s_delim(" ")
s_string("c: ")
s_static("\
4000
r\n")
s_initialize("dele")
s_static("DELE")
s_delim(" ")
s_string("c:\\test.txt")
s_static("\r\n")
s_initialize("mdtm")
s_static("MDTM")
s_delim(" ")
s_string("C:\\boot.ini")
s_static("\r\n")
s_initialize("mkd")
s_static("MKD")
s_delim(" ")
s_string("C:\\TESTDIR")
s_static("\r\n")


协议框架完成之后,开始创建Sulley会话,把所有的请求信息连起来,同时启动进程和网络监控代理。

3、Sulley会话

Sulley会话包含了请求数据整合,网络数据包的捕捉,进程调试,崩溃报告,和虚拟机控制。先让我们定义一个会话文件,然后详细的分析每个部分。

#coding=utf-8
from sulley import *
from requests import ftp
# this is our ftp.py file
def receive_ftp_banner(sock):
sock.recv(1024)

sess = sessions.session(session_filename="D:\\Program Files (x86)\\Sulley\\sulley-master1\\audits\\easyftpserver.session",sleep_time=0.01)
target = sessions.target("192.168.0.100", 21)
target.netmon = pedrpc.client("192.168.0.100",26001)
target.procmon = pedrpc.client("192.168.0.100", 26002)
target.procmon_options = \
{
"proc_name" : "easyftp.exe",
"stop_commands" : ['net stop "trend serverprotect"'],
"start_commands" : ['net start "trend serverprotect"'],
}

# Here we tie in the receive_ftp_banner function which receives
# a socket.socket() object from Sulley as its only parameter
sess.pre_send = receive_ftp_banner
sess.add_target(target)
sess.connect(s_get("user"))
sess.connect(s_get("user"), s_get("pass"))
sess.connect(s_get("pass"), s_get("cwd"))
sess.connect(s_get("pass"), s_get("dele"))
sess.connect(s_get("pass"), s_get("mdtm"))
sess.connect(s_get("pass"), s_get("mkd"))
sess.fuzz()


receive_ftp_banner()是必须的,因为每个FTP服务器在客户端连接上的时候,都会发送banner(标识)。我们将它和sess.pre_send 绑定起来,这样Sulley发送fuzzing数据前的时候就会先接收FTP banner。

和receive_ftp_banner一样,pre_send也只接收一个由Sulley传递的sock对象。

第一步我们创建一个会话文件,用于记录当前fuzzer的状态,同时控制fuzzing的启动和停止。

第二步定义攻击的目标,包括IP地址和端口号。这里设置成 192.168.0.100端口21(这是我们运行easyftp的主机IP)。

第三步,设置网络监控的端口为26001,IP地址和FTP服务器的地址一样,这个端口用于接受Sulley发出的命令。

第四步,设置调试器监听的端口26002,这个端口用于接收Sulley发出的调试命令。procmon_options选项告诉调试器我们关注的进程是easyftp.exe

第五步,在会话中加入定义好的目标对象。

第六步,将FTP请求指令有序的组织好。先是认证,然后将操作指令和需要的密码成对传入。最后启动Sulley开始fuzzing。

现在我们定义好了会话,组织好了请求指令。只剩下网络和监控脚本的设置了。当这一切都完成的时候,就可以去捕捉我们的猎物了。

4、网络和进程监控

Sulley的优点之一就是能非常好的跟踪fuzz期间的数据交互,以及目标系统的崩溃信息。这样我们就能在第一时间内分析出引起目标崩溃的数据包,然后快速的开发出exploit。

在Sulley的主目录下可以找到 process_monitor.py和network_monitor.py两个脚本,他们分别负责网络监控和进程监控。

python process_monitor.py

ERR> USAGE: process_monitor.py

<-c|–crash_bin FILENAME> filename to serialize crash bin class to

[-p|–proc_name NAME] process name to search for and attach to

[-i|–ignore_pid PID] ignore this PID when searching for the

target process

[-l|–log_level LEVEL] log level (default 1), increase for more

verbosity

[–port PORT] TCP port to bind this agent to

如下启动进程监控。

python process_monitor.py -c D:\easyftpserver.crash -p easyftp.exe




接下来看看network_monitor.py。

ERR> USAGE: network_monitor.py

<-d|–device DEVICE #> device to sniff on (see list below)

[-f|–filter PCAP FILTER] BPF filter string

[-P|–log_path PATH] log directory to store pcaps to

[-l|–log_level LEVEL] log level (default 1), increase for more verbosity

[–port PORT] TCP port to bind this agent to

Network Device List:

[0] {C2E1878A-A59A-4023-A4E5-77EE1ECCEFAE} 192.168.235.1

[1] {11E03B98-5931-490C-8617-EC82C36121B0}

[2] {E23A46F5-E2F9-46B7-B407-6868DF329C54} 192.168.75.1

[3] {554DA01B-6938-4FC5-A3C1-26CA49E8DF3D} 192.168.0.100

[4] {E0887D7D-3247-4896-ABAF-C0CDE3AC9C86}

在这里我们需要使用[3]网络接口。如下启动网络监控。

python network_monitor.py -d 3 -f "src or dst port 21" -P D:\pcaps\


提示:在启动之前必须先建立D:\pcaps目录。



一切就绪,开始猎食。

5、fuzzing和Web界面

现在我们启动Sulley,并使用内置的Web界面观察整个fuzz过程。

python ftp_session.py


输出如下:



如果输出是这样的,说明一切正常。Sulley正在繁忙的工作着。现在让我们看看Sulley的web界面,它会提供更多信息。

用浏览器打开http://127.0.0.1:26000,将看到类似图的结果。



不断的刷新浏览器就能看到当前fuzzing的进程,以及正在使用的请求和测试用例导致的崩溃信息。点击test case的数字,就会看到详细的崩溃信息,崩溃报告打开如下。



我们已经成功的Crash了easyftp,Sulley也捕捉到了所有相关的信息。我们看到两个测试用例的错误信息都是:当试图从0x021af000读取时,0042d063从线程6008的rep movsd导致访问冲突。

PyDbg崩溃信息格式在灰帽-Python之旅第四章60页的”访问违例处理程序”中有详细的讲解。当程序尝试访问它们没有权限访问的页面的时候或者以一种不合法的方式访问内存的时候,就会产生访问违例。导致违例错误的范围很广,从内存溢出到不恰当的处理空指针都有可能。从安全角度考虑,每一个访问违例都应该仔细的审查,因为它们有可能被利用。当调试器处理访问违例的时候,需要搜集所有和违例相关的信息,栈框架,寄存器,以及引起违例的指令。接着我们就能够用这些信息写一个利用程序或者创建一个二进制的补丁文件。

那接下来就是开发exploit攻击或者创建补丁修复软件了!

有了这次测试,我们对Sulley的工作方式已经很熟悉了,对于别的fuzzing对象也只要依葫芦画瓢就行了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: