In this challenge I’m going to show how focusing on only one attack vector may make you fail hard.
At the beginning, we’re given a source of an application running on certain port web.angstromctf.com:3002. By connecting to this port using nc, we’re given a simple blackjack game, taking an user bet and then making the random choice.
But as we have the source code, let’s take a look at it.
From the start we can see that the input is converting our numbers to float with bet = float(bet), then it performs checks that will determine whether the numbers isn’t smaller than 0, and if it’s not bigger than our current money status.
After that the application will generate three lines, with the second/middle one used to generate our outcome.
But as the random number generator isn’t seeded with any value, the sequence of values should be the same for each run of this program. That’s what I decided to dig into and check whether or not it’s correct. Below are the sample three 3 games.
As you can see, values do not change with each game. That made me feel confident and that’s how I stopped further analyzing code and decided to dig into this problem, writing python script that will bet very small amounts of money in order to check where it’s possible to win some money. In quick words - bad idea.
This loop will iterate as long as we’re able to win something, making sure that it’s impossible to win from any combo in this game. Banging my head after such a stupid mistake, I decided to look for something else in this code and in Python documentation about float() function I’ve noticed something interesting.
Interesting, let’s check the NaN value, as the -+inf will be blocked by the boundary checks.