Difference between revisions of "Fix the SEGA Sound"
From Sonic Retro
(Migrating final source code line) |
(Completely revamped the fix because I'm tired of having people ask me why the old one didn't work on asm68k) |
||
Line 1: | Line 1: | ||
Let's fix a problem that causes a great deal of pain to anyone adding code to Sonic 1: The SEGA sound. | Let's fix a problem that causes a great deal of pain to anyone adding code to Sonic 1: The SEGA sound. | ||
− | + | So go to Sound_E1, and replace this: | |
− | + | <asm>Sound_E1: ; XREF: Sound_ExIndex | |
− | So go to | + | move.b #$88,($A01FFF).l |
− | + | move.w #0,($A11100).l ; start the Z80 | |
− | <asm> | + | move.w #$11,d1 |
− | + | loc_71FC0: | |
− | + | move.w #-1,d0 | |
− | + | loc_71FC4: | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
nop | nop | ||
− | + | dbf d0,loc_71FC4 | |
− | + | dbf d1,loc_71FC0 | |
− | + | addq.w #4,sp | |
− | + | rts</asm> | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | rts | ||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
+ | with this: | ||
+ | <asm>Sound_E1: ; XREF: Sound_ExIndex | ||
+ | lea (SegaPCM).l,a2 ; Load the SEGA PCM sample into a2. It's important that we use a2 since a0 and a1 are going to be used up ahead when reading the joypad ports | ||
+ | move.l #$6978,d3 ; Load the size of the SEGA PCM sample into d3 | ||
+ | move.b #$2A,($A04000).l ; $A04000 = $2A -> Write to DAC channel | ||
+ | PlayPCM_Loop: | ||
+ | move.b (a2)+,($A04001).l ; Write the PCM data (contained in a2) to $A04001 (YM2612 register D0) | ||
+ | move.w #$14,d0 ; Write the pitch ($14 in this case) to d0 | ||
+ | dbf d0,* ; Decrement d0; jump to itself if not 0. (for pitch control, avoids playing the sample too fast) | ||
+ | sub.l #1,d3 ; Subtract 1 from the PCM sample size | ||
+ | beq.s return_PlayPCM ; If d3 = 0, we finished playing the PCM sample, so stop playing, leave this loop, and unfreeze the 68K | ||
+ | lea ($FFFFF604).w,a0 ; address where JoyPad states are written | ||
+ | lea ($A10003).l,a1 ; address where JoyPad states are read from | ||
+ | jsr (Joypad_Read).w ; Read only the first joypad port. It's important that we do NOT do the two ports, we don't have the cycles for that | ||
+ | btst #7,($FFFFF604).w ; Check for Start button | ||
+ | bne.s return_PlayPCM ; If start is pressed, stop playing, leave this loop, and unfreeze the 68K | ||
+ | bra.s PlayPCM_Loop ; Otherwise, continue playing PCM sample | ||
+ | return_PlayPCM: | ||
+ | addq.w #4,sp | ||
+ | rts</asm> | ||
[[Category:SCHG How-tos]] | [[Category:SCHG How-tos]] |
Revision as of 07:40, 16 February 2008
Let's fix a problem that causes a great deal of pain to anyone adding code to Sonic 1: The SEGA sound.
So go to Sound_E1, and replace this: <asm>Sound_E1: ; XREF: Sound_ExIndex move.b #$88,($A01FFF).l move.w #0,($A11100).l ; start the Z80 move.w #$11,d1 loc_71FC0: move.w #-1,d0 loc_71FC4: nop dbf d0,loc_71FC4 dbf d1,loc_71FC0 addq.w #4,sp rts</asm>
with this: <asm>Sound_E1: ; XREF: Sound_ExIndex
lea (SegaPCM).l,a2 ; Load the SEGA PCM sample into a2. It's important that we use a2 since a0 and a1 are going to be used up ahead when reading the joypad ports move.l #$6978,d3 ; Load the size of the SEGA PCM sample into d3 move.b #$2A,($A04000).l ; $A04000 = $2A -> Write to DAC channel
PlayPCM_Loop:
move.b (a2)+,($A04001).l ; Write the PCM data (contained in a2) to $A04001 (YM2612 register D0) move.w #$14,d0 ; Write the pitch ($14 in this case) to d0 dbf d0,* ; Decrement d0; jump to itself if not 0. (for pitch control, avoids playing the sample too fast) sub.l #1,d3 ; Subtract 1 from the PCM sample size beq.s return_PlayPCM ; If d3 = 0, we finished playing the PCM sample, so stop playing, leave this loop, and unfreeze the 68K lea ($FFFFF604).w,a0 ; address where JoyPad states are written lea ($A10003).l,a1 ; address where JoyPad states are read from jsr (Joypad_Read).w ; Read only the first joypad port. It's important that we do NOT do the two ports, we don't have the cycles for that btst #7,($FFFFF604).w ; Check for Start button bne.s return_PlayPCM ; If start is pressed, stop playing, leave this loop, and unfreeze the 68K bra.s PlayPCM_Loop ; Otherwise, continue playing PCM sample
return_PlayPCM:
addq.w #4,sp rts</asm>