Run program, draw something and press check button. We’ll get the “Wrong” message box:
Load program to OllyDBG, search for all referenced text strings to find Wrong message:
Scroll up we can see a big loop that compare values at bl & cl, if not equal it will jump to the code displays wrong message:
Place bp at 004013A3 > > /8A11 mov dl, byte ptr [ecx]
, press F9 to run, draw something and press check button, we will stop at bp. Look for the value store at [ecx] & [eax+ecx]
:
Notice the 0x0047E060 address, this address belongs to rersource section (.rsrc):
Mem0ry map, item 22 Address=0047E000 Size=00016000 (90112.) Owner=ImagePrc 00400000 Section=.rsrc Contains=resources Type=Imag 01001002 Access=R Initial access=RWE
Convert VA 0x0047E060 to Offset, we have 0x9060. Let’s use hex editor to open program, go to 0x9060:
Find and select all offsets has 0xFF value, we have the block size is:
This value corressponding with the number of iterations that we see in the loop check. So we know that the memory area pointed by ecx register must contains all the same value. How can we have theses value? Scroll up to the top of function, we see the code:
0040116A . 8D4424 48 lea eax, dword ptr [esp+0x48] 0040116E . 50 push eax ; /pPaintstruct 0040116F . 56 push esi ; |hWnd 00401170 . FF15 E0504000 call dword ptr [<BeginPaint>] ; \BeginPaint
The BeginPaint function prepares the specified window for painting and fills a PAINTSTRUCT structure with information about the painting. With this information, we guess that we have to draw something and then it can be used to compare with fixed data at offset 9060. Look at the code bellow BeginPaint:
0040117C . 68 2000CC00 push 0xCC0020 ; /ROP = SRCCOPY 00401181 . 6A 00 push 0x0 ; |YSrc = 0x0 00401183 . 6A 00 push 0x0 ; |XSrc = 0x0 00401185 . 51 push ecx ; |hSrcDC => 0B0100AF 00401186 . 68 96000000 push 0x96 ; |Height = 96 (150.) 0040118B . 68 C8000000 push 0xC8 ; |Width = C8 (200.) 00401190 . 6A 00 push 0x0 ; |YDest = 0x0 00401192 . 6A 00 push 0x0 ; |XDest = 0x0 00401194 . 50 push eax ; |hDestDC 00401195 . FF15 30504000 call dword ptr [<BitBlt>]; \BitBlt
The BitBlt function performs a bit-block transfer of the color data corresponding to a rectangle of pixels from the specified source device context into a destination device context. Scroll down a little bit, we see this code:
00401200 . 68 96000000 push 0x96 ; /Height = 96 (150.) 00401205 . 68 C8000000 push 0xC8 ; |Width = C8 (200.) 0040120A . 56 push esi ; |hDC 0040120B . FF15 0C504000 call dword ptr [<CreateCompatibleBitm>; \CreateCompatibleBitmap
The CreateCompatibleBitmap function creates a bitmap compatible with the device that is associated with the specified device context. Notice the Height and Width value, these value is the same with values at BitBlt call. Collect all information, we now know that we need to create a bitmap image with Height = 96 (150.) and Width = C8 (200.), and this image must contains 0x15F90 bytes from offset 0x9060. Let’s use mspaint to create a bitmap image with size is 200×150, open it in hex editor, then copy all data from offset 0x9060 and paste to offset of bitmap image that contains 0xFF values. Save image and open it, we get the flag:
End.