 |
Cheat Engine The Official Site of Cheat Engine
|
View previous topic :: View next topic |
Author |
Message |
HenryEx Expert Cheater
Reputation: 2
Joined: 18 Dec 2011 Posts: 100
|
Posted: Tue Feb 25, 2025 3:55 pm Post subject: Mono much slower in CE 7.6 |
|
|
I'm working on a table that heavily relies on mono features atm. And while it's a welcome change in CE 7.6 that some method invokes don't just crash the game anymore (no more tedious hooking of game functions and firing methods in asm), i've noticed that mono features are also much, much slower than in CE 7.5.
It's not just activating mono features - which was near instant in 7.5 and seems to take a good 1.5 seconds in 7.6. I automate setting up symbols to methods i use in scripts, and there's a marked increase in runtime when i test them side-by-side.
This is my setup log on CE 7.5.
Code: | Registering 58 method symbols, please wait...
Got Address for :Character:DamageCharacter in 0.005000 seconds.
Got Address for :Character:DecreaseMana in 0.005000 seconds.
Got Address for :Character:ReduceMorale in 0.005000 seconds.
Got Address for :BattleCharacter:ReduceActionPool in 0.005000 seconds.
Got Address for :BattleCharacter:GetCurrentActionPool in 0.006000 seconds.
Got Address for :BattleCharacter:GetCurrentBattleStat in 0.007000 seconds.
Got Address for :BattleManagerV2:StartPostBattleScreen in 0.006000 seconds.
Got Address for :BattleManagerV2:IsCounterValid in 0.005000 seconds.
Got Address for :BattleCharacter:CanCounter in 0.005000 seconds.
Got Address for :BattleCharacter:GetChainAttackChance in 0.006000 seconds.
Got Address for :HubManager:RemoveGold in 0.005000 seconds.
Got Address for :Character:GetMoodValue in 0.005000 seconds.
Got Address for :Character:GetBonusExp in 0.006000 seconds.
Got Address for :UpgradeLineUI:GenerateUpgradeValue in 0.005000 seconds.
Got Address for :PromotionWindowUI:Reroll in 0.005000 seconds.
Got Address for :CampActionUIButton:IsAvailable in 0.005000 seconds.
Got Address for :Inventory:GetFreeSpace in 0.004000 seconds.
Got Address for :Inventory:EnoughSpaceForOneEquipment in 0.005000 seconds.
Got Address for :Inventory:EnoughSpaceForItem in 0.004000 seconds.
Got Address for :Inventory:EnoughSpaceForLoot in 0.005000 seconds.
Got Address for :LootTransferWindowUI:GetMaxTransferrableAmount in 0.006000 seconds.
Got Address for :AdventurerParty:RemoveMember in 0.005000 seconds.
Got Address for :MonsterFigure:CheckDetection in 0.005000 seconds.
Got Address for :MonsterFigure:EndTurn in 0.004000 seconds.
Got Address for :BattleManagerV2:Flee in 0.005000 seconds.
Got Address for :DiceUI+<RollDice>d__31:MoveNext in 0.574000 seconds.
Got Address for :QuestMapManager:CheckExhaustion in 0.006000 seconds.
Got Address for :TrapTile:GetSpotDifficulty in 0.005000 seconds.
Got Address for :RecruitmentWindowUI:InitWindow in 0.005000 seconds.
Got Address for :AttributeChangeLine:UpdateUI in 0.004000 seconds.
Got Address for :CharacterCustomizeWindow:UpdateAcceptButton in 0.005000 seconds.
Got Address for :CharacterCustomizeWindow+<>c:<InitWindow>b__45_0 in 0.604000 seconds.
Got Address for :TraitCustomizationLineUI:UpdateUI in 0.006000 seconds.
Got Address for :CharacterTemplate:GetRandomCharacter in 0.008000 seconds.
Got Address for :BattleCharacter:InvalidCaches in 0.005000 seconds.
Got Address for :Character:InvalidCaches in 0.003000 seconds.
Got Address for :BattleCharacterInfoUI:Update in 0.005000 seconds.
Got Address for :BattleCharacterInfoUI:Close in 0.005000 seconds.
Got Address for :AdventurerOverviewUI:Update in 0.006000 seconds.
Got Address for :AdventurerOverviewUINGPlus:Update in 0.004000 seconds.
Got Address for :AdventurerOverviewUIQuestMap:Update in 0.005000 seconds.
Got Address for :AdventurerOverviewUI:Close in 0.005000 seconds.
Got Address for :AdventurerOverviewUIQuestMap:Close in 0.006000 seconds.
Got Address for :Character:AddTrait in 0.006000 seconds.
Got Address for :Character:RemoveTrait in 0.005000 seconds.
Got Address for :Database:AddGuildItem in 0.005000 seconds.
Got Address for :BattleManagerV2:Update in 0.007000 seconds.
Got Address for :Inventory:addItem in 0.006000 seconds.
Got Address for :AdventurerFigure:Update in 0.005000 seconds.
Got Address for :HubManager:Update in 0.005000 seconds.
Got Address for :BaseCharacter:AddSkill in 0.005000 seconds.
Got Address for :Character:AddSkillCharacter in 0.005000 seconds.
Got Address for :Character:GetWage in 0.005000 seconds.
Got Address for :Character:IncreaseInjuries in 0.004000 seconds.
Got Address for :RelationShip:getRelationPoints in 0.005000 seconds.
Got Address for :RecruitmentWindowUI:OnSelectClassTemplate in 0.005000 seconds.
Got Address for :RecruitmentWindowUI:OnAcceptCharacterCustomizeWindow in 0.005000 seconds.
Got Address for :CharacterCustomizeWindow:RandomizeName in 0.006000 seconds.
Fetching class fields, please wait...
Done in 3.6610 seconds. |
Here's the same code running on CE 7.6.
Code: | Registering 58 method symbols, please wait...
Got Address for :Character:DamageCharacter in 0.008000 seconds.
Got Address for :Character:DecreaseMana in 0.008000 seconds.
Got Address for :Character:ReduceMorale in 0.007000 seconds.
Got Address for :BattleCharacter:ReduceActionPool in 0.007000 seconds.
Got Address for :BattleCharacter:GetCurrentActionPool in 0.007000 seconds.
Got Address for :BattleCharacter:GetCurrentBattleStat in 0.014000 seconds.
Got Address for :BattleManagerV2:StartPostBattleScreen in 0.008000 seconds.
Got Address for :BattleManagerV2:IsCounterValid in 0.007000 seconds.
Got Address for :BattleCharacter:CanCounter in 0.007000 seconds.
Got Address for :BattleCharacter:GetChainAttackChance in 0.008000 seconds.
Got Address for :HubManager:RemoveGold in 0.009000 seconds.
Got Address for :Character:GetMoodValue in 0.008000 seconds.
Got Address for :Character:GetBonusExp in 0.007000 seconds.
Got Address for :UpgradeLineUI:GenerateUpgradeValue in 0.008000 seconds.
Got Address for :PromotionWindowUI:Reroll in 0.007000 seconds.
Got Address for :CampActionUIButton:IsAvailable in 0.008000 seconds.
Got Address for :Inventory:GetFreeSpace in 0.007000 seconds.
Got Address for :Inventory:EnoughSpaceForOneEquipment in 0.008000 seconds.
Got Address for :Inventory:EnoughSpaceForItem in 0.009000 seconds.
Got Address for :Inventory:EnoughSpaceForLoot in 0.015000 seconds.
Got Address for :LootTransferWindowUI:GetMaxTransferrableAmount in 0.008000 seconds.
Got Address for :AdventurerParty:RemoveMember in 0.007000 seconds.
Got Address for :MonsterFigure:CheckDetection in 0.008000 seconds.
Got Address for :MonsterFigure:EndTurn in 0.007000 seconds.
Got Address for :BattleManagerV2:Flee in 0.008000 seconds.
Got Address for :DiceUI+<RollDice>d__31:MoveNext in 2.077000 seconds.
Got Address for :QuestMapManager:CheckExhaustion in 0.010000 seconds.
Got Address for :TrapTile:GetSpotDifficulty in 0.016000 seconds.
Got Address for :RecruitmentWindowUI:InitWindow in 0.010000 seconds.
Got Address for :AttributeChangeLine:UpdateUI in 0.007000 seconds.
Got Address for :CharacterCustomizeWindow:UpdateAcceptButton in 0.010000 seconds.
Got Address for :CharacterCustomizeWindow+<>c:<InitWindow>b__45_0 in 2.032000 seconds.
Got Address for :TraitCustomizationLineUI:UpdateUI in 0.010000 seconds.
Got Address for :CharacterTemplate:GetRandomCharacter in 0.008000 seconds.
Got Address for :BattleCharacter:InvalidCaches in 0.028000 seconds.
Got Address for :Character:InvalidCaches in 0.030000 seconds.
Got Address for :BattleCharacterInfoUI:Update in 0.016000 seconds.
Got Address for :BattleCharacterInfoUI:Close in 0.008000 seconds.
Got Address for :AdventurerOverviewUI:Update in 0.011000 seconds.
Got Address for :AdventurerOverviewUINGPlus:Update in 0.010000 seconds.
Got Address for :AdventurerOverviewUIQuestMap:Update in 0.015000 seconds.
Got Address for :AdventurerOverviewUI:Close in 0.010000 seconds.
Got Address for :AdventurerOverviewUIQuestMap:Close in 0.009000 seconds.
Got Address for :Character:AddTrait in 0.007000 seconds.
Got Address for :Character:RemoveTrait in 0.010000 seconds.
Got Address for :Database:AddGuildItem in 0.009000 seconds.
Got Address for :BattleManagerV2:Update in 0.010000 seconds.
Got Address for :Inventory:addItem in 0.015000 seconds.
Got Address for :AdventurerFigure:Update in 0.009000 seconds.
Got Address for :HubManager:Update in 0.010000 seconds.
Got Address for :BaseCharacter:AddSkill in 0.011000 seconds.
Got Address for :Character:AddSkillCharacter in 0.007000 seconds.
Got Address for :Character:GetWage in 0.014000 seconds.
Got Address for :Character:IncreaseInjuries in 0.007000 seconds.
Got Address for :RelationShip:getRelationPoints in 0.008000 seconds.
Got Address for :RecruitmentWindowUI:OnSelectClassTemplate in 0.009000 seconds.
Got Address for :RecruitmentWindowUI:OnAcceptCharacterCustomizeWindow in 0.008000 seconds.
Got Address for :CharacterCustomizeWindow:RandomizeName in 0.007000 seconds.
Fetching class fields, please wait...
Done in 8.4560 seconds. |
From 3 and a half to 8 and a half seconds is a +130% increase in runtime! There's two methods in particular that each take more than two seconds now just to look up.
My symbol register function isn't doing anything particularly fancy either. Basically just this:
Code: | local method, methodAddress
method=mono_findMethod(nameSpace, className, methodName)
if (method==0) then
return nil, string.format("'%s:%s:%s' could not be found",nameSpace,className,methodName)
end
methodAddress = mono_compile_method(method)
if not methodAddress or (methodAddress == 0) then
return nil, string.format("'%s:%s:%s' could not be jitted",nameSpace,className,methodName)
end
return registerSymbol(symbolName, methodAddress, true) |
So just two calls to mono_findMethod and mono_compile_method.
Anything i could do differently to get closer to the old speeds, or is there something that could be optimized?
|
|
Back to top |
|
 |
