# Writeup for VishwaCTF'25 (Reverse) > Author: Nikola --- ## Hungry Friends >Author: Nikola >Description: >Hungry Friends Feed my friend. Author: Abhinav @ .0_0.ace.0_0. https://github.com/CyberCell-Viit/VishwaCTF-25-Challenges/tree/main/Reverse%20Engineering/Hungry%20Friends --- ### Solution - This challenges they give me `snakes.exe`. I will analyze it in IDA. - This main() function. ```cpp= int __cdecl main(int argc, const char **argv, const char **envp) { __time32_t v3; // eax int v4; // eax int v5; // ebx int v6; // eax int v7; // eax int v9; // [esp-Ch] [ebp-10h] int v10; // [esp-8h] [ebp-Ch] __main(); v3 = time(0); srand(v3); HIDE_CURSOR(); INIT_GAME(); SPAWN_FOOD(); while ( !GAME_OVER ) { if ( _kbhit() ) { v4 = _getch(); if ( v4 == 100 ) { DX = 1; DY = 0; } else if ( v4 > 100 ) { if ( v4 == 115 ) { DX = 0; DY = 1; } else if ( v4 == 119 ) { DX = 0; DY = -1; } } else if ( v4 == 97 ) { DX = -1; DY = 0; } } MOVE_SNAKE(); DRAW_GAME(); if ( CHAKDE == 9999 ) SHOW_FLAG(); Sleep(0x64u); } v5 = CHAKDE; v6 = std::operator<<<std::char_traits<char>>(&std::cout, "Game Over! Score: ", v9, v10); v7 = std::ostream::operator<<(v6, v5); std::ostream::operator<<(v7, &std::endl<char,std::char_traits<char>>); return 0; } ``` - I will proceed to check the `SHOW_FLAG()` function. ```cpp= int SHOW_FLAG(void) { int v0; // eax int v1; // eax int v3; // [esp+8h] [ebp-30h] int v4; // [esp+Ch] [ebp-2Ch] _BYTE v5[28]; // [esp+18h] [ebp-20h] BYREF decrypt[abi:cxx11](v5, &encrypted); v0 = std::operator<<<std::char_traits<char>>(&std::cout, "\n\nCongratulations! Flag: ", v3, v4); v1 = std::operator<<<char>(v0, v5); std::ostream::operator<<(v1, &std::endl<char,std::char_traits<char>>); return (std::string::~string)(v5); } ``` - I continue to analyze the ```=decrypt[abi:cxx11](v5, &encrypted);``` function. ```cpp= int __cdecl decrypt[abi:cxx11](int a1, int a2) { __int64 v2; // rax int v3; // eax unsigned int v4; // eax _DWORD *v5; // eax int v6; // edx _BYTE *v7; // edi __int64 v9; // [esp+4h] [ebp-44h] char v10; // [esp+17h] [ebp-31h] BYREF __int64 v11; // [esp+18h] [ebp-30h] unsigned int i; // [esp+24h] [ebp-24h] __int64 v13; // [esp+28h] [ebp-20h] LODWORD(v2) = generateKey(); v13 = v2; std::allocator<char>::allocator(&v10); v3 = std::vector<unsigned long long>::size(a2); std::string::basic_string(a1, v3, 32, &v10); (std::allocator<char>::~allocator)(&v10); for ( i = 0; ; ++i ) { v4 = std::vector<unsigned long long>::size(a2); if ( v4 <= i ) break; v5 = std::vector<unsigned long long>::operator[](i); v6 = v5[1]; LODWORD(v11) = *v5; HIDWORD(v11) = v6; v7 = std::string::operator[](a1, i, v9, HIDWORD(v9)); v9 = 17LL; *v7 = (v11 - (v13 ^ (1337 * i))) / 0x11; v13 ^= v11; } return a1; } ``` - Here i saw the program returns the value of the key. ```cpp= __int64 generateKey(void) { return 4183820235LL; } ``` - From the above logic I will write the decode function. ```python= def decrypt(a2, generate_key): a1 = [''] * len(a2) key = generate_key() for i in range(len(a2)): cipher_value = a2[i] plain_char = (cipher_value - (key ^ (1337 * i))) // 0x11 a1[i] = chr(plain_char) key ^= cipher_value return ''.join(a1) a2 = [] def generate_key(): return 4183820235 flag = decrypt(a2, generate_key) print(flag) ``` - However we don't have the encrypted data yet. It will be hidden in the stack so I will exploit it. - I will try to encode the format flag using the above mechanism and look in the stack. ![image](https://hackmd.io/_uploads/rkQ1zTcskg.png) - Here is the encrypted data. - Script solve. ```python= def decrypt(a2, generate_key): a1 = [''] * len(a2) key = generate_key() for i in range(len(a2)): cipher_value = a2[i] plain_char = (cipher_value - (key ^ (1337 * i))) // 0x11 a1[i] = chr(plain_char) key ^= cipher_value return ''.join(a1) a2 = [0xf9600d81, 0x166c, 0x1df7, 0x1562, 0x83e, 0xd01, 0x134d, 0x2be2, 0x591, 0xbde, 0x1b0a,0x0bfd,0x0c9a,0x8076,0xf5cc,0x073b,0x1d84,0x145f,0x21bc,0x092b,0x043d,0x08aa,0x1a31,0x0d90,0x1205,0xe6f3,0x0715,0x138b,0x08da,0x1369,0x1ade,0x368c,0x0ae5,0x05ff,0x22c0,0x46b0,0x79c1, 0x8032 ] def generate_key(): return 4183820235 flag = decrypt(a2, generate_key) print(flag) ``` > Flag: VishwaCTF{th3r3_4r3_5n4k35_all_4r0und} ## Safe Box >Author: Nikola >Description: >There are many ways, but the choice is yours. Author: Soham @sohamkolte https://github.com/CyberCell-Viit/VishwaCTF-25-Challenges/tree/main/Reverse%20Engineering/Safe%20Box --- ### Solution - This challenges they give me file `.NET` and i have to attack and get the flag from them - When I run it it asks me to enter the box password to unlock the flag but if you enter it three times you won't be able to open it anymore. ![image](https://hackmd.io/_uploads/SkJ6mp9jyl.png) - I was going to analyze the Assembly-CSharp.dll file to see how it works but it is Obfuscated. ![image](https://hackmd.io/_uploads/H1C7Nacoke.png) - I was going to analyze the Assembly-CSharp.dll file to see how it works but it is Obfuscated - I will beautify the code with d4dot. https://github.com/de4dot/de4dot ![image](https://hackmd.io/_uploads/HyfeL65oke.png) - Now the code is easier to read and analyze. - But wait I tried to edit the code and run the `Safe` file again and it still doesn't change anything. Maybe they are tricking me with a fake code. - After I rummaged around I found it. It was the original code for the `Safe` file. - Here name file `UnityEngine.NetworkUtils.dll` ![image](https://hackmd.io/_uploads/S1iT865okx.png) - Here it is checking if i have entered it more than three times i will disable it by deleting it. ![image](https://hackmd.io/_uploads/Sk28DT9o1e.png) ![image](https://hackmd.io/_uploads/r1hPPa9syl.png) - And this is the main function that needs to be modified so that the box is opened to get the flag. ![image](https://hackmd.io/_uploads/H1baD6cjyx.png) - I will disable it by changing the condition to always true. ![image](https://hackmd.io/_uploads/ryGfd6qikg.png) - Then i start fetch and get flag from program ![image](https://hackmd.io/_uploads/SyIuO6coyx.png) > Flag: WishwaCTF{h3r3_y0u_@r3}