외로운 Nova의 작업실

리버싱 입문 - 2(crackme2.exe) 본문

Computer App Penetesting/Reversing

리버싱 입문 - 2(crackme2.exe)

Nova_ 2022. 12. 7. 16:39

안녕하세요. 이번 시간에는 abex crackme2.exe 파일을 리버싱해보도록 하겠습니다. 아래 파일 남겨놓겠습니다.

crackme2.exe
0.02MB

 

 

- 문제 인식

먼저 실행시켜봅시다.

Name과 Serial form이 있고 옆에 check, about, quit 버튼이 있는 것을 확인할 수 있습니다. 일단 뭐 Name에는 a를 serial에는 1234를 넣어보겠습니다.

이름에다가는 4개의 문자를 넣으라고 알림창이 뜹니다. 꼭 4개 이상을 넣어야하는 이유가 있는걸까요..ㅎㅎ 일단 name을 nova로 비밀번호는 1234로 넣어보겠습니다.

serial이 틀리다고 나오네요. 이번 문제는 serial을 찾는 문제인 것 같습니다. 그렇다면 이제 ollydbg로 리버싱해보겠습니다. 일단 ollydbg로 crackme2.exe 를 올려주겠습니다.

 

- 함수 분석

먼저, main thread에서 함수를 분석해보겠습니다. crackme2.exe에 3가지 버튼을 누르면 main thread에서 함수가 실행될 겁니다. 함수는 PUSH EBP로 시작하죠. 한번 PUSH EBP를 검색해보겠습니다. 맨위 코드라인으로 가서 클릭해주고 serchfor - command 에서 PUSH EBP를 입력하고 forward를 선택해줍니다.

첫번째 함수 0x402c50 주소에 있는 것을 확인할 수 있습니다. breakpoint를 걸어줍니다. 다시 cntl+F를 눌러서 command를 검색해줍니다.

두번째 함수 0x00402cc0 주소에 있는 것을 확인할 수 있습니다. breakpoint를 걸고 다음을 검색해줍니다.

세번쨰 함수 0x00402ed0 주소에 있는 것을 확인 할 수 있습니다. breakpoint를 걸고 또 있는지 검색해줍니다. 검색을 해보면 이제 더이상은 없는 것을 확인할 수 있습니다.

그렇다면 이제 버튼을 누르면서 어떤 주소의 함수에서 브레이크가 걸리는지 보겠습니다. 먼저 check 버튼을 눌러보겠습니다. name에는 nova, serial에는 1234를 기입하고 눌러보겠습니다.

그러면 0x0040e2d0 주소에서 브레이크 됩니다. 즉 세번째 함수(0x0040e2d0)는 check버튼의 함수였군요. 이제 다시 처음으로 돌아가서 about 버튼을 눌러보겠습니다.

이번에는 0x00402cc0 주소에서 멈췄습니다. 두번째함수(0x00402cc0)은 about 버튼을 누르면 실행되는 함수인 것을 알 수 있습니다. 다시 처음으로 돌아가서 quit 버튼을 눌러보겠습니다.

0x00402c50 주소에서 멈췄습니다. 첫번째 함수(0x00402cc50)은 quit 버튼을 눌렀을떄 실행되는 함수인 것을 알 수 있습니다. 정리해보자면 아래와 같은 사실을 알 수 있습니다.

  • 0x00402c50 : qute 버튼 함수 시작점
  • 0x00402cc0 : about 버튼 함수 시작점
  • 0x00402ed0 : check 버튼 함수 시작점

여기서 우리가 분석해야할 함수는 무엇일까요? 저희는 check 버튼 함수를 분석해봐야겠죠? check 버튼 함수에서 분명 serial을 비교하고 아니라면 잘못됫다는 알림메시지, serial이 동일하다면 잘됫다는 알림메시지가 뜨게 알고리즘을 설정해놨을겁니다. 이번에는 그렇다는 것은 stack에는 실제 serial이 들어있을 가능성이 크고 stack에 있는 serial과 제가 입력한 serial을 비교하는 코드가 들어있을 가능성이 큽니다. 일단 뭐 다시 check 버튼을 누르고 stack에 있는 값을 분석해보겠습니다.

위 상태에서 스택을 분석해보면

오른쪽 하단에 nova와 1234, D2D3DAC5가 있는 것을 확인할 수 있습니다. 아마 D2D3DAC5가 serial일 가능성이 커보입니다. 한번 name은 nova, serial은 D2D3DAC5로 넣어보겠습니다.