Dark Byte Site Admin
Reputation: 470
Joined: 09 May 2003 Posts: 25769 Location: The netherlands
|
Posted: Tue Feb 25, 2025 4:48 pm Post subject: |
|
|
Not sure about the speed, stability does cost some performance. But you can now split up the workload in different threads without blocking, though not sure if the bottleneck here is lua or the queries. (if lua, no improvement)
for better speed, if you know the image, you can use mono_image_findClass or mono_image_findClassSlow for the ones with a + in the name, to find the specific class, and then use mono_class_findMethod to get the method
is the target il2cpp ?
_________________
Do not ask me about online cheats. I don't know any and wont help finding them.
Like my help? Join me on Patreon so i can keep helping |
|
Back to top |
|
 |
HenryEx Expert Cheater
Reputation: 2
Joined: 18 Dec 2011 Posts: 100
|
Posted: Wed Feb 26, 2025 4:48 am Post subject: |
|
|
The target is not il2cpp, just regular mono thankfully.
I'll have to take a look at monoscript when i'm home, at work currently. This is a little off-topic, but i'm not really a programmer, so i can have some questions that might seem basic.
As far as i understand, and from googling, Methods are game funcions and Fields are the data they work on - these are collected in Classes. Several Classes can further be grouped under a Namespace (most games don't, so it's often blank, except for external libraries used).
Then above that seem to be Images and Assemblies. I'm guessing the Assembly is the .dll that the relevant code is found in (usually Assembly-CSharp.dll, the thing you open in dnSpy etc.).
What then, is the Image? How do i find it? Is it only addressed via memory or can you find it with a string like with classes? Can i assume that all classes in a namespace share the same Image?
Would of course be cool if i could skip a few steps when bulk-processing methods like that.
|
|
Back to top |
|
 |
