Tags: rev
Rating:
For a better view check our [githubpage](https://bsempir0x65.github.io/CTF_Writeups/SEETF_CTF_2022/#babyreeee) or [github](https://github.com/bsempir0x65/CTF_Writeups/tree/main/SEETF_CTF_2022#babyreeee) out
![Babyre](https://raw.githubusercontent.com/bsempir0x65/CTF_Writeups/main/SEETF_CTF_2022/img/babyreeee.png)
So based on the description it seems to be a binary which just checks if we have the right flag. So we started to understand what this binary does by loading it into[ghidra](https://ghidra-sre.org/), which gave us already some nice insights:
Disclaimer: Never execute something you don't know. So maybe not the best habit to have. But what could possible go wrong
> uStack44 = 0x5e; //more values loaded into the stack above
>
> local_28 = 0x50;
>
> uStack36 = 0x86;
>
> uStack32 = 0x89;
>
> uStack28 = 0x89;
>
> local_18 = 0x48;
>
> uStack20 = 0x4f;
>
> uStack16 = 0x49;
>
> uStack12 = 0xf1;
>
> fgets(local_158,0x80,stdin); //here we get asked for our input
>
> sVar4 = strlen(local_158); // gets the length of our input
>
> if (sVar4 == 0x35) { // 0x35 in decimal is 53 , since we put \n as our input by pressing enter we are searching for a 52 length value
>
> puts("Good work! Your flag is the correct size.");
>
> puts("On to the flag check itself...");
>
> sVar4 = strlen(local_158);
>
> uVar5 = 0;
>
> do {
>
> uVar6 = uVar5 & 0xffffffff;
>
> if (sVar4 - 1 == uVar5) {
>
> puts("Success! Go get your points, champ.");
>
> return 0;
>
> }
>
> pcVar1 = local_158 + uVar5; // loads our input
>
> puVar2 = local_d8 + uVar5; // loads a value from above
>
> bVar3 = (byte)uVar5;
>
> uVar5 = uVar5 + 1;
>
> } while ((byte)*puVar2 == (byte)(*pcVar1 + 0x45U ^ bVar3)); // does a check if the input we gave after transformation is equal to the loaded value
>
> printf("Flag check failed at index: %d",uVar6);
>
> }
>
> else {
>
> printf("Flag wrong. Try again.");
>
> }
>
> return 1;
>
>}
- [x] Let's figure out what to do
So clever people have seem to have figured out how to convert (byte)(*pcVar1 + 0x45U ^ bVar3)) into a simple script and let it do the magic. But we used something different here:
>printf("Flag check failed at index: %d",uVar6);
every time the input does not match the right value the program tells us what was the index value of the error. This piece of information can be used as a checker if the input is correct and if so move to the next value. This dramatically reduces the time you need for a brute-force attack. So that's what we did:
```python
#!/usr/bin/python
from pwn import *
from string import ascii_lowercase,ascii_uppercase,digits
checksolution = ("Success! Go get your points, champ.\n").encode('utf-8')
elf = ELF('./rev_babyreeee')
#We know that the flag starts with SEE{ and that the flag is in the format SEE{[ -~]+} plus ascii signs
current_flag = "SEE{"
old_flag = ""
index = 4
checklist = ascii_uppercase + ascii_lowercase + digits + "_}"
while current_flag != old_flag:
missingvar = 51 - len(current_flag) #this is the amount of characters we have to find
for c in checklist:
io = elf.process()
print(io.recvline(timeout=2))
#this block here is to send the current sign of the flag to the binary and check the response
sendvar = (current_flag + c + "A" * missingvar ).encode('utf-8')
io.sendline(sendvar)
print(sendvar)
print(io.recvline(timeout=2))
print(io.recvline(timeout=2))
checkvar = io.recvall(timeout=2)
checktest = ("Flag check failed at index: {}".format(index)).encode('utf-8')
print(checkvar)
print(checktest)
#to check if we found the solution
if checkvar == checksolution:
current_flag = current_flag + c
print(current_flag)
old_flag = current_flag
break
else:
print("next please")
#check if we found the next correct character
if checkvar != checktest:
print(current_flag)
old_flag = current_flag
current_flag = current_flag + c
break
else:
print("i said next")
io.close()
#was my error checker to ensure the script comes to an end
if c == "}":
print("shit")
old_flag = current_flag
break
index += 1
print("welcome to the end")
print(current_flag)
```
- [x] Execute the exploit
So the FLAG is SEE{0n3_5m411_573p_81d215e8b81ae10f1c08168207fba396}
On our system it took not very long to brute force the flag so it was doable during the challenge. Its also not the nicest script in the world but it got the job done and maybe this was even an unintentional solution for the creators of the CTF. So if you're ever stuck on such issues you can always fall back to the old ways of cracking things ヾ( ͝° ͜ʖ͡°)ノ♪. Nevertheless it's a little neat challenge.
- [x] Do the happy dance
ヾ( ͝° ͜ʖ͡°)ノ♪ ヾ( ͝° ͜ʖ͡°)ノ♪ ヾ( ͝° ͜ʖ͡°)ノ♪