ECHO · Write ups · CyberHawks Quals 2026

The CyberHawks Quals Write Ups

The UND CyberHawks National CTF Qualifiers is the University of North Dakota’s national qualifying round, hosted on Hack The Box and tied to the IEEE CARS 2026 conference, one day of virtual jeopardy across Web, Forensics, AI and ML, Reversing, Hardware, ICS and Crypto. ECHO Club, competing solo, full cleared it on 12 September 2026: ten of ten flags, 34th of 217 teams, with a Finals invitation to UND for October 26. These are three of those ten solves, written up end to end for anyone teaching or learning the same defensive lesson, ordered approachable to hard, every flag redacted.

Provenance

Solved 12 September 2026 during the UND CyberHawks National CTF Qualifiers (event 3444) on Hack The Box, organized by the University of North Dakota’s Center for Cyber Security Research and tied to the IEEE CARS 2026 conference. Quals ran 08:00 to 23:00 Mountain, entirely virtual, ranked jeopardy format. Solved solo by Digital Orukami for ECHO Club: 10 of 10 flags, 7,150 points, 34th of 217 teams, every category swept, including Web, AI and ML, Hardware and Crypto beyond the three covered below. The event explicitly permitted AI assisted work (Hack The Box’s own banner: “use AI to support your work, not to do it”).

These three are teaching write ups, not the full submission, one from each end of the difficulty range plus the ICS category. The event is over, so the flags are shown where we still hold them; WeakLink-2’s was captured live and never written down. The method is what’s being taught, not the string.

Disclaimer. These write ups document challenge solutions completed on the Hack The Box platform for educational purposes. All analysis was performed in a controlled CTF environment. ECHOClub is not responsible for the organization or administration of the UND CyberHawks CTF or the Hack The Box platform.

Write up 1 · Forensics, static malware analysis · Difficulty: approachable

First Attempt

An operative is told to open an email attachment to “claim the key” for the next mission. She follows the instructions and… nothing arrives. The task is to analyze the document and decide whether it’s safe. It is not.

What the file actually is

The attachment is a macro enabled Word document (.docm). The first move on any Office document is never to open it, it’s to crack it open inert and read the macros:

olevba key.docm

olevba (from oletools) unpacks the VBA without executing a thing. Two macros fall out.

What the macros do

  1. AutoOpen, runs automatically the instant the document opens (that alone is a red flag). Before anything else it patches Microsoft’s AMSI, the Antimalware Scan Interface Windows exposes so installed security products can inspect scripts before they run, by overwriting the start of AmsiScanBuffer in amsi.dll with a tiny stub, blinding the scan interface for whatever runs next.
  2. RunPowershell, builds a PowerShell one liner that beacons to a remote server, downloads a payload, strips a short header, decrypts it (RC4), and executes it in memory.

That’s a textbook download and execute dropper. The “key” was never going to appear, opening the document just tries to plant a foothold on your machine.

The teaching point

  • A document that must run code to “give” you something is the attack, not the delivery.
  • Read macros statically. olevba and oledump tell you the whole story with zero risk. Detonating in a VM is a fallback, not the first step.
  • AMSI patch + in memory PowerShell stager is a real world phishing pattern, not a CTF ism, the same recipe shows up in live intrusions.

Where the flag hid

The challenge author planted the flag as a string inside the macro, assembled from Chr() and StrReverse() fragments so it wouldn’t show up under a plain strings. Reconstructing the concatenation by hand yields the flag, no execution required.

FlagHTB{L3ts_k33p_1t_s1mpl3_4nd_st34lthy}

Tools

oletools (olevba), and a disposable analysis box. We never opened the document in Word.

Write up 2 · ICS, OPC UA authentication · Difficulty: medium

WeakLink-2

A pharma fill and finish line exposes an OPC UA server, the industrial control protocol standardized by the OPC Foundation. A previous patch “hardened” it: the only endpoint now requires Basic256Sha256 encryption with SignAndEncrypt and a client certificate. Sounds locked down. It isn’t, the server’s trust store is set to auto trust.

The lesson in one line

