LOAD DATA LOCAL INFILE在phpmyadmin4.0.10版本后的应用
@ s1ye · Saturday, Feb 29, 2020 · 3 · Feb 29, 2020

LOAD DATA LOCAL INFILE

很早之前就出现的问题了,文章中不会过多的复述相关知识,谷歌关键词搜索“mysql 客户端任意文件读取”。

介绍

# 简单来了解一下官方文档吧。

The LOAD DATA statement can load a file located on the server host, or, if the LOCAL keyword is specified, on the client host.

There are two potential security issues with the LOCAL version of LOAD DATA:

1. The transfer of the file from the client host to the server host is initiated by the MySQL server. In theory, a patched server could be built that would 
tell the client program to transfer a file of the server's choosing rather than the file named by the client in the LOAD DATA statement. Such a server could
access any file on the client host to which the client user has read access. (A patched server could in fact reply with a file-transfer request to any 
statement, not just LOAD DATA LOCAL, so a more fundamental issue is that clients should not connect to untrusted servers.)

2. In a Web environment where the clients are connecting from a Web server, a user could use LOAD DATA LOCAL to read any files that the Web server process 
has read access to (assuming that a user could run any statement against the SQL server). In this environment, the client with respect to the MySQL server 
actually is the Web server, not a remote program being run by users who connect to the Web server.

重点看这两个潜在的安全问题,简单来说就是:

  • 利用该语句可以访问客户端用户具有读取访问权限的客户端主机上的任何文件。
  • 在客户端是从web服务器进行连接的web环境中(例如:phpmyadmin),利用该语句可以读取Web服务器进程具有读取权限的任何文件。

文档中也有解释,在web充当客户端这种web环境中,相对于mysql服务器的客户端是web服务器。说的再简单一些,利用load data local infile读取文件的权限,等同于你php的权限(php为后端语言的情况),php能读/etc/passwd那用改语句也可以读。因此就产生了两个利用条件:

  • php.ini:open_basedir
  • my.ini:local_infile = 1

mysql客户端中的利用

可以看到默认secure_file_priv的value是NULL,需要我们手动去改才能使用load data infile,但是加了local后可以直接读文件,并不受这个限制。

phpmyadmin中的问题

环境为phpmyadmin5.0.1,官方最新版了吧

可以看到,插入了0行。同样是root,同样是使用了local,php也并没有设置open_basedir,很好奇为什么读不到数据。问了同事他说也没遇到过,同事通过查看phpmyadmin的源代码告诉我可以绕过(感谢我老铁的帮助Orz),同时我在phpmyadmin的官方github commit中找到了问题。

绕过限制

github 中2016年的commit

Enable LOAD DATA LOCAL INFILE only when needed

可以发现由于客户端文件读取那个漏洞,phpmyadmin将默认不能使用local infile这个功能,而是将他放入了LDI这个插件中,只有导入了该插件才可以使用该功能。(但是我发现默认并没有这个插件,也有可能后面的版本给移除了,但是功能还在?)

再来看一下修改的代码部分:

没有什么验证,只要post format=1即可define PMA_ENABLE_LDI =1。我下载了最新版的phpmyadmin看了一下源代码,依旧如此。

因此当可以登陆phpmyadmin却不知道根路径或者无法写文件时,也许我们又至少多了一条路可以走

最后

还跟同事开玩笑说让他赶紧交了phpmyadmin 0day,不过顶多算一个bug吧。另外如果文中出现笔误,或者哪里理解错误还望及时指出联系我更改,以免误人子弟。

仅此记录2020,艹

2020.06.11 学校突然说不给我毕业证,经查明有一门课任课老师忘记给录成绩,与学校多次协商无果,心情烦躁,工作也不是很顺心,决定辞职。

2020.06.18 正式离职,与学校老师以及领导继续对线,恰巧赶上hw想着去赚点钱好好休息一段时间再找下一份工作。

2020.06.19 北京疫情爆发,无法进京参加hw,在大连租住地边学习边跟学校继续对线。

2020.06.24 多次与老师和领导反应,互相踢皮球,老师叫我联系领导解决,领导叫我联系老师解决,最终将学校举报到省教育厅。

2020.06.28 由于省教育厅联系学校解决此事,端午节假期结束后第一时间,学校领导及任课教师开会重新讨论该事件,最终给予我审核通过,颁发毕业证。ps: 就离谱,我自己协商不同意,举报以后就管用了? : )

2020.07.25 期间一直在家里自己搞技术玩,厂商通知去吉林hw,收拾东西准备前往。

2020.07.26 大连疫情爆发,吉林厂商不允许大连相关人员入场,需要隔离14天。

2020.07.30 经过多天预约,终于做了核酸检测,收拾装备,准备离连。

2020.08.02 连夜回到家中,父母不在家,又是无尽的孤独。甚至保安见到我大连回来的躲得远远的,并且说了句“和他一栋楼的,完了!”,????

2020.08.16 总hw次日开始,抵达杭州,17号晚班8点开始。

2020.08.17 晚八点抵达工作地点,打开电脑,收到消息9点后redteam不允许攻击,随便看看流量就写代码去了。九点十分,甲方通知护网暂停,择日开启 : ) 。

2020.08-xx 过几天马上去成都了,“巴威”来了,我希望您别影响我飞机起飞,谢谢。

以后再hw我就是个sb,要不是学校的破事心烦不想立刻工作恰巧赶上了hw,想着呆着不如多赚点,我是万万不可能参加的。hw1.5时,歇逼两个月 :)

想去哪哪疫情,离开哪哪疫情,2020,当个人吧,求你了。

关于我

s1ye的❤️博客

平时会记录一些学习笔记或分享有趣的姿势

一个热爱技术的普通网络安全从业者

团队

所在团队🌈 :ChaBug

ID:s1ye(撕夜,)

可以通过email1联系我,

- 2020 年 2 月 8 日更新


  1. [email protected] ↩︎