<?xml version="1.0" encoding="utf-8"?>
<CheatTable CheatEngineTableVersion="52">
  <CheatEntries>
    <CheatEntry>
      <ID>15</ID>
      <Description>"Auto-Attach and Version Check"</Description>
      <VariableType>Auto Assembler Script</VariableType>
      <AssemblerScript>[enable]
{$LUA}
ShowMessage('This table auto-attaches to InstanceServerG.exe, auto-detects which game is loaded, and verifies version 1.153 automatically.')
{$ASM}

[disable]
</AssemblerScript>
    </CheatEntry>
    <CheatEntry>
      <ID>1</ID>
      <Description>"How to use"</Description>
      <VariableType>Auto Assembler Script</VariableType>
      <AssemblerScript>[ENABLE]
{$lua}
ShowMessage('1) Run the game (the main menu is fine).\n\n2) Load this table - it attaches to InstanceServerG.exe and auto-detects Red Alert or Tiberian Dawn.\n\n3) Tick the cheats you want under the game you are playing.\n\n4) Start a mission - the cheats engage automatically and re-hook every mission.')
{$asm}

[DISABLE]
</AssemblerScript>
    </CheatEntry>
    <CheatEntry>
      <ID>2</ID>
      <Description>"[MAIN] Red Alert 1.153"</Description>
      <Options moHideChildren="1"/>
      <GroupHeader>1</GroupHeader>
      <CheatEntries>
        <CheatEntry>
          <ID>4</ID>
          <Description>"Infinite Money  (min 70,000)"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
RA_MMM = true
{$ASM}

[disable]
{$LUA}
RA_MMM = false
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>5</ID>
          <Description>"Instant Build"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
RA_MCP = true
pcall(writeInteger,"iEnableMCP",1)
{$ASM}

[disable]
{$LUA}
RA_MCP = false
pcall(writeInteger,"iEnableMCP",0)
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>13</ID>
          <Description>"Infinite Power"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
RA_PWR = true
{$ASM}

[disable]
{$LUA}
RA_PWR = false
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>11</ID>
          <Description>"No Fog of War (Reveal Map)"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
RA_FOG = true
{$ASM}

[disable]
{$LUA}
RA_FOG = false
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>16</ID>
          <Description>"No Friendly Fire"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
RA_FF = true
pcall(writeInteger,"iEnableFF",1)
{$ASM}

[disable]
{$LUA}
RA_FF = false
pcall(writeInteger,"iEnableFF",0)
{$ASM}
</AssemblerScript>
        </CheatEntry>
      </CheatEntries>
    </CheatEntry>
    <CheatEntry>
      <ID>6</ID>
      <Description>"[MAIN] Tiberian Dawn 1.153"</Description>
      <Options moHideChildren="1"/>
      <GroupHeader>1</GroupHeader>
      <CheatEntries>
        <CheatEntry>
          <ID>8</ID>
          <Description>"Infinite Money  (min 70,000)"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
TD_MMM = true
{$ASM}

[disable]
{$LUA}
TD_MMM = false
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>9</ID>
          <Description>"Instant Build"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
TD_MCP = true
pcall(writeInteger,"iEnableMCP_TD",1)
{$ASM}

[disable]
{$LUA}
TD_MCP = false
pcall(writeInteger,"iEnableMCP_TD",0)
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>14</ID>
          <Description>"Infinite Power"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
TD_PWR = true
{$ASM}

[disable]
{$LUA}
TD_PWR = false
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>12</ID>
          <Description>"No Fog of War (Reveal Map)"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
TD_FOG = true
{$ASM}

[disable]
{$LUA}
TD_FOG = false
{$ASM}
</AssemblerScript>
        </CheatEntry>
        <CheatEntry>
          <ID>17</ID>
          <Description>"No Friendly Fire"</Description>
          <VariableType>Auto Assembler Script</VariableType>
          <AssemblerScript>[enable]
{$LUA}
TD_FF = true
pcall(writeInteger,"iEnableFF_TD",1)
{$ASM}

[disable]
{$LUA}
TD_FF = false
pcall(writeInteger,"iEnableFF_TD",0)
{$ASM}
</AssemblerScript>
        </CheatEntry>
      </CheatEntries>
    </CheatEntry>
    <CheatEntry>
      <ID>10</ID>
      <Description>"Diagnosis Mode"</Description>
      <VariableType>Auto Assembler Script</VariableType>
      <AssemblerScript>[enable]
{$LUA}
DIAG = true
{$ASM}

