2013 csaw CTF Quals Writeup
Reversing1 - 100pt
안티 디버깅 걸려있는데 상관 안쓰고 풀었다.
int __cdecl __noreturn main(int argc, const char **argv, const char **envp)
{
unsigned int len; // kr00_4
unsigned int v4; // ecx
if ( IsDebuggerPresent() )
{
len = strlen(Text);
v4 = 0;
if ( len >> 2 != -1 )
{
do
*&Text[4 * v4++] ^= 0xCCDDEEFF;
while ( v4 < (len >> 2) + 1 );
}
MessageBoxA(0, Text, "Flag", 2u);
}
else
{
MessageBoxA(0, Text, "Flag", 2u);
}
ExitProcess(0);
}
Text 변수 긁어와서 xor연산해주는데 그거 역연산 짜주면 된다.
from idaapi import *
from idautils import *
from itertools import *
a = []
for i in range(32):
a.append(hex(Byte(0x408B20+i)))
a = [int(i,16) for i in a]
b = [0xff,0xee,0xdd,0xcc]
flag = ""
for x,y in zip(a,cycle(b)):
flag += chr(x^y)
print flag
FLAG : flag{this1isprettyeasy:)}
Reversing2 - 200pt
이 문제도 아까랑 그냥 거의 비슷하다.
int __cdecl __noreturn main(int argc, const char **argv, const char **envp)
{
HANDLE v3; // edi
char *v4; // esi
unsigned int v5; // ecx
unsigned int v6; // eax
v3 = HeapCreate(0x40000u, 0, 0);
v4 = HeapAlloc(v3, 8u, 37u);
memcpy_s(v4, 36u, &unk_409B10, 36u);
if ( !*(*(__readfsdword(0x18u) + 48) + 2) )
{
__debugbreak();
v5 = 0;
v6 = (strlen(v4 + 1) >> 2) + 1;
if ( v6 > 0 )
{
do
*&v4[4 * v5++] ^= 0x8899AABB;
while ( v5 < v6 );
}
}
MessageBoxA(0, v4, "Flag", 2u);
HeapFree(v3, 0, v4);
HeapDestroy(v3);
ExitProcess(0);
}
할당해주는 값 긁어와서 xor해주면된다.
from idaapi import *
from idautils import *
from itertools import *
a = []
for i in range(40):
a.append(hex(Byte(i+0x409b10)))
a = [int(i,16) for i in a]
b = [0xbb,0xaa,0x99,0x88]
flag=""
for x,y in zip(a,cycle(b)):
flag += chr(x^y)
print flag
FLAG : flag{number2isalittlebitharder:p}
DotNet - 100pt
값을 입력받아서 그것과 num2랑 xor한 값이 num3면 된다고 한다.
밑에 부분은 AES Decrypt 해주는 부분이 있는데 맞는 입력 값을 넣으면 저기서 플래그를 만들어주는 거다.
using System;
using System.IO;
using System.Security.Cryptography;
using System.Threading;
namespace dotnetreversingchallenge
{
// Token: 0x02000002 RID: 2
internal class aClass
{
// Token: 0x06000001 RID: 1 RVA: 0x00002060 File Offset: 0x00000260
private static void Main(string[] args)
{
Console.WriteLine("Greetings challenger! Step right up and try your shot at gaining the flag!");
Console.WriteLine("You'll have to know the pascode to unlock the prize:");
string value = Console.ReadLine();
long num = Convert.ToInt64(value);
long num2 = 53129566096L;
long num3 = 65535655351L;
if ((num ^ num2) == num3)
{
Console.WriteLine("yay");
}
else
{
Console.WriteLine("Incorrect, try again!");
}
try
{
byte[] iv = new byte[]
{
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue,
byte.MaxValue
};
byte[] array = new byte[16];
BitConverter.GetBytes(num).CopyTo(array, 0);
BitConverter.GetBytes(num).CopyTo(array, 8);
string s = "ls/5RTxwflDrqr5G8pO9cQ1NlgQcFjcJj9x4z7oIhlfY4w42GAFqKbyzwqHAZQBZa5ctysKKWIbTgU2VxoRYohxCbPyV6sEU/tn+sIxNg6A/r5OJnIMqTs0seMrzWh5J";
Thread.Sleep(500);
Console.WriteLine(aClass.DecryptStringFromBytes_Aes(Convert.FromBase64String(s), array, iv));
Console.WriteLine("Success!!");
}
catch (Exception arg)
{
Console.WriteLine("ERROR!!! darn. huh? how did I get here? Hmm, something must have gone wrong. What am I doing?", arg);
}
Console.WriteLine("press key to continue");
Console.ReadKey();
}
// Token: 0x06000002 RID: 2 RVA: 0x00002174 File Offset: 0x00000374
private static byte[] EncryptStringToBytes_Aes(string plainText, byte[] Key, byte[] IV)
{
if (plainText == null || plainText.Length <= 0)
{
throw new ArgumentNullException("plainText");
}
if (Key == null || Key.Length <= 0)
{
throw new ArgumentNullException("Key");
}
if (IV == null || IV.Length <= 0)
{
throw new ArgumentNullException("Key");
}
byte[] result;
using (AesCryptoServiceProvider aesCryptoServiceProvider = new AesCryptoServiceProvider())
{
aesCryptoServiceProvider.Key = Key;
aesCryptoServiceProvider.IV = IV;
ICryptoTransform transform = aesCryptoServiceProvider.CreateEncryptor(aesCryptoServiceProvider.Key, aesCryptoServiceProvider.IV);
using (MemoryStream memoryStream = new MemoryStream())
{
using (CryptoStream cryptoStream = new CryptoStream(memoryStream, transform, CryptoStreamMode.Write))
{
using (StreamWriter streamWriter = new StreamWriter(cryptoStream))
{
streamWriter.Write(plainText);
}
result = memoryStream.ToArray();
}
}
}
return result;
}
// Token: 0x06000003 RID: 3 RVA: 0x000022CC File Offset: 0x000004CC
private static string DecryptStringFromBytes_Aes(byte[] cipherText, byte[] Key, byte[] IV)
{
if (cipherText == null || cipherText.Length <= 0)
{
throw new ArgumentNullException("cipherText");
}
if (Key == null || Key.Length <= 0)
{
throw new ArgumentNullException("Key");
}
if (IV == null || IV.Length <= 0)
{
throw new ArgumentNullException("IV");
}
string result = null;
using (AesCryptoServiceProvider aesCryptoServiceProvider = new AesCryptoServiceProvider())
{
aesCryptoServiceProvider.Key = Key;
aesCryptoServiceProvider.IV = IV;
ICryptoTransform transform = aesCryptoServiceProvider.CreateDecryptor(aesCryptoServiceProvider.Key, aesCryptoServiceProvider.IV);
using (MemoryStream memoryStream = new MemoryStream(cipherText))
{
using (CryptoStream cryptoStream = new CryptoStream(memoryStream, transform, CryptoStreamMode.Read))
{
using (StreamReader streamReader = new StreamReader(cryptoStream))
{
result = streamReader.ReadToEnd();
}
}
}
}
return result;
}
}
}
간단하다 매우 53129566096 ^ 65535655351해주면 13371337255이 나오는데 이거 입력해주면 된다.
FLAG : flag{I'll create a GUI interface using visual basic...see if I can track an IP address.}
bikinibonanza - 150pt
.NET 파일이다.
여기 마지막에 플래그 출력해주는 분기가 있는데 brfalse.s를 brtrue.s로 바꿔주면 된다.
그러면 플래그 출력해주는 분기로 가서 아무거나 입력해도 플래그가 출력된다.
FLAG : key(0920303251BABE89911ECEAD17FEBF30)