serial 키가 맞다는 알림메시지가 뜹니다. 그렇다면, 아마 어셈블리 코드에서는 serial을 비교하고 분기(jump) 시켜주는 코드가 있을 것임을 알 수 있습니다. 이부분을 한번 찾아 크랙해보겠습니다. 

 

- 크랙

0x00403329 주소 부분이후에 TEST 명령어를 하게되고 이후 JE 분기명령을 통해 serial이 맞다면 jump하지않고 그대로 가고, serial이 다르다면 jump한다는 사실을 알 수 있습니다. 그럼 이 프로그램을 crack해보겠습니다.

저기 JE 분기명령전의 test ax,ax를 cmp bx,ax로 변경하면 됩니다. test 명령어는 두개의 operand를 and하기때문에 test ax,ax는 ax가 0000인지 아닌지 즉, 함수의 리턴값이 ax로 들어가게되고 ax(함수의 리턴값)이 0인지 아닌지 확인하는 구문입니다. 따라서 cmp bx,ax를 하게되면 zero 플래그가 0이 되지 않으니 JE 분기명령은 일어나지 않고 serial이 맞다는 메시지 박스가 뜰것입니다. 한번 해보겠습니다.

변경을 해주고 name은 nova serial은 12341234로 해보겠습니다.

잘되는 것을 볼 수 있습니다. 하지만 한가지 문제점이 생겼습니다. 시리얼 값이 맞다는 메시지박스 이후에 바로 버튼 누르는 것을 대기하는 상태로 가는것이아닌 시리얼 값이 다르다는 메시지 박스가 뜨는 문제점이 있습니다.

이러한 문제점을 해결하기위해 코드의 흐름을 step over로 확인해보게되면

0x0040341b 주소부분 call 함수이후에 JE 004034F1 부분에서 분기를 하면 정상적으로 대기상태로가고 분기를 안하면 wrong serial! 이라는 메시지박스가 뜨는 것을 확인할 수 있습니다. 만약 AX가 1일경 TEST AX,AX의 연산결과 zero 플래그가 0이기때문에 분기가 일어나지 않습니다. 따라서 AX가 1이더라도 zero 플래그가 1이되도록 TEST AX,AX를 CMP AX,AX로 변경해줍니다.

다시 실행해보겠습니다.

잘되었다는 메시지만 뜨는 것을 확인할 수 있습니다. 그렇다면 크랙판을 저장해보겠습니다. 코드에서 오른쪽 마우스 크릭- select all 해준후

 

왼쪽마우스클릭 - edit - copy to excutable 이후에 새로운 창이뜹니다.

이후 오른쪽마우스 클릭 - save file을 하면됩니다. 크랙판을 올려두겠습니다.

crackme2(cracked).exe
0.02MB

 

 

 

- serial 구해지는 로직 알아보기

크랙을 만들긴 했지만 serial이 만들어지는 원리는 아직 알아보지 못했습니다. 이 과정은 코드에서 call 하는 부분에서 스택과 레지스터를 유심히 관찰한후 그 결과를 바탕으로 가정하고 추측하는 방법을 사용해야합니다. 일단 코드를 하나씩 실행시켜서 call 명령어 부분에서 알아낸 몇가지 사실을 적어보겠습니다.

  • 004031F7 call 함수 : eax에 name의 nova에서 n의 아스키코드인 6E를 eax로 가져옵니다.
  • 0040325B call 함수 : D2를 스택으로 이동시킵니다.
  • 0040327B call 함수 : D2를 기존에 있던(지금은 첫글자로 없음) 문자열에 붙입니다.
  • 위 3개의 함수를 4번 반복합니다.

6E와 D2는 64라는 값의 차이가 있습니다. 그렇다면 name 문자의 아스키코드값에다가 64를 더해서 serial 값을 만드는 것임을 추측할 수 있습니다. 따라서 o의 아스키 값은 6F로 54를 더하면 D3가 됩니다. nova의 시리얼값은 D2D3DAC5이므로 o도 맞음을 알 수 있고, 이후 다 64 값이 차이가 남을 알 수 있어, serial은 name 문자의 64값을 더해서 만들어짐을 알 수 있습니다. 또한, 처음에 name은 4개 이상넣어야된다고 알림메시지가 떳는데 이 시리얼값을 만들기위해서는 name이 4개 있어야 하기때문임을 알 수 있습니다.

Comments