Dolphin, the GameCube and Wii emulator - Forums

Full Version: Setting a breakpoint BEFORE launching game?
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
Pages: 1 2 3
The byte location of what you are comparing/updating. ex: CDEF = 8000000C 8000000D 8000000E 8000000F. Since you were comparing bytes at EF01 alignment and thought it was misaligned, you would move the comparison left one byte and check the byte at CD and the first byte of your original comparison EF -> CDEF.

I looked at the codehandler for Nintendont and Dolphin and they appear to treat alignment the same way., but alignment seems like it'd be the only difference between your conditional and others' codes that you tried. Unless there's an issue with endifs.
(03-12-2022, 06:04 PM)Modception Wrote: [ -> ]The byte location of what you are comparing/updating. ex: CDEF =  8000000C 8000000D 8000000E 8000000F.  Since you were comparing bytes at EF01 alignment and thought it was misaligned, you would move the comparison left one byte and check the byte at CD and the first byte of your original comparison EF -> CDEF.

Ah yes I tried that -- shifting the address and the comparison byte pattern +/- 1,2,3,4 bytes. 

This is what I'm observing with Wave Race Blue Storm:

Code:
OP code               Platform    Observation

04 (32-bit write)     Dolphin     Alignment required
04 (32-bit write)     Wii         Alignment required

02 (16-bit write)     Dolphin     Alignment not required
02 (16-bit write)     Wii         Alignment not required

20 (32-bit ifequal)   Dolphin     Alignment required
20 (32-bit ifequal)   Wii         Nonfunctional -- always evaluates false

28 (16-bit ifequal)   Dolphin     Alignment required
28 (16-bit ifequal)   Wii         Nonfunctional -- always evaluates false

However the very last one does work if I set the MMMM value to (FFFF - XXXX) as per this guide, but I think that causes it to evaluate true even when the memory contents are something else.


(03-12-2022, 06:04 PM)Modception Wrote: [ -> ]Unless there's an issue with endifs.

I've tried the E2000001 00000000 and E0000000 00000000 codes without success.
Interesting discussion going on here, maybe I can answer some of the questions:

As you've already found out, it is possible to call game functions from a Gecko code, but it can be tricky. You have no idea where in RAM your code is, so you need to load the function address into CTR (or LR) and then use bctrl or blrl to execute the function. Of course, while doing that, you need to make sure you save and restore any registers that shouldn't be overwritten. If necessary, that means writing your own ASM to save/restore registers on the stack (which requires your own ASM code, so, C0 or C2 instead of the "easier" code types. This is explained in the Link ( https://mariokartwii.com/showthread.php?tid=1052 ) that was posted a while ago.

As for the if-else-endif construct behaving weird / unexpected on the Wii, Wiimm and me have encountered that years ago, too, that's why we first switched to only using C0 and C2 code and writing all the custom behaviour ourselves in Assembly.

A C0 code will be executed every time the Gecko handler runs - so, by default, every time a frame has been rendered. A C2 code will be *parsed* every time the Gecko handler runs, and will be executed whenever the game execution reaches the address it patches.

Your Gecko cheat code didn't run immediately at game boot, because the default Gecko hook is the VBI hook - this means, the gecko handler and all your gecko codes are executed each time a frame has been rendered. That's too late to modify video initialization apparently, so you had to perform your workaround of branching back to the game's entrypoint. Which, to be honest, I was surprised that that even worked without issues.

If you are having issues with the if/else/endif construct in the Gecko code, I would suggest implementing it yourself. Meaning, do not use the Gecko if/endif statements at all, just write one huge C0 gecko code and do all the comparisons and checks yourself in native ASM.
Thanks Leseratte.

Yes it is weird that branching to entrypoint works to reset the game.  I can only speculate that maybe the entrypoint does some routine where it initialises all the registers to some fresh values or something.   Or when the game starts, it makes no assumptions about the state of the registers?

Thought I recognised your name -- saw you in ULGX source code Cool
That is correct, the game cannot make any assumptions about register state (that's why very shortly into the entrypoint it will execute a function that sets all the registers to their proper values), but the game can assume that its data sections are unmodified, which wouldn't be the case anymore if you just branch to the entrypoint again. But I guess doing that after the first rendered frame is early enough that that doesn't cause issues in this game.
(03-11-2022, 10:46 AM)pneumatic Wrote: [ -> ]The A8 code seems to works fine on Dolphin and Wii, so I'll use that instead

It seems the A8 code fails after about 15 minutes of game play!   I had never tested it for longer than 15 minutes, so I never detected the issue.

It appears something is causing the A8 counter to reset back to 0 after 15 minutes, so the A8 code evaluates true and executes my ASM which resets to entry point in the middle of the game, resulting in a crash.

The workaround I'm using is to store my own boolean "MyVar" to control the "reset once" behaviour, as mentioned here.   So far it survives for longer than 15 minutes, but I'd still like to test for at least 2 hours of gameplay.

I've updated the wiki here, and also combined it with the 16:9 code as it doesn't seem to work if they are applied as two separate codes.
Good to know!
Pages: 1 2 3