Basic Questions and Answers Thread

Discussion in 'Discussion & Q&A' started by Malevolence, Jul 7, 2009.

  1. MarkeyJester

    MarkeyJester ♡ ! Member

    Joined:
    Jun 27, 2009
    Messages:
    2,867
    Last edited by a moderator: Jan 25, 2015
  2. ProjectFM

    ProjectFM Optimistic and self-dependent Member

    Joined:
    Oct 4, 2014
    Messages:
    912
    Location:
    Orono, Maine
    I used the one that came with your original Sonic 128 disassembly.
     
  3. ProjectFM

    ProjectFM Optimistic and self-dependent Member

    Joined:
    Oct 4, 2014
    Messages:
    912
    Location:
    Orono, Maine
    Sorry to double post. The topic you showed me didn't help at all. I'm using a copy of my disassembly to add the sound driver and the original builds fine. Also, it isn't not working because the address being too long because it's even shorter than the original.
     
    Last edited by a moderator: Jan 25, 2015
  4. MarkeyJester

    MarkeyJester ♡ ! Member

    Joined:
    Jun 27, 2009
    Messages:
    2,867
    You haven't confirmed whether the above was the problem or not.

    EDIT: Your second post didn't come through until I posted my response...

    So it's not a problem with the assembler. Having never touched "Sonic 3's" driver from that tutorial, I am unaware of any macros and/or addressing which may have an issue with your assembler. Unfortunately, I don't have much time to go an research through. Perhaps someone else here can get to it and provide an answer?
     
    Last edited by a moderator: Jan 25, 2015
  5. Kaz

    Kaz Well-Known Member Member

    Joined:
    Nov 2, 2013
    Messages:
    66
    Dear lord, you might have gotten that error because the Sonic Retro Wiki holding that page is in an utter redesign, and most functions from the old wiki don't work properly such as <asm> tags. You might have copied info that was incorrectly formatted. Please try it again when the wiki is fully redesigned.
     
  6. ProjectFM

    ProjectFM Optimistic and self-dependent Member

    Joined:
    Oct 4, 2014
    Messages:
    912
    Location:
    Orono, Maine
    I went to the source section of the tutorial and found that all the text in that section is spaced correctly so I'm going to start over using that version of the tutorial.
     
  7. TheStoneBanana

    TheStoneBanana banana Member

    Joined:
    Nov 27, 2013
    Messages:
    602
    Location:
    The Milky Way Galaxy
    Alright, so I've run into a bit of a dilemma here. For... something... I'm porting to my project, it requires the function bytesToLcnt. This is in both Sonic 2 and Sonic 3K, and is the same in both. The problem is, if I plop it into Sonic 1 in the correct place, my assembler thinks it's an op-code or something and refuses to build, claiming that it's an unknown code. No, before you ask, it's not indented.

    Doing a bit of research, it seems that the AS assembler can recognize and build the function, but the assembler I use (ASM68K) cannot.

    tl;dr My main question here is would it be worth it to port my project to AS, or is there some sort of workaround I can use to get this running?
     
  8. Devon

    Devon I'm a loser, baby, so why don't you kill me? Member

    Joined:
    Aug 26, 2013
    Messages:
    1,376
    Location:
    your mom
    I say just take the code from thay function and replace n or with thee value you want.
     
  9. Psi

    Psi Well-Known Member Member

    Joined:
    Dec 20, 2014
    Messages:
    102
    Is anyone experienced with porting objects to S3+K's asm? I've heard there are significant differences between it and Sonic 2 (besides different addresses) and when I try to utilise this code, the object just causes the game to freeze:


    Obj_Laser:
    moveq #0,d0
    move.b 5(a0),d0
    move.w Obj_Blob_Index(pc,d0.w),d0
    jmp Obj_Blob_Index(pc,d0.w)
     
    Obj_Blob_Index:
    dc.w Obj_Blob_Init-Obj_Blob_Index
    dc.w Obj_Blob_Move-Obj_Blob_Index
    dc.w Obj_Blob_Destroy-Obj_Blob_Index
     
    Obj_Blob_Init:
            move.l  #SME_q1Oa7,$C(a0) ; ($C)
            move.w  #$F400/$20,$A(a0)
            move.w  #$2,5(a0)
            move.b  #$8,width_pixels(a0)
            move.b  #$4,render_flags(a0)
            move.b  #$4,y_radius(a0) ; $A
    move.l Obj_Laser_Display,(a0)
     
    Obj_Laser_Display:
    lea (Player_1).w,a1
    move.b #$18,$30(a0) ; distance laser will travel
    cmpi.b #$29,$20(a1)
    beq.s Obj_Laser_DownwardNICOLE ; if not, branch
    move.w #$660,$18(a0) ; speed of laser
    jmp Obj_Laser_ContNICOLE
    Obj_Laser_DownwardNICOLE:
    move.w #$660,$1A(a0) ; speed of laser
    Obj_Laser_ContNICOLE:
    add.w #$10,y_pos(a0)
    btst #0,(Player_1).w
    beq.s Obj_Laser_Cont
    neg.w $10(a0)
    sub.w #$20,y_pos(a0)
    Obj_Laser_Cont:
    lea (ArtSNK_Laser0).l,a1
    move.w #$F400,d2
    jsr (SNKDec).l
    addq.b #2,5(a0) ; 
     
    Obj_Blob_Move:
    cmp.b #$0,$30(a0)
    beq.w Obj_Blob_Destroy
    sub.b #$1,$30(a0)
    jsr (loc_358A8).l
    move.b $40,$20(a0) ; lol
     
    clr.w d0
    move.b mapping_frame(a0),d0
    asl.w #$1,d0 ; *2 for correct offset
    lea (LaserArtPointers).l,a1
    adda.w (a1,d0.w),a1
    move.w #$F400,d2
    jsr (SNKDec).l
     
    lea (Ani_Laser).l,a1
    jsr (Animate_Sprite).l
    jsr (sub_FE6E).l ;Touch_KillEnemy, Touch_Monitor 
    jmp (Draw_Sprite).l
    rts
    Obj_Blob_Destroy:
    clr.b ($FFFFFFA6).w ; clear NICOLE flag 
    jmp Delete_Current_Sprite
    rts
    Ani_Laser:
    dc.w laser0-Ani_Laser
    laser0: dc.b 3,0,1,1,2,2,3,3,$FD,0
    even
     
    SME_q1Oa7:
    dc.w SME_q1Oa7_8-SME_q1Oa7, SME_q1Oa7_10-SME_q1Oa7
    dc.w SME_q1Oa7_18-SME_q1Oa7, SME_q1Oa7_20-SME_q1Oa7
    SME_q1Oa7_8: dc.b 0, 1
    dc.b $F8, 5, 0, 0, $FF, $F8
    SME_q1Oa7_10: dc.b 0, 1
    dc.b $F8, 5, 0, 0, $FF, $F8
    SME_q1Oa7_18: dc.b 0, 1
    dc.b $F8, 5, 0, 0, $FF, $F8
    SME_q1Oa7_20: dc.b 0, 1
    dc.b $F8, 5, 0, 0, $FF, $F8
    even

    The art pointers are at the end of the ASM and SNKDec is a routine placed just before NemDec.
     
    Last edited by a moderator: Jan 26, 2015
  10. vladikcomper

    vladikcomper Well-Known Member Member

    Joined:
    Dec 2, 2009
    Messages:
    415
    1) In Obj_Blob_Init, you have:


    move.w #$2,5(a0)

    This will cause Address Error on real hardware, also in several accurate emulators, like Regen, Gens/GS and Exodus.

    On the M68K, you are not allowed to write to odd addresses (like ObjectAddress+$0005, since ObjectAddress is always even, so the addition will be odd).

    2) At the beginning of object code, you're trying to use byte 5 as a routine counter/switcher, like so:


    Obj_Laser:
    moveq #0,d0
    move.b 5(a0),d0 ;~~
    move.w Obj_Blob_Index(pc,d0.w),d0
    jmp Obj_Blob_Index(pc,d0.w)

    Sonic 1 (and Sonic 2 also) this byte is used to store the second byte of the object's mappings pointer, which is a long word which starts at byte 4 and ends at byte 7, taking 4 bytes total.

    You should consider using byte $24 instead, this is what most of objects use as a routine counter. If you do so, don't forget to fix all the "addq.b #2,5(a0)" instances and everything that touches 5(a0).

    3) This line:


    move.w #$660,$1A(a0)

    Sonic 1 and Sonic 2 use byte $1A to store mappings frame and byte $1B to store animation frame, if I'm correct. However, you're using these byte to store laser's speed, which will cause many conficts later on.

    There are may be more conflicting addresses there. Sorry, I don't have time to look for them all.

    4) This line:


    move.l Obj_Laser_Display,(a0)

    Did you mean?


    move.l #Obj_Laser_Display,(a0)

    In Sonic 3/K, the first four bytes of object's SST (byte 0 -- byte 3) are used to store object's code offset. This allows programmer to easily switch which code is being executed for this object on the fly.

    Sonic 1 and Sonic 2 don't have this system. As you might know, these games use one static offset table (ObjectIndex) that stores which object ID calls which code and these offsets cannot be changed, which means, ID $01 is tie to offset "Obj01", ID $20 is tied to offset "Obj20" etc.

    Importing the whole system is too much of a hardwork, however, there are certain workarounds you may come up with. I would attempt this:


    objloaded = $1F
    obj = $3C

    ; ------------------------------------------------

    Obj_Laser:
    tst.b objloaded(a0) ; was code offset been initalized?
    bne.s @Exec ; branch if yes
    move.l #Obj_Laser_Main,obj(a0)
    st.b objloaded(a0)

    @Exec:
    movea.l obj(a0),a1
    jmp (a1)

    ; ------------------------------------------------
    Obj_Laser_Main:
    moveq #0,d0
    move.b $24(a0),d0 ;~~
    move.w Obj_Blob_Index(pc,d0.w),d0
    jmp Obj_Blob_Index(pc,d0.w)

    <...>

    This is a litle dirty, but should work quite well, as long as addresses I've listed in the first two lines are not used for your object already.

    You'll then have to replace all instances of "move.l #<Offset>,(a0)" with "move. #<Offset>,obj(a0)".

    * * *

    Those were the main issues I could spot. Sorry. didn't have time to look further.
     
  11. Psi

    Psi Well-Known Member Member

    Joined:
    Dec 20, 2014
    Messages:
    102
    I put 5 since that seems to be the routine byte in S3+K instead of $24. I decided to just screw it and put routine. It's the one that works right out of all three.

    Ah well that's made some key progress. The object loads, however it seems to loop around the game and using over and over slows it down (I'm guessing I've screwed up the routine that deletes it after a duration). There's also some problems getting it to collide or work in the right direction, but those might be connected to other branches in the ASM to the object (little is labelled as clearly as in the other two games).

    Just to note $1F and $3C seem to be used in the coding already (x_radius and ros_addr respectively).

    EDIT: Okay I've managed to fix the deletion/slow down and direction errors, but collision still seems to be an issue, as in it seems completely random whether it hits anything or not.

    I realised I forgot to translate a priority flag properly, but putting one with the same byte as the other games in seems to crash the game. Badly.
     
    Last edited by a moderator: Jan 29, 2015
  12. ProjectFM

    ProjectFM Optimistic and self-dependent Member

    Joined:
    Oct 4, 2014
    Messages:
    912
    Location:
    Orono, Maine
    I tried porting the CPZ speed booster to Sonic 1 Hivebrain from the Sonic 2 beta and, though it shows up, doesn't do anything.

    Here is the code:


    ;===============================================================================
    ; Object 04 - Speed Booster
    ;===============================================================================
    Obj04: ; Offset_0x016468:
    moveq #0,d0
    move.b $24(a0),d0
    move.w Offset_0x016476(pc,d0),d1
    jmp Offset_0x016476(pc,d1)

    Offset_0x016476:
    dc.w Offset_0x01647E-Offset_0x016476
    dc.w Offset_0x0164B4-Offset_0x016476

    Offset_0x01647A:
    dc.w $1000,$0a00

    Offset_0x01647E:
    addq.b #2,$24(a0)
    move.l #Map_Obj04,$4(a0) ; Offset_0x01658A
    move.w #$E39C,$2(a0)
    ; bsr J_ModifySpriteAttr_2P_03 ; Offset_0x0165AA ; No S1 equivalent
    ori.b #4,$1(a0)
    move.b #$20,$19(a0)
    move.b #1,$18(a0)
    move.b $28(a0),d0
    andi.w #2,d0
    move.w Offset_0x01647A(pc,d0),$30(a0)

    Offset_0x0164B4:
    move.b ($FFFFFE05).w,d0
    andi.b #2,d0
    move.b d0,$1A(a0)
    move.w $8(a0),d0
    move.w d0,d1
    subi.w #$10,d0
    addi.w #$10,d1
    move.w $C(a0),d2
    move.w d2,d3
    subi.w #$10,d2
    addi.w #$10,d3
    lea ($FFFFB000).w,a1
    btst #1,$22(a1)
    bne.s Offset_0x016510
    move.w $8(a1),d4
    cmp.w d0,d4
    bcs Offset_0x016510
    cmp.w d1,d4
    bcc Offset_0x016510
    move.w $C(a1),d4
    cmp.w d2,d4
    bcs Offset_0x016510
    cmp.w d3,d4
    bcc Offset_0x016510
    move.w d0,-(a7)
    bsr Offset_0x016544
    move.w (a7)+,d0

    Offset_0x016510:
    lea ($FFFFB040).w,a1
    btst #1,$22(a1)
    bne.s Offset_0x016540
    move.w $8(a1),d4
    cmp.w d0,d4
    bcs Offset_0x016540
    cmp.w d1,d4
    bcc Offset_0x016540
    move.w $C(a1),d4
    cmp.w d2,d4
    bcs Offset_0x016540
    cmp.w d3,d4
    bcc Offset_0x016540
    bsr Offset_0x016544

    Offset_0x016540:
    bra J_MarkObjGone_01 ; Offset_0x0165A4

    Offset_0x016544:
    move.w $30(a0),$10(a1)
    bclr #0,$22(a1)
    btst #0,$22(a0)
    beq.s Offset_0x016562
    bset #0,$22(a1)
    neg.w $10(a1)

    Offset_0x016562:
    move.w #$F, $2E(a1)
    move.w $10(a1),$14(a1)
    bclr #5,$22(a0)
    bclr #6,$22(a0)
    bclr #5,$22(a1)
    move.w #$CC,d0
    jmp PlaySound ; Offset_0x0014C6

    Map_Obj04: include "_mapsobj04.asm"
    even
    J_MarkObjGone_01: ; Offset_0x0165A4:
    jmp MarkObjGone ; (Offset_0x00D2A0)
    J_ModifySpriteAttr_2P_03: ; Offset_0x0165AA:
    jmp ModifySpriteAttr_2P ; (Offset_0x00DC30)

    I also pointed to it in Object pointers.asm.

    Another thing I'm wondering is how to add art to an object. I have an art file and a piece of code pointing to it's location but I don't understand how you make an object use it's art. Right now only garbage tiles are displayed with it's mappings.
     
  13. SuperEgg

    SuperEgg I'm a guy that knows that you know that I know Member

    Joined:
    Oct 17, 2009
    Messages:
    Location:
    THE BEST GOD DAMN STATE OF TEXAS
    Change FFFFB000 to FFFFD000
     
  14. Mohammad Sanjakdar

    Mohammad Sanjakdar Newcomer Trialist

    Joined:
    Jan 20, 2015
    Messages:
    12
    Location:
    Aleppo, Syria
    Hi i have question:

    How to know which address is not used so i can use it without getting problems
     
  15. TheInvisibleSun

    TheInvisibleSun Visible Member

    Joined:
    Jul 2, 2013
    Messages:
    424
    Location:
    Western New York, USA
    Last edited by a moderator: Jan 29, 2015
  16. warr1or2

    warr1or2 I AM CLG Member

    Joined:
    Apr 7, 2008
    Messages:
    417
    Location:
    Town Creek, AL
    the retro has some on their site, just search up "Sonic 1 Unused RAM" i think it is when I searched it
     
  17. MarkeyJester

    MarkeyJester ♡ ! Member

    Joined:
    Jun 27, 2009
    Messages:
    2,867
    ^ This, and you may want to remove the "$FFFFB040" specific part of the routine that deals with Tails.
     
    Last edited by a moderator: Jan 29, 2015
  18. presto

    presto Raised from the dead... Member

    Joined:
    Oct 12, 2014
    Messages:
    40
    Location:
    Cluj-Napoca
    EDIT: Nevermind, the new posts didn't show up for me. Trash please.
     
    Last edited by a moderator: Jan 29, 2015
  19. Psi

    Psi Well-Known Member Member

    Joined:
    Dec 20, 2014
    Messages:
    102
    Does anyone know how to branch new objects into the collision data of S3+K? Basically I've put a branch in the object's code like so:


    jsr (Test_Sprite_Collisions).l
    And then I added this to the collision coding for enemies:


    loc_100BC:
    cmpi.l #Obj_Laser,(a0) ; is it laser?
    bne.s loc_100BC_Sally ; if not branch.
    cmpi.b #0,$20(a0) ;is it correct animation?
    beq.w loc_1012E_NICOLE ;if so branch.

    loc_100BC_Sally:
    btst #1,$2B(a0)
    bne.s loc_100F0
    cmpi.b #9,$20(a0)
    beq.s loc_1012E
    cmpi.b #2,$20(a0)
    beq.s loc_1012E
    cmpi.b #2,$38(a0)
    bne.s loc_100F0
    cmpi.b #1,$2F(a0)
    beq.s loc_1012E
    cmpi.b #3,$2F(a0)
    beq.s loc_1012E
    bra.w Touch_ChkHurt
    ; ---------------------------------------------------------------------------
     
    loc_100F0:
    cmpi.b #1,$38(a0)
    bne.w Touch_ChkHurt
    tst.b $2F(a0)
     
    loc_100FE:
    beq.w Touch_ChkHurt
    btst #6,$2A(a0)
    bne.w Touch_ChkHurt
    move.w $10(a0),d1
    move.w $14(a0),d2
    sub.w $10(a1),d1
    sub.w $14(a1),d2
    jsr (GetArcTan).l
    subi.b #$20,d0
    cmpi.b #$40,d0
    bcc.w Touch_ChkHurt
    jmp loc_1012E

    loc_1012E_NICOLE:
    addq.b #2,routine(a0)
     
    loc_1012E: 
    tst.b $29(a1)
    beq.s loc_1019A
    neg.w $18(a0)
    neg.w $1A(a0)
    neg.w $1C(a0)
    move.b $28(a1),$25(a1)
    move.w a0,d0
    move.b d0,$1C(a1)
    move.b #0,$28(a1)
    subq.b #1,$29(a1)
    bne.s loc_1015E
    bset #7,$2A(a1)
     
    loc_1015E:
    cmpi.b #2,$38(a0)
    bne.s locret_10198
    cmpi.b #1,$2F(a0)
    bne.s locret_10198
    move.b #2,$2F(a0)
    move.b #$21,$20(a0)
    bclr #0,$2A(a0)
     
    loc_10180:
    tst.w $18(a0)
    bmi.s loc_1018C
    bset #0,$2A(a0)
     
    loc_1018C:
    move.b $44(a0),$1E(a0)
    move.b $45(a0),$1F(a0)
     
    locret_10198:
     
    rts
    Thus far the coding only works partially, in that whether it hits an enemy seems to be completely random. I can't make any effect whatsoever on other object data like the monitors. It does collect rings for some reason though, which I don't even intend for it to do.

    Any idea what's causing problems?
     
    Last edited by a moderator: Jan 29, 2015
  20. ProjectFM

    ProjectFM Optimistic and self-dependent Member

    Joined:
    Oct 4, 2014
    Messages:
    912
    Location:
    Orono, Maine
    Thanks! Now it works properly! Now I'm stumped on how a can add art and a simple custom animation. I have the files and I have their locations in the sonic1.asm. Right now it only displays some random art and keeps flash between two pieces of it. I used this guide: http://info.sonicretro.org/SCHG_How-to:Work_with_Objects#Section_C:_Displaying.2FBasic_SSTs but it only told me where it loads the art, not where a piece of art I want is located. Also, the script to add an animation requires DisplaySprite to be in the code and I think the code I have if already using an animation. Could someone please help me with this?
     
    Last edited by a moderator: Jan 30, 2015