Next, I will talk about how to develop the 2.1 beat03 builde017 card recorder (I) in the previous article. I will not discuss memory scanning and Protocol parsing for the moment. I will focus on analyzing hook APIs first. To hook an API, you need to find the API. How can you find the API? The call for playing traveling music has been found above. A call can be understood as a function. Is the process of walking a same-level call, a higher-level call, or a lower-level call?
First, let's explain the "level" problem. Define two functions first:
Void playmusic (){
// After compilation, a call is used to play music.
}
Void displaymove (){
// After compilation, It is a mobile call.
}
The so-called same-level call is
Bool framefunc (){
Playmusic ();
Displaymove ();
}
The upper-level call calls playmusic in displaymove, and the lower-level call is playmusic calls displaymove. Based on the debugging steps, the same level is found in the current function; the higher level is returned and the lower level is involved. Operations are different, so this is very important. In OD, if it is a same-level call, it is to press F8 to find it slowly; for a higher-level call, CTRL + F9 is required to return to the upper-level function; for a lower-level call, press F7 in the playmusic call place. Of course, we don't know how to call it. We can use the exclusion method. In this case, we must be patient.
The first is the same-level function.
00411540/$8b4424 04 mov eax, dword ptr ss: [esp + 4]
00411544 |. 53 push EBX
00411545 |. 05 17 fcffff add eax,-3e9; Switch (cases 3e9... 3ed)
0041154a |. 55 push EBP
0041154b |. 56 push ESI
0041154c |. 83f8 04 CMP eax, 4
0041154f |. 57 push EDI
00411550 |. 8bd9 mov EBX, ECx
00411552 |. 0f87 df010000 ja junqirpg.00411737
00411558 |. ff2485 401741> jmp dword ptr ds: [eax * 4 + 411740]
0041155f |> 8b83 10010000 mov eax, dword ptr ds: [EBX + 110]; Case 3e9 of switch 00411545
The aboveCodeIs the beginning of a same-level function. It can be seen that this is a switch statement. When a breakpoint occurs at 00411540, the status is displayed:
Stack SS: [0012f240] = 000003ec
Eax= 00000000
Local call from 002.167ae
That is to say, this function is called by the upper-level function where the address is 003667ae. Keep pressing F9 and find that this is an infinite loop. As we all know when using frameworks to develop games, a general game framework has two infinite loops. One is used to update data and perform logical operations, while the other is used to write the screen. This function can be understood as an update function in framefunc in HGE (C ++ 2D game engine) or xNa (. NET's 3D Game Development Framework. The meaning of this Code is equivalent:
Bool framefunc (){
Switch ()
Case 1:
Break;
Case 2
Break;
}
In Case 1, compile the code
0041155f |> 8b83 10010000 mov eax, dword ptr ds: [EBX + 110]; Case 3e9 of switch 00411545
The place where the breakpoint is located. It is found that moving will trigger the breakpoint. This indicates that the correct call has been found. As to whether the call is in this Code or in the method called by this Code, we need to analyze it again.
Game developers know that the frequency of framefunc calls is related to FPS. Generally, it takes at least 24 calls per second. Case1 code must have a multi-thread processing method, which makes analysis very difficult. After the breakpoint is down at F, press F9 to find that the code is executed more than once, and the principle is similar to that of a stack. Press the step and write the screen in renderfunc by step.
The operands are recorded on the 004976f4 address.
0041158b |> \ A1 f4764900 mov eax, dword ptr ds: [4976f4]
And the operand is assigned to eax. There is no call between 0041155f and 0041158b. This code may be related to what we are looking for. Of course it can be found below. When a piece moves from one place to another, it may have been given the form of "from" and "to". The following describes the path analysis.
in fact, we only need the data from and. Why are these two data so important? If you use the memory scanning method to develop the card recorder, you will encounter this problem. But when your child sacrifices an enemy child, which one does it eat? This is the trouble.