[disable]
{$LUA}
DIAG = false
{$ASM}
</AssemblerScript>
    </CheatEntry>
  </CheatEntries>
  <UserdefinedSymbols/>
  <Comments>============================================================
 Command &amp; Conquer Remastered Collection
 Infinite Money + Instant Build + Infinite Power + No Fog of War + No Friendly Fire  (HUMAN PLAYER ONLY)
============================================================
 Process to open : InstanceServerG.exe  (NOT ClientG.exe)
 Game version    : 1.153 (745903) - verified against local DLLs
 Table version   : v2.13
 Cheat Engine    : 7.0 or newer
============================================================

[USAGE]
1) Run the game (the main menu is fine).
2) Load this table - it auto-attaches and auto-detects the game.
3) Tick the cheats you want under the game you are playing.
4) Start a mission - the cheats engage and re-hook automatically.

[WHAT IT DOES]
 - Infinite Money : credits stay at 70,000+.
 - Infinite Power : power stays at 10,000+.
 - Instant Build  : production completes fast (one step per frame, respecting the unit exit animation).
 - No Fog of War  : reveals the map and structures for you only.
 - No Friendly Fire : your units' attacks and their kill-explosions no longer damage your own units (healing still works).

[PLAYER-ONLY]
 All cheats read the human player's pointer/owner, so AI is unaffected.

