(Sorry for my bad english) Hello everyone, so im having a problem here trying to make monitors work so i can go to another act of the zone by breaking them. I enable activated the act 4 of every zone so i can use them as a hub for their respective zones. The problem is that im always going to scrap brain zone act 1 instead of the act 1 of (for example) green hill zone because i was in the GHZ hub stage. I will leave here the code of one of the monitors here: Obj2E_ChkACT1: cmpi.b #4,d0 ; does monitor contain a shield? bne.w Obj2E_CHKACT2 cmpi.w #$003,($FFFFFE10).w ; check if level is GHZ4 bne.s CHKMZ move.w #1,($FFFFFE02).w ; restart level move.w #$000,($FFFFFE10).w ; set level number to GHZ1 CHKMZ: cmpi.b #203,($FFFFFE10).w ; is level MZ4 ? bne.s CHKSYZ move.w #1,($FFFFFE02).w ; restart level move.w #$200,($FFFFFE10).w ; set level number to MZ1 CHKSYZ: cmpi.w #403,($FFFFFE10).w ; is level SYZ4 ? bne.s CHKLZ move.w #1,($FFFFFE02).w ; restart level move.w #$400,($FFFFFE10).w ; set level number to SYZ1 CHKLZ: cmpi.b #103,($FFFFFE10).w ; is level LZ4 ? bne.s CHKSLZ move.w #1,($FFFFFE02).w ; restart level move.w #$100,($FFFFFE10).w ; set level number to LZ1 CHKSLZ: cmpi.w #303,($FFFFFE10).w ; is level SLZ4 ? bne.s CHKSBZ move.w #1,($FFFFFE02).w ; restart level move.w #$300,($FFFFFE10).w ; set level number to SLZ1 CHKSBZ: cmpi.w #503,($FFFFFE10).w ; is level SBZ4 ? move.w #1,($FFFFFE02).w ; restart level move.w #$500,($FFFFFE10).w ; set level number to SBZ1
Despite the labels, the 68k is really just reading instruction by instruction sequentially until something alters the PC value. It's like a train on rails. In this case, after each of your checks, the value is changed, and then the 68k just trots forward and reads all the code in front of it, which is all the rest of the value changes ahead of it. The train is going down the rails and missing the junctions. What you need to do instead is that after these value changes are done in each check block, you need to branch to the point after your very last check. That way, the 68k knows to not run the code past that and instead process what you've changed like I assume you do after the final SBZ block.
cmpi.b #203,($FFFFFE10).w ; is level MZ4 ? cmpi.w #403,($FFFFFE10).w cmpi.b #103,($FFFFFE10).w ; is level LZ4 ? cmpi.w #303,($FFFFFE10).w ; is level SLZ4 ? cmpi.w #503,($FFFFFE10).w ; is level SBZ4 ? These instructions have the same problem in common. First of all, the size of the instructions "cmpi.b" where the .b specifies a "byte". The zone and act together however are stored as a word (two bytes), so you should consider using "cmpi.w" .w for word. The second issue is how the value is represented, we'll take "#303" as an example. By default, the assembler assumes these values are "decimal" (e.g. 0 to 9) and it will convert the value to "hexadecimal" (0 to F) when assembling. 303 is assembled as "012F". What you really want, is 303 represented as a "hexadecimal" value already. In which case, placing a $ (dollar symbol) after the hash (poung) tag as "#$303" will cause the assembler to assemble 303 as... ...303. It will not attempt to convert to hexadecimal this way. This applies to all of those values. This is one of many reasons why I encourage people to think in hexadecimal terms throughout, combination of the two leads to confusion and stuns performance. Might I also suggest reading this guide, as it may help you to understand "why" it works.