HenryEx Expert Cheater
Reputation: 2
Joined: 18 Dec 2011 Posts: 100
|
Posted: Sat Mar 01, 2025 7:53 am Post subject: |
|
|
Had a look at it and rewrote my script to fetch the image for Assembly-CSharp.dll, and just reuse that with manual calling of the functions you suggested. I'm hoping that image addresses don't change and that there aren't multiple images floating around for a given assembly.
That did give a substantial speed boost, for both versions. It really seems to be the monohandler, and less the Lua side of the code that slows things down so heavily. (see the test at the end)
Old CE 7.5
Code: | ==Table Setup==
Launching Mono...
Launched in 0.8170 seconds.
Fetching pointers from game methods...
Got pointers in 0.6910 seconds.
Registering 58 method symbols, please wait...
Got Address for :Character:DamageCharacter() in 0.0010 seconds.
Got Address for :Character:DecreaseMana() in 0.0010 seconds.
Got Address for :BattleCharacter:GetCurrentBattleStat() in 0.0050 seconds.
Got Address for :BattleManagerV2:StartPostBattleScreen() in 0.0020 seconds.
(...)
Got Address for :DiceUI+<RollDice>d__31:MoveNext() in 0.0830 seconds.
Got Address for :CharacterCustomizeWindow+<>c:<InitWindow>b__45_0() in 0.0740 seconds.
(...)
Registered symbols in 0.2820 seconds.
Fetching class fields, please wait...
Got fields in 0.3430 seconds.
Done in 2.1950 seconds.
|
New CE 7.6
Code: | ==Table Setup==
Launching Mono...
Launched in 1.4480 seconds.
Fetching pointers from game methods...
Got pointers in 0.7720 seconds.
Registering 58 method symbols, please wait...
Got Address for :Character:DamageCharacter() in 0.0000 seconds.
Got Address for :Character:DecreaseMana() in 0.0010 seconds.
Got Address for :BattleCharacter:GetCurrentBattleStat() in 0.0040 seconds.
Got Address for :BattleManagerV2:StartPostBattleScreen() in 0.0020 seconds.
(...)
Got Address for :DiceUI+<RollDice>d__31:MoveNext() in 0.3880 seconds.
Got Address for :CharacterCustomizeWindow+<>c:<InitWindow>b__45_0() in 0.3760 seconds.
(...)
Registered symbols in 0.9080 seconds.
Fetching class fields, please wait...
Got fields in 1.0570 seconds.
Done in 4.2750 seconds.
|
Good news: Doesn't take a full 2 seconds to fetch a single method with a + in the name anymore, and setup is way faster in general.
Bad news: CE7.6 is still twice as slow in general as CE7.5
The class fields setup in particular is way slower due to looking up field vartype going through the new class_inEnum functions and such, but that's an outlier. As seen above, even just attaching the mono features takes twice as long.
And it seems far more unstable, too - in CE7.5, you can just disconnect and reconnect easily via the Mono menu, but in CE7.6, it seems to be a one-way street. In almost all cases, when i try to disconnect after connecting once, CE just hangs. Which means that i can't close the game either after a connection, since CE tries to disconnect and hangs, too.
Anyways, i ran some speed tests on this simple function i wrote to get a mono image by name, to compare performance in 7.5 and 7.6. The called functions do almost nothing but write commands directly to the monopipe:
Code: | function getAssemblyImage ( imgname )
local result
for _,v in ipairs( mono_enumAssemblies() ) do
local img = mono_getImageFromAssembly(v)
if mono_image_get_name(img) == imgname then
result = img
break
end
end
return result
end
|
Results for 1000 calls:
CE7.6:
Test took 7.075000 seconds to run, ca. 0.007075 seconds per function run
Test took 7.076000 seconds to run, ca. 0.007076 seconds per function run
Test took 7.180000 seconds to run, ca. 0.007180 seconds per function run
Test took 7.257000 seconds to run, ca. 0.007257 seconds per function run
CE7.5:
Test took 3.333000 seconds to run, ca. 0.003333 seconds per function run
Test took 3.244000 seconds to run, ca. 0.003244 seconds per function run
Test took 3.338000 seconds to run, ca. 0.003338 seconds per function run
Test took 3.331000 seconds to run, ca. 0.003331 seconds per function run
|
|
Back to top |
|
 |