Encryption is not authentication. Requiring a certificate means nothing if the server accepts any certificate. Auto trust turns “bring your own cert” into “no cert check at all.”

Walking in

  1. Mint a self signed certificate. One detail trips people: OPC UA requires the client’s application URI to appear as a SAN (URI form) in the cert, or the server rejects it before trust is even considered.
  2. Connect with Basic256Sha256 with SignAndEncrypt presenting that cert. The auto trust store accepts it and hands you a session. Authentication defeated.

Using Python’s asyncua:

client.application_uri = "urn:me:client"
await client.set_security_string("Basic256Sha256,SignAndEncrypt,cert.der,key.pem")
await client.connect()          # in.

Finding the bug

Browsing the address space, the process exposes a live Recipe node that is writable, the active production recipe can be changed by any connected client. Elsewhere, a protected recipe’s “commissioning log” node reads back: “(sealed, token released after active recipe change)”. The node tells you the trigger: change the active recipe and the seal releases.

The exploit

Write the active Recipe node to the protected recipe’s name. That single privileged write (gated only by the transport we already bypassed) flips the seal and releases the token into the commissioning log node, where it reads back as the flag.

Flagcaptured live during the event, not retained in this write up

Why it matters

This is the shape of real ICS incidents: the crypto checkbox is ticked, but a misconfigured trust store plus an over permissive writable tag means an attacker can change what the plant is making. The “weak link” was never the cipher, it was the policy around it.

Tools

asyncua, cryptography (self signed cert). Worked from an isolated box on the club’s rig.

Write up 3 · Reversing, Go binary analysis · Difficulty: hard

World Hello

A single stripped, statically linked Go executable called telemetry. Run it and it does… nothing visible. No prompt, no output, no network. The task is to recover the “campaign tag” it builds. Everything about the binary is designed to waste your time in a disassembler.

The three traps

  1. A decoy symbol table. Go keeps a function name table (pclntab) even when stripped, so tools happily print names like main.buildCampaignTag, main.statA… The catch: the addresses those names map to point into the binary’s zero filled data section, not the real code. Follow them and you’re reading nothing.
  2. ~750 decoy functions. The real logic is ~8 functions; the author padded the package with hundreds of noiseFunc stubs so the interesting code is a needle in a haystack.
  3. Deliberately empty output. The program builds the tag, then writes it with a length of zero, write(1, "", 0). Nothing prints, and the value never sits in the file as a static string, so strings, single byte XOR, add, and reverse scans all come up empty (we tried all of them).

The turn

Every static angle is booby trapped, but the value is real at runtime. Go builds the string on its heap the moment before that empty write. So we stop reversing the code and watch the memory:

gdb ./telemetry
(gdb) catch syscall write      # the one write it does
(gdb) run
(gdb) find /b 0xc000000000, 0xc000400000, 0x48,0x54,0x42,0x7b   # "HTB{" in the Go heap
0xc000134040
(gdb) x/s $_
0xc000134040:  "HTB{RUNT1M3_G0_R3V34L5_1NT3NT}"

Note: Go’s heap lives around 0xc000000000, not down in the binary’s load address. Our first search scanned the program image and found nothing; the string was up in the heap arena the whole time. Find and read in the same run, the heap address moves between executions.

The last turn

The heap string is not quite the flag. The challenge is named World Hello, not Hello World, and that is the hint: the accepted flag is the recovered inner string read back to front. Reverse it and submit.

FlagHTB{TN3TN1_5L43V3R_0G_3M1TNUR}

The teaching point

  • Anti RE hardening protects the code, not the data at runtime. When static analysis is a wall, let the program build the secret and read it out of memory.
  • Don’t trust a stripped binary’s symbol table, it can be planted. Cross check the addresses against the actual executable sections.
  • The flag itself names the lesson: the runtime reveals the intent.

Tools

pwntools, radare2, GoReSym (to expose the decoy table), gdb, strace. Isolated box.

ECHO Club UND CyberHawks Quals 2026 Write Ups

Solo clear by Digital Orukami · Hack The Box · UND CyberHawks National CTF · educational use only.