Cheat Engine Forum Index Cheat Engine
The Official Site of Cheat Engine
 
 FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 


[Tutorial] Cheating Galactic Civilization 2 (V1.0) - Part 2

 
Post new topic   Reply to topic    Cheat Engine Forum Index -> Cheat Engine Tutorials -> Auto Assembler tutorials
View previous topic :: View next topic  
Author Message
Recifense
I post too much
Reputation: 166

Joined: 17 Mar 2008
Posts: 3688
Location: Pernambuco - Brazil

PostPosted: Sun Jan 09, 2011 9:52 pm    Post subject: [Tutorial] Cheating Galactic Civilization 2 (V1.0) - Part 2 Reply with quote


    This is the second part of the tutorial

    The first part can be found at: http://forum.cheatengine.org/viewtopic.php?t=529802

    4 - Cheating Ship's Movement Points:


    ___ TutNote 13: Enable the script "Tutorial_MET_MRT" and load the game (that we saved in 1.4). Press DONE for the Report, Research and Colony screens.
    ___ Note that the game starts with two ships: A flagship and a Colony ship. Let's have a look at each ship, paying close attention to numbers:

    Code:

       The Hit Points       : Flagship = 17/17   and Colony = 1/1;
       The Moves Left points: Flagship = 3/0     and Colony = 2/0;
       Sensor Range         : Flagship = 9 pc    and Colony = 3 pc;
       Range                : Flagship = 1.6 gct and Colony = 1.5 gct;
       Level                : Flagship = 0
       Colonists           :                    Colony = 100
       


    ___ TutNote 14: So we know each ship "Moves Left" points. If you click on icon "i" just after the ship's name, you can get additional information.
    ___ Note that the ship can auto-survey, auto-explore, auto-retreat and auto-attack. This is a tip of how we should implement the MLP cheat.
    ___ We cannot enable free movement for all our ships because they may not stop moving. Wink So, the best approach here is to enable just the
    ___ one that is under our selection. Let's see what we can do with movement points.

    ______ A) Go to CE, write 3 on value field, change the Scan type to 'Exact Value' and Value type to '4 bytes'. Enable Fast scan by clicking in its check-box;
    ______ Now click on FIRST SCAN. A lot of addresses was found;
    ______ B) Go back to the game and move you flagship to a nearby place in order to decrease MLP by 1;
    ______ C) Go back to CE and write 2 on value field. Now click on NEXT SCAN. A few addresses remained;
    ______ D) Go back to the game and move you flagship to a nearby place in order to decrease MLP by 1;
    ______ E) Go back to CE and write 1 on value field. Now click again on NEXT SCAN. Now only 2-3 addresses remained;
    ______ F) Go back to the game and move you flagship to a nearby place in order to decrease MLP by 1;
    ______ G) Go back to CE and write 0 on value field. Now click oncemore on NEXT SCAN. Now only 1 address remained;
    ______ H) If this didn't happen to you. End your game turn and repeat the steps from A to G;
    ______ I) Transfer the address to CE's table and change its value to 4;
    ______ J) Go back to game and verify the flagship "Moves Left" points. If everything was fine, it will be 4.
    ______ K) Now let's see what codes access this address.

    ______ k.01 - Right-click on this entry on the table and select "Find out what accesses this address";
    ______ k.02 - Go back to the game. Note the 1 code line is already on the codelist;
    ______ k.03 - Move the flagship. Note that 3 more code lines were added to the codelist;
    ______ k.04 - Let's have a look at those code lines

    Code:

       C18 0055B790 - 83 b9 f0 01 00 00 00          - cmp dword ptr [ecx+000001f0],00         
       C19 004DB21D - 8b 80 f0 01 00 00             - mov eax,[eax+000001f0]
       C20 0056716A - 39 ae f0 01 00 00             - cmp [esi+000001f0],ebp
       C21 00567198 - 29 86 f0 01 00 00             - sub [esi+000001f0],eax
       


    ___ TutNote 15: C18 verifies if the ship can move. Select it on list and click on SHOW DISASSEMBLER. Go to CE's "Memory Viewer" and scroll up the code. There are
    ___ INT 3 codes near it, change at least the 5 nearest ones to NOP to avoid crashes. Go gack to the list and add this line code to the codelist. Add "- MP" to the description.
    ___ Now select MORE INFORMATION. We can conclude that the MLP is at offset 01f0 of a structure and that ECX is the base of this structure. So create a new structure, naming
    ___ it "Ship" and with size 0x400 (From the PlayerInfo structure, just click on File->New Window). Change the address to the value of ECX.
    ___ Select Structures->Define new structure. Change the name to Ship. Click OK. Click YES. Change the value to 0x400. Click OK.) Rename offset 01f0 to "Moves Left".
    ___ Note that at the offset 000c we have the ship's name. Rename it to "Ship Name", type = String, bytesize = 32.
    ___ C19 and C20 just read the MLP value. C21 decreases the MLP. Transfer this code line to the codelist. Add "- MP" to the description. This will be the hacking point.
    ___ But we cannot implement it yet. We need to know how we can distinguish our ships from those of the AIs (foes).

    ___ TutNote 16: Close the found list (press STOP/CLOSE).Select C18 from the Advanced Options->Code List, right-click on it and choose "Find out what addresses this code writes to"
    ___ (If you forgot to change the INT 3's into NOPs, the game will crash).

    ______ A) Go back to the game. Note that an address was added to Changed Addresses list. It is related to the flagship.
    ______ B) Select the Colony Ship. Note that a second address was added to the list.
    ______ C) Go to CE and right-click on the second address and choose "Show register states";
    ______ D) Add an extra address on the Ship structure and change its address to the value of ECX (of the register states list);
    ______ E) Seeing the 2 ships structure side-by-side we can conlude:

    ______ e.01 - Offset 000C is really the ship's name;
    ______ e.02 - Offset 01ac is the range, so rename it to "Range";
    ______ e.03 - Offset 01dc is the Hit Points, so rename it to "Hit Points"
    ______ e.04 - Offset 01f0 is the "Moves Left";

    ______ F) Let's see what we can do with ships' addresses. Select the flagship. Copy its address from the
    ______ structure. Go to CE and click on the Hex box near the value to found field. Click on NEW SCAN.
    ______ Select the value field and paste the flagship address on it. Turn FAST SCAN on. Click on FIRST SCAN.
    ______ A few addresses appeared.
    ______ G) Go to the game and select the Colony Ship.
    ______ H) Go back to CE and copy the Colony ship address from the structure to the search field. Select "Changed value" for "Scan Type" and press NEXT SCAN;
    ______ I) Now only 3-4 addresses remained. Now go to the game and select a planet.
    ______ J) Back to CE, note that two addresses point to 00000000. Add them to the table. Rename them to "Pointer to Selected";
    ______ K) Let's see what codes access the first pointer by right-clicking on it and select "Find out what accesses this address";
    ______ L) Go back to the game. Note that two code lines were added to the list. Select the flagship. Note that other code lines were
    ______ added to the list. Note that only one updates the content of the pointer. Select it on the list and Add it to the codelist.
    ______ Add "- pSel Ship" to the description. Close the code finder (STOP/CLOSE).

    Code:

       C22 005CE76B - 89 b7 5c d1 01 00             - mov [edi+0001d15c],esi
       


    ______ M) Add the flagship MLP address to the table and freeze it. Now Let's try to find other ships. Two AI factions with 2 ships each are enough.
    ______ N) When you find an AI ship, click on it and observe the first pointer content address. Add an extra adress for each new ship on the Ship structure
    ______ and change each address to the content of the pointer.
    ______ O) Now with that we have at least 6 ships, let's have another look on the ship structure:

    ______ o.01 - Offset 00c8 is OwnerID. The same value found at offset 0004 and 04f4 of Playerinfo structure. Rename it to "OwnerID";
    ______ o.02 - Offset 01d4 is a pointer to ship type. Just look in the area they point to by right-clicking on each pointer, choosing "memory browse pointer" and observing
    ______ the Copy memory on the Memory Viewer. Reneme it to "pTypeInfo";
    ______ o.03 - Offset 01d8 is the Type ID. Rename it to "TypeID"
    ______ o.04 - Offset 01e0 can be the maximum Hit Points value. But we are not sure yet.

    ___ TutNote 17: Now we have enough information to implement a cheat for the Moves Left points. Since the script is getting bigger,
    ___ let's also implement a mechanism to enable/disable each cheat individually. Here is what have to do:

    ______ A) Implement a mechanism to enable/disable each cheat individually;
    ______ B) Modify the _MonET script to add get the player ID;
    ______ C) Implement a script to get the selected ship address (C22);
    ______ D) Implement a script to give free movement to player's selected ship (C21).

    ______ AATut 6: If we use an instruction like "cmp [iEnableME],0", the compiler will not know if the content of
    ______ the memory address "iEnableME" is a byte, or a word, or a double-word, etc. So we need to make it clear what
    ______ it is. For this purpose we use the directive "type PTR", where type can be BYTE, WORD, DWORD or QWORD).
    ______ Since "iEnableME" is a double-word, the corrent instruction is: cmp DWORD PTR [iEnableME],0.
    ______ Instructions that involves registers like cmp al,[esi+04] or cmp ax,[esi+18] or ,mov eax,[iEnableME] don't need
    ______ the directive, since the compiler knows that register AL is a BYTE, AX is a WORD and EAX is a DWORD.

    ______ He is our script till now:

    Code:

    {
     Script for Galactic Civilization 2 V1.0
     Example on a Tutorial
     Implementing a script to monitor the player's Treasure Value
     Implementing a script to monitor the player's Research Technology
     Implementing a script to monitor the player's Ship Moves Left (new)
    }

    [ENABLE]
    alloc(MyCode,1024)         // Allocating memory. 1024 (1Kb) is enough.

    label(_MonET)              // Declaring a label
    label(_BackME)             // Declaring a label
    label(_ExitME)             // Declaring a label
    label(_MonRT)              // Declaring a label
    label(_BackMR)             // Declaring a label
    label(_ExitMR)             // Declaring a label
    label(_MonSelShip)         // Declaring a label (new)
    label(_BackMSS)            // Declaring a label (new)
    label(_ExitMSS)            // Declaring a label (new)
    label(_MonMovesLeft)       // Declaring a label (new)
    label(_BackMML)            // Declaring a label (new)
    label(_ExitMML)            // Declaring a label (new)
    label(pPlayer)             // Declaring a label
    label(pSelShip)            // Declaring a label (new)
    label(iPlayerID)           // Declaring a label (new)
    label(iEnableME)           // Declaring a label (new)
    label(iEnableMR)           // Declaring a label (new)
    label(iEnableMM)           // Declaring a label (new)

    registersymbol(MyCode)     // Registering "MyCode",    so it can be easily find it in the memory viewer.
    registersymbol(pPlayer)    // Registering "pPlayer",   so it can be easily used in a table or structure.
    registersymbol(pSelShip)   // Registering "pSelShip",  so it can be easily used in a table or structure.  (new)
    registersymbol(iPlayerID)  // Registering "iPlayerID", so it can be easily used in a table or structure. (new)
    registersymbol(iEnableME)  // Registering "iEnableME", so it can be easily used in a table or structure. (new)
    registersymbol(iEnableMR)  // Registering "iEnableMR", so it can be easily used in a table or structure. (new)
    registersymbol(iEnableMM)  // Registering "iEnableMM", so it can be easily used in a table or structure. (new)

    //======================= Just to separate script parts

    MyCode:                    // This is the address of the memory that was allocated

    //======================= Just to separate script parts
    // This script will monitor the player's Treasure to guarantee a minimum value (10000)
    // [Note] The register EBP is modified by the original code, so we are free to use it.

    _MonET:                    // This is the address of this script part (Same as MyCode)
     mov [pPlayer],edi         // Let's save the content of register EDI for debugging

     mov ebp,[edi+04]          // Get the player ID at offset 0004 (new)
     mov [iPlayerID],ebp       // Saving it for further use        (new)

     cmp dword ptr [iEnableME],0 // The content of variable iEnableME is 0?                (new)
     je _ExitME                // Jump if yes (e = equal to) We assumed that 0 is disabled.(new)

     mov ebp,#10000            // The assemble instruction MOV is used to load value into an address or register
                               // In this case, EBP will be loaded with 10000 (the # indicates that it is a decimal value)
     cmp ebp,[edi+000004f0]    // The assemble instruction CMP is use to compare two values
                               // In this case, the content of the register EBP is compared to the
                               // content of the memory pointed by the content of register EDI plus offset 000004f0
     jle _ExitME               // The assemble instruction Jcc is used to perform conditional jumps.
                               // In this case, the condition is LE which means (less or equal).
     mov [edi+000004f0],ebp    // If the content of EBP is greater than that at the memory
                               // then the value at the memory will be changed to 10000
    _ExitME:                   // This is the label needed because of the conditional jump
     mov ebp,[edi+000004f0]    // Original code should be executed
     jmp _BackME               // Go back to the original code

    //======================= Just to separate script parts
    // This script will monitor the player's Research Progress to guarantee that it is concluded in one turn
    // [Note] The register EDX is modified by the original code, so we are free to use it.

    _MonRT:                    // This is the address of this script part
     cmp dword ptr [iEnableMR],0 // The content of variable iEnableMR is 0?                (new)
     je _ExitMR                // Jump if yes (e = equal to) We assumed that 0 is disabled.(new)

     cmp esi,[pPlayer]         // The register ESI points to a PlayerInfo structure. Is it ours?
     jne _ExitMR               // The code will jump if it is not equal (NE = not equal)

     mov edx,[esi+00000504]      // Get the pointer to the array of research progress values
                               // Remember that at this point: EDX = Base, EDI = Index   and EAX = value needed to complete research
     mov [edx+edi*4],eax       // So let's update the current research progress with the value needed to complete this research

    _ExitMR:                   // This is the label needed because of the conditional jump
     mov edx,[esi+00000504]      // Original code should be executed
     jmp _BackMR               // Go back to the original code

    //======================= Just to separate script parts    (new)
    // This script will monitor when a ship is selected in order to save its address

    _MonSelShip:               // This is the address of this script part
     pushfd                    // Note that the first instruction after the hacking point is a conditional
                               // jump (jE). So we have to preserve the EFLAGS by pushing them into the stack.
     or esi,esi                // ESI or ESI return Zero if the content of register ESI is 0
     jz _ExitMSS               // Jump if content od ESI is 0 (i.e. a NULL pointer)

     mov [pSelShip],esi        // Save in the variable pSelShip, the address of just selected ship
                               // It will be used on the Moves Left script
    _ExitMSS:
     popfd                     // We need to restore the EFLAGS status.
                               // So we take back its value from the stack.
     mov [edi+0001d15c],esi    // Original code should be executed
     jmp _BackMSS              // Go back to the original code

    //======================= Just to separate script parts   (new)
    // This script will monitor a ship movement points and will not let it decrease
    // if it is the player's last select ship

    _MonMovesLeft:             // This is the address of this script part
     push ebx                  // A register will be needed in this script. Since the original code
                               // is not modifying one, we decided to use the register EBX.
                               // But we have to preserve its content. So push it into the stack.
     cmp dword ptr [iEnableMM],0 // The content of variable iEnableMR is 0?
     je _ExitMML               // Jump if yes (e = equal to) We assumed that 0 is disabled.

     cmp esi,[pSelShip]        // The register ESI points to a Ship structure. Is it the selected?
     jne _ExitMML              // The code will jump if it is not equal (NE = not equal)

     mov ebx,[esi+000000c8]    // Get the value stored at offset 00C8 (The OwnerID)
     cmp ebx,[iPlayerID]       // Compare the ship's OwnerID with the PlayerID
     jne _ExitMML              // Jump if they are not equal (NE)

     mov eax,00000000          // Make the content of register EAX = 0
                               // The instruction XOR EAX,EAX could have been used (it is shorter)
    _ExitMML:                  // This is the label needed because of the conditional jump
     pop ebx                   // We need to restore the register EBX content.
                               // So we take back its value from the stack.
     sub [esi+000001f0],eax    // Original code should be executed
                               // It subtracts from Ship's Moves Left the value stored in register EAX
     jmp _BackMML              // Go back to the original code

    //======================= Variables ==============================
    // We can put the variables here, right after the last script.

    pPlayer:                   // The variable name followed by : (in fact, it is a lable)
     dd 0                      // Reserving 4 bytes and initializing its value with 0
    pSelShip:                  // The variable name followed by : (in fact, it is a lable)   (new)
     dd 0                      // Reserving 4 bytes and initializing its value with 0
    iPlayerID:                 // The variable name followed by : (in fact, it is a lable)
     dd #999                   // Reserving 4 bytes and initializing its value with 999
    iEnableME:                 // The variable name followed by : (in fact, it is a lable)   (new)
     dd 1                      // Reserving 4 bytes and initializing its value with 1
    iEnableMR:                 // The variable name followed by : (in fact, it is a lable)   (new)
     dd 1                      // Reserving 4 bytes and initializing its value with 1
    iEnableMM:                 // The variable name followed by : (in fact, it is a lable)   (new)
     dd 1                      // Reserving 4 bytes and initializing its value with 1
          
    //=================== The Haking Points ==========================
    // It can also be placed before the scripts. But let's put it after them, just to remind us
    // that the script was created and loaded into the computer memory and now can be accessed.

    galciv2.exe+07ebad:        // The address to be intercepted
     jmp _MonET                // Jumping to the script (this instruction is 5 bytes long)
     nop                       // Adding a NOP (90h) instruction to complete 6 bytes (remember this!)
    _BackME:                   // This label is the address to go back. It is galciv2.exe+07ebad plus 6 bytes.

    galciv2.exe+18f0f2:        // The address to be intercepted   (new)
     jmp _MonRT                // Jumping to the script (this instruction is 5 bytes long)
     nop                       // Adding a NOP (90h) instruction to complete 6 bytes (remember this!)
    _BackMR:                   // This label is the address to go back. It is galciv2.exe+18f0f2 plus 6 bytes.

    galciv2.exe+1ce76b:        // The address to be intercepted   (new)
     jmp _MonSelShip           // Jumping to the script (this instruction is 5 bytes long)
     nop                       // Adding a NOP (90h) instruction to complete 6 bytes (remember this!)
    _BackMSS:                  // This label is the address to go back. It is galciv2.exe+1ce76b plus 6 bytes.

    galciv2.exe+167198:        // The address to restore the code   (new)
     jmp _MonMovesLeft         // Jumping to the script (this instruction is 5 bytes long)
     nop                       // Adding a NOP (90h) instruction to complete 6 bytes (remember this!)
    _BackMML:                  // This label is the address to go back. It is galciv2.exe+167198 plus 6 bytes.

    //======================= Just to separate script parts
    // This part is performed when we disable the script by uncking its frozen box.
    // Here we should:
    // - Restore the original codes
    // - Unregister the symbols
    // - Deallocate (free) the memory

    [DISABLE]
    galciv2.exe+07ebad:        // The address to restore the code
     mov ebp,[edi+000004f0]    // The code to be restored (this instruction is 6 bytes long)
                               // = 8b af f0 04 00 00
    galciv2.exe+18f0f2:        // The address to restore the code   (new)
     mov edx,[esi+00000504]    // The code to be restored (this instruction is 6 bytes long)
                               // = 8b 96 04 05 00 00
    galciv2.exe+1ce76b:        // The address to restore the code   (new)
     mov [edi+0001d15c],esi    // The code to be restored (this instruction is 6 bytes long)
                               // = 89 b7 5c d1 01 00
    galciv2.exe+167198:        // The address to restore the code   (new)
     sub [esi+000001f0],eax    // The code to be restored (this instruction is 6 bytes long)
                               // = 29 86 f0 01 00 00

    unregistersymbol(MyCode)   // UNregistering "MyCode",    so it cannot be accessed anymore.
    unregistersymbol(pPlayer)  // UNregistering "pPlayer",   so it cannot be accessed anymore.
    unregistersymbol(pSelShip) // UNregistering "pSelShip",  so it cannot be accessed anymore. (new)
    unregistersymbol(iPlayerID)// UNregistering "iPlayerID", so it cannot be accessed anymore. (new)
    unregistersymbol(iEnableME)// UNregistering "iEnableME", so it cannot be accessed anymore. (new)
    unregistersymbol(iEnableMR)// UNregistering "iEnableMR", so it cannot be accessed anymore. (new)
    unregistersymbol(iEnableMM)// UNregistering "iEnableMM", so it cannot be accessed anymore. (new)

    dealloc(MyCode)              // DE-allocating memory so the system can use it for other purposes.


    ______ A) Time to save the script. On the Auto Assemble, left-click on File and then select Save.
    ______ B) Let's add the script to CE table. Left-click on File and then select "Assigned to current cheat table".
    ______ CE will check the script and, if everything is ok, it will be added to the table with the discription "Auto assemble cheat".
    ______ Change it to "Tutorial_MET_MRT_MSS_MML".
    ______ C) Save the table;
    ______ D) Disable the previous script by unchecking its frozen box.
    ______ E) Now enable the new script;
    ______ F) Add the new variables to the table: pSelShip, iPlayerID, iEnableME, iEnableMR and iEnableMM.
    ______ G) Let's test the enable section of the script:

    ______ g.01 - Select your flagship and check the content of pSelShip. Now move it around;
    ______ g.02 - Check if the Moves Left value does not change;
    ______ g.03 - Select your colony ship and check the content of pSelShip. Now move it around;
    ______ g.04 - Check if the Moves Left value does not change;
    ______ g.05 - Change the value of iEnableMM to 0 and move the colony ship;
    ______ g.06 - Chack if the Moves Left value decreases;
    ______ g.07 - Change the value of iEnableMM back to 1 and move the colony ship;
    ______ g.08 - Check if the Moves Left value does not change;
    ______ g.09 - So the new cheat is working. Smile

    ___ TutNote 18: That concludes the 3rd part of the tutorial. Wink

    It continues...

    The Third and last part can be found at:
    http://forum.cheatengine.org/viewtopic.php?t=529804

    Cheers!
Back to top
View user's profile Send private message Send e-mail
Display posts from previous:   
Post new topic   Reply to topic    Cheat Engine Forum Index -> Cheat Engine Tutorials -> Auto Assembler tutorials All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You can download files in this forum


Powered by phpBB © 2001, 2005 phpBB Group

CE Wiki   IRC (#CEF)   Twitter
Third party websites