상세 컨텐츠

본문 제목

Babylon's KeygenMe - 풀이 및 Keygen source.

0x10 정보보안/0x14 Reverse Engineering

by sweetchip 2012. 11. 25. 16:20

본문

반응형


안녕하세요 pgnsc입니다.


이거 푸느라 진이 다 빠졋네요 ㅋㅋ


난이도는 어려운 편은 아닙니다만.. 연산을 계속 해대고 프로그래밍 실력 부족으로 몇번 삽질한 다음에 키젠을 완성했습니다.


오늘도 그림위주로 설명하겠습니다.


Keygen-me 파일

0x2indos.exe


총 6개의 루틴을 거쳐서 키가 생성됩니다.




프로그램은 name에 따른 serial 을 생성하고 그 시리얼이 맞을경우 통과시키는 간단한 프로그램입니다.


하지만 리버싱을 하는 사람 입장에선 절대 간단한 프로그램이 아니죠 ㅠㅠ



올리디버거에서 적절하게 위치를 찾아갑니다.


저는 yeah 문자가 있는곳으로 갔습니다. [성공했을경우 그 문자열을 띄워주거든요]



맨위의 암호화 시작에서 부터 루틴을 주석으로 정리해뒀습니다.

1. name 사이에 공백을 삽입 [ex : sweetchip =>s w e e t c h i p ]

2. keytable 배열을 각각 0x01 씩 더해준다


keytable 은 트레이싱중 모습을 드러내게 됩니다.


하지만 위에서의 ascii 로 변환된 key테이블은 믿을게 못됩니다. ascii가 표현을 하기엔 한계가 있기 때문입니다.


3. name 과 keytable 을 Xor 연산한다.


위 사진 에서 보시다 시피 a8은 ascii 로 나타낼수 없어 ? 로 되어지고, 뒤 0x31은 아예 보이지 않는 현상이 나타납니다.

꼭 key table 은 hex code 로 보셔야 합니다.

xor된 키테이블 입니다.



4. xor연산을 한 keytable 을 거꾸로 뒤집는다.

거꾸로 뒤집힌 키테이블



5. 앞에서 한글자, 뒤에서 한글자씩 반복해서 가져온다 [ex 12345678 => 18273645]

위 예처럼 키테이블을 정렬한 모습입니다.



6. 가져온 문자를 하나씩 검사한다. 0x1F보다 작은경우 또는 0x7A보다 큰 경우, 0x36으로 설정한다.

5번과 달리 6으로 변경된 값이 많은걸 볼수 있습니다.


루틴종료.


암호화루틴 종료및 사용자 입력 시리얼 검사후 판별한다.


실제 키는 사용자가 입력한 name 길이이다.


[Ex : name이 'sweetchip' 일경우 '1]66/S/60' ]


실제로 그런지는 여러분이 직접 확인하시길 바랍니다 :D



대충 이해가 가셧나요 ~_~



위 분석한 자료들을 토대로, 아래의 c 로 키젠프로그램을 만들었습니다.


처음으로 키젠의 소스가 100줄이 넘었네요 ㅋㅋ


키젠---===

babylon_keygen_made_by_sweetchip.exe

==========



// Keygen source.cpp

// 개인 공부용으로 사용, 출처는 꼭 남겨주시면 감사드리겠습니다.


#include

#include


void reverseString(char* s) {

size_t size = strlen(s);

char temp;


for (size_t i = 0; i < size / 2; i ) {

temp = s[i];

s[i] = s[(size - 1) - i];

s[(size - 1) - i] = temp;

}

}


int main()

{

char keytable[0x100] = {0x2D ,0x5B ,0x23 ,0x5D ,0x5D ,0x3D ,0x7D ,0x26 ,0x26 ,0x26 ,0x2B ,0x28 ,0x3D ,0x24 ,0x2A ,0x2C ,0x2C ,0x29 ,0x26 ,0x2E ,0x2A ,0x2F ,0x2B ,0x2B ,0x2B ,0x5B ,0x5D ,0x5B ,0x3B ,0x2F ,0x2E ,0x2E ,0xA7 ,0x30};

char name[30];


int keylen = strlen(keytable);

char tmp[0x100];

char tmp2[0x100];

char result[0x100];


puts("/////////////////////////////////////////////");

puts("///// babylon's Keygenme - Keygen /////");

puts("///// made by sweetchip /////");

puts("///// 12.11.25 /////");

puts("/////////////////////////////////////////////");


printf("\ninput your name : ");

scanf("%s",&name);

int namelength = strlen(name);


if(namelength<=3 || namelength>=15)

{

puts("\nattention! 3 < name < 15\n");

system("pause");

return 0;

}


for(int i=0, j=0; j

{

char alpha = name[j];

tmp[i]=alpha;

tmp[i 1] = ' ';

i ;

if(j==namelength-1)

{

tmp[i 1]='\0';

}

}


for(int i=0; i

{

keytable[i] = keytable[i] 0x01;

}


int tmplen = strlen(tmp);


for(int i =0; i

{

keytable[i] = tmp[i] ^ keytable[i];

}


reverseString(keytable);


for(int i = 0, j=keylen-1,k=0; i

{

tmp2[k] = keytable[i];

k ;

tmp2[k] = keytable[j];

if(j-i==1 || j-i==0)

{

k ;

tmp2[k]=keytable[j-1];

tmp2[k 1]='\0';

break;

}

}


for(int i=0; i

{

if(tmp2[i] < 0x1f || tmp2[i] > 0x7a)

{

tmp2[i]=0x36;

}

}


for(int i = 0; i

{

result[i] = tmp2[i];

}

result[namelength 1]='\0';


printf("\nYour Key is : %s\n\n have a nice day.",result);


system("pause");


}


감사합니다

반응형

관련글 더보기