Stripe CTF 2.0 Level 3
About
Here is a python level. They claim this one is more secure and it is a bit more but not really.
Hint Given
There really is no hint given other then in the code
Problem in the code
So take a look at line #86
query = """SELECT id, password_hash, salt FROM users
WHERE username = '{0}' LIMIT 1""".format(username)
cursor.execute(query)
So that is taking a username and pulling out data to see if the user/password combo is correct. The main issue is they aren't checking for invalid input. Like putting in quotes for the username.
Solution
So we are going to attack this with a SQL injection attack. Since there isn’t any validating of data that is sent in via the username we can put SQL in the username to make it pull out data that we want. So we can do this with a UNION statement. Pretty much our attack will be to union data we provide so it overrides the data that is in the database. So first we have to create a salted password to use. So lets first up python and do something like this
>>> import hashlib
>>> hashlib.sha256(“bob”+”bob”)
<sha256 HASH object @ 0x10045dc30>
>>> hashlib.sha256(“bob”+”bob”).hexdigest()
’4c26991843b5498e99ef26e6cf45c4eecd9e6890436f619054aaa8790b35967c’
So what we are doing is creating our own salted password to pass in via SQL injection to the app so it can compare with a password we send in via the form and a salt we are also injecting. So once we have that encrypted password and a known salt/password we will enter the following
As the username
‘ UNION SELECT id, ’4c26991843b5498e99ef26e6cf45c4eecd9e6890436f619054aaa8790b35967c’ AS password_hash, ‘bob’ AS salt FROM users where username=’bob’;–
As the password
bob
So that will take id,password_hash and salt and replace it in the code with what the database would return when select a user bob.
Now you have the next level’s password.
Stripe CTF 2.0 Level 2
About
This is another PHP level where they emulate a little social network where you can upload a image of to use for your profile. This level goes into what is wrong if you don’t force an output file type for uploaded content.
Hint Given
The hint really is that you can upload a file to use as an image.
Problem in the code
The problem in the code is really how they handle the upload. They just take a file and move it into the uploads/ directory and keep the name of the file you uploaded. Generally if you accept images, you’d want to convert anything uploaded into a jpeg.
Solution
So this is a pretty simple one. Create a file called like attack.php with the following contents in it.
<?php echo file_get_contents(“../password.txt”);
So that will put the file in uploads/attack.php so you can fire up your browser and hit the following page
https://level02-4.stripe-ctf.com/user-cnfowzkbbk/uploads/attack.php
It will spit out the contents of password.txt.
Stripe CTF 2.0 Level 1
About
In this level you are given a form where you have to “guess” the secret password to get the password to the next level. This level is in PHP and requires you to really looking at the code to figure out an attack point.
Hint Given
I don’t think there are any real hints in this level in the description.
Problem in the code
So here is the following section of code that has a problem. Take a look at line 13
extract($_GET);
This is where you know how to attack this level. The problem is that extract() takes an array and sets the key value to variables with the value set. This is not a good thing to do with $_GET/$_POST array since the user can set those and override any of the variables that are setup before the extract. This is line 12
$filename = 'secret-combination.txt';
$combination = trim(file_get_contents($filename));
This will take the contents of $filename and put it in $combination
Solution
So now that you know the weak spots. We want to attack the $_GET array. So we pass in a blank $filename and $attempt. So our query looks like
https://level01-2.stripe-ctf.com/user-xxxxxx/?filename=&attempt=
What that does is make $combination contain an empty string since the file contents of nothing is nothing. Then you are passing in combination on the $_GET array as nothing so it matches. The form wants to post but since it uses extract() to get the variable settings we can just attack it via $_GET and make the attack pretty easy.
Stripe CTF 2.0 Level 0
About
This is the first level of Stripe’s challenge. You start off in an app that stores secret passwords for users and you have an option to store a password or retrive a password.
Hint Given
So the following hint that is given on the page is as follows.
It turns out that the password to access Level 1 is stored within the Secret Safe. If only you knew how to crack safes…
It isn’t much of a hint since you know it’s stored there anyway probably
Problem in the code
So here is the following section of code that has a problem. Take a look at line 33
var query = 'SELECT * FROM secrets WHERE key LIKE ? || ".%"';
There is no checking for input provided by the user. There is also the following
db.all(query, namespace, function(err, secrets) {
Solution
This is an easy one if you know anything about sql. A % in sql is a wildcard. So just pass in a % for a secret you want to retrive and you will have the level 1 password shown.