don't click here

Basic Questions & Answers thread

Discussion in 'Engineering & Reverse Engineering' started by Tweaker, May 29, 2008.

  1. Change the bsr.w to a jsr and it should work fine - the error message is saying that the offset to the target label (-32798) is too big to fit in a bsr.w.
     
  2. GT Koopa

    GT Koopa

    Member
    2,023
    20
    18
    Elgin, IL
    Flicky Turncoat DX, T.L.W.S. Vs M.G.W.
    I thought it was one of those things that jsrs and jmps couldn't solve, and I should just leave it alone.

    It worked. You are a life saver.
     
  3. Sik

    Sik

    Sik is pronounced as "seek", not as "sick". Tech Member
    6,718
    10
    0
    being an asshole =P
    Rule of thumb:

    bra.s --> bra.w --> jmp
    bsr.s --> bsr.w --> jsr

    It doesn't work for conditional branches though, you'd need to mix conditional branching and jumps in such a case. Luckily, that's an oddity and not the rule.
     
  4. E-122-Psi

    E-122-Psi

    Member
    2,502
    681
    93
    Got it, thanx. Hopefully that will give me enough frames to complete the movelist.

    Having a problem with getting combo button moves working in Sonic 2 asm now, here's my attempted code:

    Code (Text):
    1. ; ---------------------------------------------------------------------------
    2. ; Subroutine to do Jump Dash (code by Vladikcomper)
    3. ; ---------------------------------------------------------------------------
    4.  
    5. ; ||||||||||||||| S U B R O U T I N E |||||||||||||||||||||||||||||||||||||||
    6.  
    7. Sonic_SpinHammer:
    8.  
    9.  
    10.     btst    #7,status(a0)          ; was Jump Dash flag set?
    11.     beq.b   Sonic_SpinHammer_Rts     ; if yes, branch
    12.     move.b    (Ctrl_1_Press_Logical).w,d0
    13.     btst    #1,(Ctrl_1_Held_Logical).w; is down being pressed?        
    14.     beq.b    Sonic_SpinHammer_Rts; if no, return
    15.     and.b    #$40,d0        ; get only button A    
    16.     cmpi.b    #$40,d0        ;is A being pressed?
    17.     beq.w    Sonic_SpinHammer_Rts; if not, return
    18.     move.w    #$BC,d0                   ; play sound
    19.     jsr    (PlaySound).l
    20.     bset    #7,status(a0)          ; set Jump Dash flag
    21.     move.b    #$25,anim(a0)    ; use spinning animation
    22.     move.w    #$650,y_vel(a0)        ; set Jump Dash speed
    23.     move.w    #0,x_vel(a0)           ; clear Y-velocity
    24.     btst    #0,status(a0)          ; is sonic facing left?
    25.     beq.s    Sonic_SpinHammer_Rts     ; if no, branch
    26.     neg.w     x_vel(a0)              ; negate X-velocity
    27.  
    28. Sonic_SpinHammer_Rts:
    29.     rts
    30.  
    31. ; End of function Sonic_SpinHammer
    It's based on the Jump Dash code from the SSRG (I've added the necessary coding outside the main branch as well), however I can't get it to work with the two button activation (hold down and A).

    Oh and another more minor question, what technique do you guys use to edit the text in Sonic 2 for characters (eg. to change who 'Got Through Act 1' or who you select on the options screen)? ASM, Text editor or something?
     
  5. MainMemory

    MainMemory

    Kate the Wolf Tech Member
    4,795
    382
    63
    SonLVL
    For the options screen, if you look at byte_97CA you'll see:
    Code (ASM):
    1. byte_97CA:  dc.b $10,"* PLAYER SELECT *"
    2. byte_97DC:  dc.b  $E,"SONIC AND MILES"
    3. byte_97EC:  dc.b  $E,"SONIC AND TAILS"
    4. byte_97FC:  dc.b  $E,"  SONIC ALONE  "
    5. byte_980C:  dc.b  $E,"  MILES ALONE  "
    6. byte_981C:  dc.b  $E,"  TAILS ALONE  "
    As for the end-of-act results... they're sprite mappings, but editing them in SonMapEd removes part of them, crashing the game.
     
  6. E-122-Psi

    E-122-Psi

    Member
    2,502
    681
    93
    Dang, oh well the options are now one more obstacle solved. Thanx MainMemory.
     
  7. Hanoch

    Hanoch

    Also known as TheKnock, Birashot Member
    491
    0
    0
    Israel
    everything
    Code (ASM):
    1. ; ---------------------------------------------------------------------------
    2. ; Subroutine to do Jump Dash (code by Vladikcomper)
    3. ; ---------------------------------------------------------------------------
    4.  
    5. ; ||||||||||||||| S U B R O U T I N E |||||||||||||||||||||||||||||||||||||||
    6.  
    7. Sonic_SpinHammer:
    8.  
    9.  
    10.     btst    #7,status(a0)          ; was Jump Dash flag set?
    11.     beq.b   Sonic_SpinHammer_Rts     ; if yes, branch
    12.     move.b    (Ctrl_1_Press_Logical).w,d0
    13.     btst    #1,d0; is down being pressed?        
    14.     beq.b    Sonic_SpinHammer_Rts; if no, return
    15.     and.b    #$40,d0        ; get only button A    
    16.     cmpi.b    #$40,d0        ;is A being pressed?
    17.     bne.w    Sonic_SpinHammer_Rts; if not, return
    18.     move.w    #$BC,d0                   ; play sound
    19.     jsr    (PlaySound).l
    20.     bset    #7,status(a0)          ; set Jump Dash flag
    21.     move.b    #$25,anim(a0)    ; use spinning animation
    22.     move.w    #$650,y_vel(a0)        ; set Jump Dash speed
    23.     move.w    #0,x_vel(a0)           ; clear X-velocity
    24.  
    25.     ;btst    #0,status(a0)          ; is sonic facing left?
    26.     ;beq.s    Sonic_SpinHammer_Rts     ; if no, branch ; those 3 lines aren't necessary because you are not even applying X velocity.
    27.     ;neg.w     x_vel(a0)              ; negate X-velocity
    28.  
    29. Sonic_SpinHammer_Rts:
    30.     rts
    31.  
    32. ; End of function Sonic_SpinHammer
    Fix'd it for you.
     
  8. Selbi

    Selbi

    The Euphonic Mess Member
    1,516
    102
    43
    Northern Germany
    Sonic ERaZor
    Code (ASM):
    1.         cmpi.b  #$FF,($FFFFCxxx).w
    2.         bne.s   Op_Next
    This is a check I'm going to use a lot. The only difference between each version, is the xxx, which is always a multiple of $48 + $A00 (basically $48 * X + $A00), while X is between 0 and 5. Is there a way to put that line into a bsr and make it look like this:
    Code (ASM):
    1.         cmpi.b  #$FF,($FFFFC($A00+($48*d0))).w
    2.         bne.s   Op_Next
    I know this does not work, but is the a way to do it? Or am I forced to calculate each line myself?
     
  9. nineko

    nineko

    I am the Holy Cat Tech Member
    6,364
    522
    93
    italy
    I believe you can do something like this:
    Code (Text):
    1. moveq #$0,d0
    2. *give d0 its value here*
    3. mulu.w #$48,d0
    4. addi.l $FFFFCA00,d0
    5. movea.l d0, a6
    6. cmpi.b #$FF,(a6)
    Not tested, because I'm not at home.
     
  10. Selbi

    Selbi

    The Euphonic Mess Member
    1,516
    102
    43
    Northern Germany
    Sonic ERaZor
    Either I'm too stupid, or that doesn't work. Here's the full code for me:
    Code (ASM):
    1.         moveq   #0,d2           ; make sure d2 is empty
    2.         move.w  ($FFFFFF9A).w,d2    ; get the number $48 needs to be multiplicated
    3.         divu.w  #2,d2           ; because this number works like 0, 2, 4, 6 etc, it needs to be halved
    4.         mulu.w  #$48,d2         ; multiplicate that number with $48
    5.         add.l   $FFFFCA00,d2        ; add another $FFFFCA00 to it
    6.         movea.l d2,a6           ; move the result to a6
    7.         cmp.l   #$FF,a6         ; is the last byte of the calculated location $FF?
    8.         beq.s   Op_CheckOk      ; if yes, branch
    9.         move.w  #1,d2           ; otherwise, set d2 to 1, for something which will be used later
    Almost forgot, my problem is that d2 always gets set to 1 at the end. My guess was the longword, but since I can't use bytes on address registers, I'm screwed.
     
  11. Hanoch

    Hanoch

    Also known as TheKnock, Birashot Member
    491
    0
    0
    Israel
    everything
    Try using lsr.w #1,d2 it also divides by 2 but for some reason programmers like to use this better.
     
  12. Try
    Code (ASM):
    1.         move.w  ($FFFFFF9A).w,d2    ; get the number $48 needs to be multiplicated
    2.         mulu.w  #$24,d2         ; d2 / 2 * $48 = d2 * $24
    3.         add.w   $CA00,d2        ; add another $CA00 to it
    4.         movea.w d2,a6           ; sign extension takes place automatically
    5.         cmp.b   #$FF,(a6)           ; is the last byte of the calculated location $FF?
    6.         beq.s   Op_CheckOk      ; if yes, branch
    7.         move.w  #1,d2           ; otherwise, set d2 to 1, for something which will be used later
     
  13. DigitalDuck

    DigitalDuck

    Arriving four years late. Member
    5,416
    492
    63
    Lincs, UK
    TurBoa, S1RL
    Because it's a lot more efficient.
     
  14. Selbi

    Selbi

    The Euphonic Mess Member
    1,516
    102
    43
    Northern Germany
    Sonic ERaZor
    The code looks good, but still no success. Probably a problem on my side. Just to make sure I'm right: Let's say there's #2 in $FFFFFF9A, wouldn't the output (a6) be $FFFFCA48?
     
  15. nineko

    nineko

    I am the Holy Cat Tech Member
    6,364
    522
    93
    italy
    Your main problem is that you used cmp.l #$FF,a6 instead of cmpi.b #$FF,(a6)

    edit: I didn't see you posted at the same time. My bad. You can disregard the content of this post. Also because as I said I'm not at home so I wrote it without any code references in my hand :v:
     
  16. Yup, the cmp.b #$FF,(a6) will be comparing it with the byte at $FFFFCA48 in that case.

    EDIT: I forgot an immediate value sign. It's add.w #$CA00, not add.w $CA00.

    On a similar note, I believe this is the fastest way to multiply by $24 (assuming d2 already contains the number to be multiplied and d3 is a spare register):
    Code (ASM):
    1.     add.w   d2,d2   ; x = original value of d2
    2.     add.w   d2,d2   ; d2 = 4x
    3.     move.w  d2,d3
    4.     lsl.w   #3,d3   ; d3 = $20x
    5.     add.w   d3,d2   ; $20x + 4x = $24x
    Really though, it's much simpler to just use a multiply instruction unless it's a speed-critical section of the code.
     
  17. Selbi

    Selbi

    The Euphonic Mess Member
    1,516
    102
    43
    Northern Germany
    Sonic ERaZor
    While it doesn't work where it should, it works at another point, so yeah, probably my mistake. Thanks so far. =)
     
  18. nineko

    nineko

    I am the Holy Cat Tech Member
    6,364
    522
    93
    italy
    Maybe a6 is used by something else in a certain section of your code. I used it as an example, but you should look at the code surrounding your snippet and if necessary you should attempt to use another address register.
     
  19. Did you notice my edit about the missing immediate value sign? (add.w #$CA00 instead of add.w $CA00)
     
  20. Selbi

    Selbi

    The Euphonic Mess Member
    1,516
    102
    43
    Northern Germany
    Sonic ERaZor
    That was not the problem, but I forgot some things. The location had a totally different format (yes, I managed to put together two totally different code without noticing). Just changed it to the correct way and it worked. Thanks again. =)