[TWEAKING]
 - Edit the clamp values inside the table-level LuaScript (70000 / 10000 / #53 / #108).
============================================================
</Comments>
  <LuaScript>if not syntaxcheck then
  getAutoAttachList().add('InstanceServerG.exe')

  -- Returns (true, ver) if game is 1.153, (false, ver) if wrong, (nil, reason) if undetermined
  function DSH_GAME_VERSION()
    local pid = getProcessIDFromProcessName('InstanceServerG.exe')
    if pid == nil then return nil, 'game not running' end
    local exe = nil
    local okm, mods = pcall(enumModules, pid)
    if okm and mods ~= nil then
      for _, m in pairs(mods) do
        if type(m) == 'table' and m.Name == 'InstanceServerG.exe' then exe = m.PathToFile end
      end
    end
    if exe == nil then return nil, 'exe path unknown' end
    local okv, raw, info = pcall(getFileVersion, exe)
    if not okv or info == nil then return nil, 'version unknown' end
    local major = tonumber(info.major) or 0
    local minor = tonumber(info.minor) or 0
    local release = tonumber(info.release) or 0
    local ver = string.format('%d.%d.%d', major, minor, release)
    local match = (major == 1 and minor == 153)
    return match, ver
  end

  local vwarned = false
  local function tryAttach()
    local pname = process
    if pname ~= nil and string.lower(pname) == 'instanceserverg.exe' then
      if not vwarned then
        local ok, ver = DSH_GAME_VERSION()
        if ok == false then
          ShowMessage('Wrong game version: found ' .. tostring(ver) .. '. This table targets 1.153 (745903).')
        end
        vwarned = true
      end
      return
    end
    local pid = getProcessIDFromProcessName('InstanceServerG.exe')
    if pid ~= nil then openProcess(pid) end
  end

  tryAttach()

  if AUTHWATCH == nil then
    AUTHWATCH = createTimer(nil, false)
    AUTHWATCH.Interval = 2000
    AUTHWATCH.OnTimer = function(t) tryAttach() end
    AUTHWATCH.Enabled = true
  end

  if MAIN_TIMER == nil then
    local RA_hookScript = [=[
alloc(RA_Build,96)
label(RA_Build_Ret)
label(RA_Build_Skip)
label(iEnableMCP)
registersymbol(iEnableMCP)
RedAlert.dll+50FC0:
jmp RA_Build
nop
RA_Build_Ret:
RA_Build:
  push eax
  cmp dword [iEnableMCP],0
  je RA_Build_Skip
  mov eax,[RedAlert.dll+194088]
  test eax,eax
  je RA_Build_Skip
  cmp [ecx+2B],eax
  jne RA_Build_Skip
  mov dword [ecx+0E],1
  cmp dword [ecx],#30
  jge RA_Build_Skip
  mov dword [ecx],#30
RA_Build_Skip:
  pop eax
  push ebp
  mov ebp,esp
  sub esp,10
  jmp RA_Build_Ret
align 10
iEnableMCP:
dd 0
alloc(RA_FF,256)
label(RA_FF_Original)
label(iEnableFF)
registersymbol(iEnableFF)
RedAlert.dll+A7430:
jmp RA_FF
nop
RA_FF:
  cmp dword [iEnableFF],0
  je RA_FF_Original
  mov eax,[esp+4]
  mov eax,[eax]
  test eax,eax
  jle RA_FF_Original
  mov eax,[esp+10]
  test eax,eax
  je RA_FF_Original
  mov edx,[eax+107]
  cmp edx,-1
  je RA_FF_Original
  mov eax,[RedAlert.dll+12c580]
  imul edx,[eax+8]
  add edx,[eax+14]
  cmp edx,[RedAlert.dll+194088]
  jne RA_FF_Original
  mov edx,[ecx+107]
  cmp edx,-1
  je RA_FF_Original
  mov eax,[RedAlert.dll+12c580]
  imul edx,[eax+8]
  add edx,[eax+14]
  cmp edx,[RedAlert.dll+194088]
  jne RA_FF_Original
  xor eax,eax
  ret 14
RA_FF_Original:
  push ebp
  mov ebp,esp
  sub esp,14
  jmp RedAlert.dll+A7436
align 10
iEnableFF:
dd 0
]=]

    local RA_unhookScript = [=[
unregistersymbol(iEnableMCP)
dealloc(RA_Build)
unregistersymbol(iEnableFF)
dealloc(RA_FF)
]=]

    local TD_hookScript = [=[
alloc(TD_Build,96)
label(TD_Build_Normal)
label(iEnableMCP_TD)
registersymbol(iEnableMCP_TD)
TiberianDawn.dll+40147:
jmp TD_Build
nop
nop
TD_Build:
  push eax
  cmp dword [iEnableMCP_TD],0
  je TD_Build_Normal
  mov eax,[TiberianDawn.dll+1296c0]
  test eax,eax
  je TD_Build_Normal
  cmp [esi+18],eax
  jne TD_Build_Normal
  mov byte [esi+3],1
  cmp word [esi],#84
  jge TD_Build_Normal
  mov word [esi],#84
TD_Build_Normal:
  pop eax
  jmp TiberianDawn.dll+4015a
align 10
iEnableMCP_TD:
dd 0
alloc(TD_FF,256)
label(TD_FF_Original)
label(iEnableFF_TD)
registersymbol(iEnableFF_TD)
TiberianDawn.dll+92930:
jmp TD_FF
TD_FF:
  cmp dword [iEnableFF_TD],0
  je TD_FF_Original
  mov eax,[esp+4]
  mov eax,[eax]
  test eax,eax
  jle TD_FF_Original
  mov eax,[esp+10]
  test eax,eax
  je TD_FF_Original
  mov eax,[eax+93]
  test eax,eax
  je TD_FF_Original
  cmp eax,[TiberianDawn.dll+1296c0]
  jne TD_FF_Original
  mov eax,[ecx+93]
  test eax,eax
  je TD_FF_Original
  cmp eax,[TiberianDawn.dll+1296c0]
  jne TD_FF_Original
  xor eax,eax
  ret 10
TD_FF_Original:
  push ebp
  mov ebp,esp
  push ebx
  push esi
  jmp TiberianDawn.dll+92935
align 10
iEnableFF_TD:
dd 0
]=]

    local TD_unhookScript = [=[
unregistersymbol(iEnableMCP_TD)
dealloc(TD_Build)
unregistersymbol(iEnableFF_TD)
dealloc(TD_FF)
]=]

    local function dllBase(name)
      local b = getAddressSafe(name)
      if b == nil or b == 0 then return nil end
      return b
    end

    local RA_Hooked = false
    local RA_Base = nil
    local RA_FOG_APPLIED = false
    local TD_Hooked = false
    local TD_Base = nil
    local TD_FOG_APPLIED = false
    local Checked = false
    local Err = false

    MAIN_TIMER = createTimer(nil, false)
    MAIN_TIMER.Interval = 500
    MAIN_TIMER.OnTimer = function(t)
      local ok, err = pcall(function()
        local target = getProcessIDFromProcessName('InstanceServerG.exe')
        if target ~= nil then
          local cur = getOpenedProcessID()
          if cur == nil or cur == 0 or cur ~= target then
            openProcess(target)
          end
        end

        if not Checked then
          local pid2 = getOpenedProcessID()
          if pid2 ~= nil and pid2 ~= 0 then
            local vok, vver = DSH_GAME_VERSION()
            if vok == false then
              ShowMessage('Wrong game version: found ' .. tostring(vver) .. '. This table targets 1.153 (745903).')
            end
            Checked = true
          end
        end

        pcall(loadNewSymbols)

        -- Red Alert
        local raBase = dllBase('RedAlert.dll')
        if raBase ~= nil then
          if not RA_Hooked or RA_Base ~= raBase then
            if RA_Hooked then pcall(autoAssemble, RA_unhookScript) end
            if autoAssemble(RA_hookScript) then
              RA_Hooked = true
              RA_Base = raBase
              RA_FOG_APPLIED = false
            end
          end
        else
          if RA_Hooked then
            pcall(autoAssemble, RA_unhookScript)
            RA_Hooked = false
            RA_Base = nil
          end
        end

        -- Tiberian Dawn
        local tdBase = dllBase('TiberianDawn.dll')
        if tdBase ~= nil then
          if not TD_Hooked or TD_Base ~= tdBase then
            if TD_Hooked then pcall(autoAssemble, TD_unhookScript) end
            if autoAssemble(TD_hookScript) then
              TD_Hooked = true
              TD_Base = tdBase
              TD_FOG_APPLIED = false
            end
          end
        else
          if TD_Hooked then
            pcall(autoAssemble, TD_unhookScript)
            TD_Hooked = false
            TD_Base = nil
          end
        end

        -- sync build flags
        if RA_Hooked then
          if RA_MCP then pcall(writeInteger, 'iEnableMCP', 1) else pcall(writeInteger, 'iEnableMCP', 0) end
        end
        if TD_Hooked then
          if TD_MCP then pcall(writeInteger, 'iEnableMCP_TD', 1) else pcall(writeInteger, 'iEnableMCP_TD', 0) end
        end

        -- sync friendly-fire flags
        if RA_Hooked then
          if RA_FF then pcall(writeInteger, 'iEnableFF', 1) else pcall(writeInteger, 'iEnableFF', 0) end
        end
        if TD_Hooked then
          if TD_FF then pcall(writeInteger, 'iEnableFF_TD', 1) else pcall(writeInteger, 'iEnableFF_TD', 0) end
        end

        -- money + power (Red Alert)
        if RA_Hooked then
          local p = readInteger(raBase + 0x194088)
          if p ~= nil and p ~= 0 then
            if RA_MMM then
              local c = p + 0x1B4
              local v = readInteger(c)
              if v ~= nil and v &lt; 70000 then writeInteger(c, 70000) end
            end
            if RA_PWR then
              local c = p + 0x200
              local v = readInteger(c)
              if v ~= nil and v &lt; 10000 then writeInteger(c, 10000) end
            end
          end
        end

        -- money + power (Tiberian Dawn)
        if TD_Hooked then
          local p = readInteger(tdBase + 0x1296c0)
          if p ~= nil and p ~= 0 then
            if TD_MMM then
              local c = p + 0x10E
              local v = readInteger(c)
              if v ~= nil and v &lt; 70000 then writeInteger(c, 70000) end
            end
            if TD_PWR then
              local c = p + 0x15a
              local v = readInteger(c)
              if v ~= nil and v &lt; 10000 then writeInteger(c, 10000) end
            end
          end
        end

        -- fog (Red Alert)
        if RA_Hooked then
          if RA_FOG and not RA_FOG_APPLIED then
            pcall(autoAssemble, [=[
RedAlert.dll+44bd0:
db B0 01 83 C4 04
RedAlert.dll+44be0:
db B0 01 83 C4 04
RedAlert.dll+44bef:
db B0 00 83 C4 04
]=])
            pcall(writeByte, raBase + 0x19bda4, 1)
            RA_FOG_APPLIED = true
          elseif not RA_FOG and RA_FOG_APPLIED then
            pcall(autoAssemble, [=[
RedAlert.dll+44bd0:
db E8 0B D4 FE FF
RedAlert.dll+44be0:
db E8 8B D3 FE FF
RedAlert.dll+44bef:
db E8 2C D3 FE FF
]=])
            pcall(writeByte, raBase + 0x19bda4, 0)
            RA_FOG_APPLIED = false
          end
        end

        -- fog (Tiberian Dawn)
        if TD_Hooked then
          if TD_FOG and not TD_FOG_APPLIED then
            pcall(autoAssemble, [=[
TiberianDawn.dll+37ecd:
db B0 01 83 C4 04
TiberianDawn.dll+37edc:
db B0 01 83 C4 04
]=])
            pcall(writeByte, tdBase + 0x126bd1, 1)
            TD_FOG_APPLIED = true
          elseif not TD_FOG and TD_FOG_APPLIED then
            pcall(autoAssemble, [=[
TiberianDawn.dll+37ecd:
db E8 CE B7 FE FF
TiberianDawn.dll+37edc:
db E8 8F B7 FE FF
]=])
            pcall(writeByte, tdBase + 0x126bd1, 0)
            TD_FOG_APPLIED = false
          end
        end
      end)
      if not ok and not Err then
        if DIAG then ShowMessage('Cheat script error: ' .. tostring(err)) end
        Err = true
      end
    end
    MAIN_TIMER.Enabled = true
  end
end
</LuaScript>
</CheatTable>
