LabyREnth 2016 Write-up: “bowie.pl”

Unix track #1 – bowie.pl

This is a Perl script which is really large (3MB). When you open it up, you’ll see it request input from STDIN, then compares it against these concatenated chars like so:

my $input = <STDIN>;
$input = trim($input); 
if ($input eq (chr(5156 - 5035) . chr(-4615 - -4716) . chr(3162 - 3047))) {
  ...

It then has a lot of MIME::Base64::decode() statements, which seem to be building up data in variable $a. Only if the input matches does it go further into the nested if‘s and performs more decoding. Otherwise it just borks.

If you follow further, you’ll notice that at some point it calls eval() with even more Base64-decoded code.

Perl’s Debugging Hooks

One interesting thing I learnt while solving this challenge was that Perl internally has some mechanisms for debugging, allowing you to easily write your own debugger. How easy? You can fit a tracer into a one-liner like so:

PERL5DB='sub DB::DB {my @c=caller;print STDERR qq|@c[1,2] ${"::_<$c[1]"}[$c[2]]|}' \
perl -d my-script.pl

So the gist of solving this challenge would be to check what $input is being compared to, set that into the $input variable, and let ‘er rip. The beauty of this method is, it will even handle the eval() for you. You don’t need to separately decode it and put it back in, or run it as a separate script.

You can find my solver script here. Everything happens in the DB::DB function, which is called before a statement is executed. It then waits for if ($input eq ...) statement, transforms that into an assignment statement and evals it in the program’s context. The rest of the code are just stolen from the Perl debugger to save and restore program context (or something like that).

Save the script as Devel/Tracer.pm, then run the bowie.pl script like so:

perl -d:Tracer bowie.pl < /dev/null

After the script is done, you should get a entrevue.gif dropped in the current directory. That image is a picture of David Bowie with the flag written over him.

I learn new things every time I play CTF.

If you found this Perl debugger thing interesting, you can take a look at these links:

LabyREnth 2016 Write-up: “Regex”

Random track #2 – Regex

This is a challenge involving regular expressions. It reads the huge expression from the file omglob_what_is_dis_crap.txt. The code that reads and evaluates this expression will only provide you with the key if you provide it with an input that doesn’t match this expression. Of course the program runs on a remote server, so you don’t have direct access to the flag.

Inspecting the expression, there’s a lot of “OR” conditions, and splitting them into lines gets you something like this:

^(
.*[^0mglo8sc1enC3].*|
.{,190}|
.{192,}|
.{97}[cgClm]|
.{135}[so1l803]|
   .
   .
   .

If this looks familiar to you, it’s because a similar challenge appeared in PlaidCTF 2015. I solved and wrote about the challenge here using Z3 (an SMT solver).

Basically the first 3 lines of expressions at the start dictate what characters can appear in the input, as well its length (191, in this case). This, however, is a watered-down challenge compared to the PlaidCTF one. You do not need to use Z3 in this case. To illustrate what I mean, if you sort each of the regex part in numeric order using sort -k 1.3n, you get this:

.{0}[eo1Cnsc0lm38]
.{1}[3]
.{1}[8l0osm]
.{1}[c1C]
.{1}[en]
.{2}[18]
.{2}[3omsglcn]
.{2}[C]
.{2}[e]
.{3}[3]
.{3}[com8negC]
   .
   .
   .

Using a script, you can easily piece together what characters should (not) go into each position, and thus, construct the correct input to feed to the server.

Because I’m lazy, I decided to re-use my solver script from last time. At that time, the character set was "plaidctf" but this time round it’s "0mglo8sc1enC3", the length of which is unable to fit exactly into N bits (not a power of 2). So I made a few modifications to make it use Z3 Ints instead of a BitVec to support arbitrary string lengths. Fortunately I did a good enough regex parser the last time, so that worked out of the box. (Never did I imagine that it would ever be re-used again.) Now all you need to do is to change the valid character set and length of the flag at the top of the solver script, and off it goes!

I said this was watered-down because Z3 took about 20 minutes the last time to solve PlaidCTF’s constraints. This, on the other hand, took less than one second.

Netbooting Your Raspberry Pi

A very long time ago, I set up and played around with diskless machines. These are basically PCs can boot up an operating system fully without hard disks. All the operating system files come from a server on the network. It was amazing (well, to me at least)!

Back then, Ethernet cards used to have a DIP/PLCC socket, which allowed you to insert an EEPROM on which you burn a boot ROM. Fortunately I didn’t have to do any of that because the network cards at that time already came with PXE ROMs built-in, just as they do today. To activate this, you just need to select the network card’s option ROM in the boot order, or make it higher up in the boot priority.

3Com network card with boot ROM socket marked

As part of the boot process, the network card will request an address from the DHCP server, which also tells the client where it can find the TFTP server with the next boot stage. The ROM will download this file from the TFTP server and start executing it.

That’s how Linux ultimately gets started from the network.

An announcement was made recently on the Raspberry Pi blog that you can achieve total network boot, just like on the PC, without any SD cards.

Continue reading

X-CTF 2016 Badge Firmware

As promised, we are releasing the source code for the X-CTF badge, about 1 month after the event to give interested participants the chance to take a crack at it. If you are interested in the badge design process, check out my previous post on the hardware aspects.

Jeremias and Jeremy gave a talk at one of the Null Security meetups. Check out the slides if you haven’t already. In one part, Jeremy talks about the custom firmware he wrote for his badge and the additional challenges he set up for partipants to get more points. The 2nd part of the talk covers the electronic badge and challenges.

The Challenges

The challenges try to exploit the nature of being a self-contained electronic device. Rather than trying to replicate more CTF puzzles and simply placing them into the badge, we specially designed them for the badge.

You can find the answers to the badge puzzles (and the main CTF puzzles) in the X-CTF GitHub repo, which was released shortly after the event.

Since there’s only a single entry point into the set of challenges (meaning you must solve each puzzle before getting to the next), the puzzles must be designed with increasing levels of difficulty; too difficult and the participants will totally give up.

Stage 1: Catch Me If You Can

animation of challenge 1

I particularly like this one. Unlike a program running on the computer, you can’t easily snapshot the state of the program, nor try to influence (slow down) its execution.

Continue reading

Designing the X-CTF 2016 Badge

X-CTF 2016 badge with Lithium-ion battery attached

I had the opportunity to collaborate with some NUS students to design the electronic badge for their X-CTF event this year.

The purpose of the badge was to inspire more people to take an interest in hardware hacking, or to get them started on electronics. With so much hype on the Internet-of-Things (IoT) these days, what better idea than to let participants take home their very own IoT device. The super low cost WiFi chip, Expressif’s ESP8266, made this possible. We also wanted it to be shaped like a gaming device, with a D-pad and an LCD.

You can see the final badge design above: a ESP8266-based board with a backlit monochrome Nokia LCD, D-pad and a SELECT button. Powered by a lithium-ion battery, charged via the USB port, which also provides a serial connection to the ESP8266.

I was inspired by the SyScan 2015 badge. It was so simple and spartan: a monochrome LCD, an LED, a 5-way joystick switch and a 32-bit ARM processor (on the back). As the regulator was built-in and it runs all the way down to 2.4V, there was no need for an external regulator.

SyScan 2015 electronic badge

Continue reading