프로그램을 실행하면 앞문제들과 동일하다.
메인함수도 동일
비교함수를 IDA로 바로 디컴파일 해보자.
__int64 __fastcall sub_7FF6A5671000(__int64 a1)
{
int i; // [rsp+0h] [rbp-18h]
for ( i = 0; (unsigned __int64)i < 0x1C; ++i )
{
if ( ((unsigned __int8)(16 * *(_BYTE *)(a1 + i)) | ((int)*(unsigned __int8 *)(a1 + i) >> 4)) != byte_7FF6A5673000[i] )
return 0i64;
}
return 1i64;
}
3번문제와 동일하게 a1은 덤프를 통해 가져올 수 있다.
00007FF6A5673000 24 27 13 C6 C6 13 16 E6 47 F5 26 96 47 F5 46 27 $'.ÆÆ..æGõ&.GõF'
00007FF6A5673010 13 26 26 C6 56 F5 C3 C3 F5 E3 E3 00 00 00 00 00 .&&ÆVõÃÃõãã.....
파이썬에 저 계산식 그대로 코드를 작성해보자.
str = '24 27 13 C6 C6 13 16 E6 47 F5 26 96 47 F5 46 27 13 26 26 C6 56 F5 C3 C3 F5 E3 E3'
str = tuple(str.split(" "))
res = ''
for i in range(len(str)):
res += chr(16*(int(str[i], 16)) | int(str[i], 16)>>4)
print(res)
어딘가 문제가 생긴 것 같다.
어셈블리어 코드를 자세히 살펴봤더니 디컴파일이 잘못됐는건지 계산식에서 [and ecx,F0]라는 구문이 생략된 것 같다.
ecx에 계산결과를 계속 저장하고 있었으니 위 파이썬 코드에서 &0xF0를 추가하면 해결될 것 같다.
str = '24 27 13 C6 C6 13 16 E6 47 F5 26 96 47 F5 46 27 13 26 26 C6 56 F5 C3 C3 F5 E3 E3'
str = tuple(str.split(" "))
res = ''
for i in range(len(str)):
res += chr(16*(int(str[i], 16)) & 0xF0 | int(str[i], 16)>>4)
print(res)
중간에 계산식 오류를 찾느라 어셈블리어와 디컴파일된 코드를 비교하며 하나하나 따라가다보니 어셈블리어 계산식이 살짝씩 눈에 들어오기 시작했다. 목표는 디컴파일 없이 어셈블리어만 보고 직접 계산식을 세워보는 건데 가능할지는 잘 모르겠다.
'Security > Reversing' 카테고리의 다른 글
Dreamhack rev-basic-6 (0) | 2022.06.01 |
---|---|
Dreamhack rev-basic-5 (0) | 2022.05.28 |
Dreamhack rev-basic-3 (0) | 2022.05.24 |
Dreamhack rev-basic-2 (0) | 2022.05.23 |
Dreamhack rev-basic-1 (0) | 2022.05.23 |