본문 바로가기
pwnable

[Toddler's Bottle] random

by 미스터 J 2024. 5. 11.
반응형

몬데...?


#include <stdio.h>

int main(){
        unsigned int random;
        random = rand();        // random value!

        unsigned int key=0;
        scanf("%d", &key);

        if( (key ^ random) == 0xdeadbeef ){
                printf("Good!\n");
                system("/bin/cat flag");
                return 0;
        }

        printf("Wrong, maybe you should try 2^32 cases.\n");
        return 0;
}


key를 입력받고 key의 랜덤 상수제곱을 해서 0xdeadbeef와 같아야한다.

우선 좀 해봤다고 바로 gdb를 켜봤다.

나름 리버싱 책도 읽고 해서 자신있게 분석해봤는데 여전히 알 수가 없었다.

우선 생각한 공격부분을 말해보자면.

1. random()함수의 값을 조작.(내가 알기로는 random도 일정한 테이블이 있다고 알고 있으므로 같은 값을 추출할 수 있을것)

2. if문의 값을 강제로 0xdeadbeef로 패치

정도를 생각했었다.

 

여전히 write-up을 참고한다.

random에 취약점이 있는 것이 맞았다. seed값을 정해주지 않으면 같은 값이 나오고, 진짜 랜덤값을 얻으려면 srand(time(NULL))을 써야 한다.

레지스터는 이렇게 보는 구나. 계속 x/i $esp 이렇게 입력했는데 나오지 않았다.

eax에 random의 값이 저장되기 때문에 해당값을 실행해주고 eax를 확인해야한다.

write-up 마다 브레이크 포인트 잡는 게 천차만별이다.

0x0000000000400601 <+13>:    call   0x400500 <rand@plt>

해당 함수 실행 다음에만 잡아주면 되는것 같다.

eax = 0x6b8b4567 값이 들어있는것을 확인할 수 있었다.

key ^ 0x6b8b4567 = 0xdeadbeef 가 되고 XOR은 key = 0x6b8b4567 ^ 0xdeadbeef를 만족한다.

3039230856이란 키 값이 나왔다.

Mommy, I thought libc random is unpredictable...

 

상대적으로 쉽다! 어제 뼈빠지게 고생해서 그런것 같다

passcode가 10pt 짜리 문제였다... 이러니까 어렵지. 앞으로는 점수 적은 순으로 풀어보자

반응형

'pwnable' 카테고리의 다른 글

[Toddler's Bottle] flag  (0) 2024.05.11
[Toddler's Bottle] passcode  (0) 2024.05.11
[Toddler's Bottle] mistake  (0) 2024.05.11
[Toddler's Bottle] shellshock  (0) 2024.05.11
[Toddler's Bottle] black jack  (0) 2024.05.11