HackCTF static

2019. 7. 25. 02:340x02 Reverse Engineer/0x03. Etc

728x90

해당 문제 컨셉 : Binary Patch 

환경 : 64bit ELF 

Thinking.. static이 문제 명인 이유 : 도출 된 input 값을 입력하면 특정 문자에 의해 command가 먹히지 않음.

그래서 정적으로 분석하고 코드를 짜야함. 

 

패치 하면 다음과 같은 코드를 볼 수 있음.

__int64 __fastcall sub_A3A(int argc, char **argv, char **a3)
{
  const char *s1; // [rsp+20h] [rbp-10h]
                                                // bi0s ~~ 
  s1 = getenv("team_name");
  if ( s1 && !strncmp(s1, "bi0s", 4uLL) )       // 
                                                // 
  {
    if ( argc == 2 )
    {
      if ( (unsigned int)enc(s1, argv[1]) == 1 )
        printFlag((__int64)argv[1]);
      else
        printf("Better luck next time!", argv);
    }
    else
    {
      printf("usage: chall <input>", "bi0s", argv);
    }
  }
  else
  {
    printf("Nope.", argv);
  }
  return 0LL;
}

환경변수 안만들고도 진행할 수 있다 strncmp가 있기 때문에. 

 

그럼 첫번째 if문 가볍게 우회한다고 가정하자.

 

enc 함수에 접근

__int64 __fastcall enc(const char *bi0s, const char *inputKey)
{
  void *flag; // rdi
  char v3; // dl
  size_t newIndex; // rax
  char *copyDummy; // [rsp+8h] [rbp-68h] 차이 : 8바이트 
  char v7[32]; // [rsp+10h] [rbp-60h] 32는 페이크야
  __int64 realKEy; // [rsp+30h] [rbp-40h]
  __int64 v9; // [rsp+38h] [rbp-38h]
  int v10; // [rsp+40h] [rbp-30h]
  __int16 v11; // [rsp+44h] [rbp-2Ch]
  char v12; // [rsp+46h] [rbp-2Ah]
  int v13; // [rsp+48h] [rbp-28h]  사용 안하는 값 
  int v14; // [rsp+4Ch] [rbp-24h]
  int v15; // [rsp+50h] [rbp-20h] 사용 안하는 값
  int index; // [rsp+54h] [rbp-1Ch]
  int xorVal; // [rsp+58h] [rbp-18h]
  int i; // [rsp+5Ch] [rbp-14h]
                                                // real : 4919197161836291817161 이네 
  copyDummy = (char *)bi0s;                     // 22글자 
  xorVal = 0;
  index = 0;
  realKEy = '91817161';                         // key
  v9 = '71618362';
  v10 = '1919';
  v11 = '49';
  v12 = 0;
  flag = (void *)inputKey;
  if ( strlen(inputKey) == 22 )                 // input이 22글자되어야 하고 bi0s는 xor에 이용된다 
  {
    for ( i = 0; i < strlen(copyDummy); ++i )   // 4
      xorVal += copyDummy[i];                   // bi0s
    v13 = 0;
    xorVal /= 30;                               // 후 처리 
    while ( index != 22 )
    {
      if ( index & 1 )                          // 짝수 / 홀수 
        v3 = inputKey[index] - 4;
      else
        v3 = inputKey[index] + 4;
      v7[index] = v3;
      v7[index] ^= xorVal;
      ++index;
    }
    v15 = 0;
    flag = v7;
    for ( i = strlen(v7) - 1; i >= 0; --i )     // 22여야함 
    {
      flag = v7;
      newIndex = strlen(v7);                    // 길이 22
      if ( v7[newIndex - i - 1] != *((_BYTE *)&realKEy + i) )
        return nullsub_2(flag);
    }
    v14 = 0;
  }
  return nullsub_2(flag);
}

*((_BYTE*)&realKey+i)) 의 의미를 알아야 함 . 

위의 코드를 통해 페이로드를 작성하면 다음과 같다.

#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <string.h>
// round 1 

int main()
{
	char env[5] = "bi0s";
	char xorVal = 0;
	char inputKey[23] = "\0";
	char realKey[23] = "4919197161836291817161";
	char v7[] = "\0";
	int index = 0;
	char v3;
 // 2단계
	for (int i = 0; i < strlen(realKey); i++)
	{
		inputKey[i] = realKey[i] ^= 0xC; 
	}
//  1단계 
	for (int i = 0; i < strlen(env); i++)
	{
		xorVal += env[i];
	}
	xorVal /= 30; // result = 0xC

	while (index != 22)
	{
		if (index & 1)
			v3 = inputKey[index] - 4;
		else
			v3 = inputKey[index] + 4;
			v7[index] = v3;
			v7[index] ^= xorVal;
			++index;
	}
	printf("%s", inputKey);
	// 85=5=5;=:=4?:>5=4=;=:=
}

상기 주석 1단계를 통해 xorVal을 알아낸 다음 그 xorVal과 realKey를 XOR 취하는 작업으로 거슬러 올라가야함.

 

#include <stdio.h>
#include <string.h>
// round 2
int main()
{
	char inputKey[23] = "85=5=5;=:=4?:>5=4=;=:=";
	char v7[32] = "\0";
	int index = 0;
	int v3 = 0;
	for (int i = 0; i < strlen(inputKey); i++)
	{
		//v3 = inputKey[i]; // 1byte
		if (i % 2 == 0)
			v3 = -4;
		else
			v3 = 4;
		inputKey[i] = inputKey[i] + v3;
	}
	printf("HackCTF{%s}\n", inputKey);
}

The END.

'0x02 Reverse Engineer > 0x03. Etc' 카테고리의 다른 글

Rootme Prob . ELF x86 - KeygenMe  (0) 2020.02.06
KaKaoTalk MacOS Analysis  (0) 2020.01.26
[Rootme] Go lang Basic  (0) 2019.01.31
rootme elf nanometis  (0) 2018.05.22
rootme elf-antidebug  (0) 2018.05.22