Dark Byte Site Admin
Reputation: 470
Joined: 09 May 2003 Posts: 25769 Location: The netherlands
|
Posted: Mon Mar 03, 2025 4:07 pm Post subject: |
|
|
It seems I released CE's lua without optimization enabled
try this dll: https://cheatengine.org/download/lua53-ce76.zip
let me know the statistics
_________________
Do not ask me about online cheats. I don't know any and wont help finding them.
Like my help? Join me on Patreon so i can keep helping |
|
Back to top |
|
 |
HenryEx Expert Cheater
Reputation: 2
Joined: 18 Dec 2011 Posts: 100
|
Posted: Tue Mar 04, 2025 10:19 am Post subject: |
|
|
That DLL seems to work a lot better. On the getAssemblyImage function test from above, it performs even better than CE7.5.
Code: | CE 7.5
==========
Test took 3.3100 seconds to run, ca. 0.003310 seconds per function run
Test took 3.2330 seconds to run, ca. 0.003233 seconds per function run
Test took 3.3450 seconds to run, ca. 0.003345 seconds per function run
Test took 3.3290 seconds to run, ca. 0.003329 seconds per function run
CE 7.6 old DLL
==========
Test took 7.1750 seconds to run, ca. 0.007175 seconds per function run
Test took 7.1050 seconds to run, ca. 0.007105 seconds per function run
Test took 7.3160 seconds to run, ca. 0.007316 seconds per function run
Test took 7.1030 seconds to run, ca. 0.007103 seconds per function run
CE 7.6 new DLL
==========
Test took 2.6020 seconds to run, ca. 0.002602 seconds per function run
Test took 2.6190 seconds to run, ca. 0.002619 seconds per function run
Test took 2.6380 seconds to run, ca. 0.002638 seconds per function run
Test took 2.6350 seconds to run, ca. 0.002635 seconds per function run |
It's not a representative showing though, as the effect isn't quite as great in practical application, but it still performs way better during my table setup. Though it still doesn't beat out CE7.5 on that one.
Code: | CE 7.5
======
==Table Setup==
Launching Mono...
Launched in 0.8670 seconds.
Fetching pointers from game methods...
Got pointers in 0.6820 seconds.
Registering 60 method symbols...
Got Address for :Character:DamageCharacter() in 0.0010 seconds.
(...)
Got Address for :DiceUI+<RollDice>d__31:MoveNext() in 0.0920 seconds.
Got Address for :CharacterCustomizeWindow+<>c:<InitWindow>b__45_0() in 0.0770 seconds.
(...)
Registered symbols in 0.2970 seconds.
AOB searching for 4 more symbols...
Found address for aobSkillListAddResize in 0.0050 seconds.
Found address for aobSkillListRemove in 0.0040 seconds.
Found address for aobTalentListAddResize in 0.0040 seconds.
Found address for aobTalentListRemove in 0.0050 seconds.
AOB search concluded in 0.0270 seconds.
Fetching class fields, please wait...
Got fields in 0.1210 seconds.
Done in 2.0630 seconds.
CE 7.6 old
==========
==Table Setup==
Launching Mono...
Launched in 0.8830 seconds.
Fetching pointers from game methods...
Got pointers in 0.7750 seconds.
Registering 60 method symbols...
Got Address for :Character:DamageCharacter() in 0.0010 seconds.
(...)
Got Address for :DiceUI+<RollDice>d__31:MoveNext() in 0.4070 seconds.
Got Address for :CharacterCustomizeWindow+<>c:<InitWindow>b__45_0() in 0.3820 seconds.
(...)
Registered symbols in 0.9350 seconds.
AOB searching for 4 more symbols...
Found address for aobSkillListAddResize in 0.0090 seconds.
Found address for aobSkillListRemove in 0.0080 seconds.
Found address for aobTalentListAddResize in 0.0100 seconds.
Found address for aobTalentListRemove in 0.0090 seconds.
AOB search concluded in 0.0450 seconds.
Fetching class fields, please wait...
Got fields in 0.7310 seconds.
Done in 3.4420 seconds.
CE 7.6 new
==========
==Table Setup==
Launching Mono...
Launched in 0.8900 seconds.
Fetching pointers from game methods...
Got pointers in 0.7320 seconds.
Registering 60 method symbols...
Got Address for :Character:DamageCharacter() in 0.0010 seconds.
(...)
Got Address for :DiceUI+<RollDice>d__31:MoveNext() in 0.1890 seconds.
Got Address for :CharacterCustomizeWindow+<>c:<InitWindow>b__45_0() in 0.1770 seconds.
(...)
Registered symbols in 0.5100 seconds.
AOB searching for 4 more symbols...
Found address for aobSkillListAddResize in 0.0090 seconds.
Found address for aobSkillListRemove in 0.0100 seconds.
Found address for aobTalentListAddResize in 0.0090 seconds.
Found address for aobTalentListRemove in 0.0090 seconds.
AOB search concluded in 0.0450 seconds.
Fetching class fields, please wait...
Got fields in 0.3820 seconds.
Done in 2.6270 seconds. |
New DLL ist just a ~27% increase overall from CE7.5, compared to the ~67% increase in time overall with the old DLL.
For reference, the 4 AOB searches are basically just AA executing a single line of 'aobSearchRegion' + registerSymbol, no mono involved. These are unchanged between the two DLL versions, but have slowed down overall from CE7.5.
I'm assuming that's "stability tax".
edit: I'm noticing i don't see the increase in mono activation time in these tests. Might be related to the overall instability of mono in CE 7.6.
If something goes wrong and the mono pipe gets disconnected, i usually have to restart CE now because relaunching mono hangs. Manually disconnecting and reconnecting mono features works, at best, once with some considerable lag, afterwards CE will also just hang indefinitely.
This doesn't seem to be a Lua problem though, since the new DLLs have not made a change in that.
late edit: I get a message about double posting, so i'm appending this here.
Here's a test of my chunkiest function, which gathers data from, and builds a table out of, almost a thousand different skills from the game.
This is a single run each.
Code: | CE 7.5
======
Test took 5.699 seconds to run
Test took 5.678 seconds to run
Test took 5.668 seconds to run
Test took 5.581 seconds to run
CE 7.6 old
==========
Test took 26.509 seconds to run
Test took 26.350 seconds to run
Test took 26.076 seconds to run
Test took 26.080 seconds to run
CE 7.6 new
==========
Test took 10.236 seconds to run
Test took 9.976 seconds to run
Test took 9.926 seconds to run
Test took 10.489 seconds to run
|
Almost half a minute made me question my sanity when i first made the upgrade to 7.6, haha.
|
|
Back to top |
|
 |
|
|
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
|
|