Sonic 2 Hacking Guide
Binary - Sound & Music

Music is a great interest to many people. This is one of the difficult areas of the Sonic 2 ROM. The reason is due to the compression used. This doesn't mean that you can't put your own music into Sonic 2, but it will be helpful to port the Sonic 2 beta music into the ROM instead since that doesn't use compression. So, to port the Sonic 2 beta music into the final ROM, simply copy everything from 0EC000 to 0FFFFF. Once this information is put into the final ROM, you can begin modifying the music.

NOTE: A few things are taken from the Genesis Sound Software Manual.

0F8000 - Music pointers
0FEE91 - Sound pointers

Each pointer is 16-bits in size. All pointers are in little-endian format (Intel, Z80, etc). They point to the song data per song, in the order that they're listed on the Sonic 2 beta sound test.

The format for the songs is a bit complex. Read carefully and follow along. I will number the important bytes from the start of the song data.

HEADER:
#1 - #48

1 + 2 - Voice list pointer

3 - Number of DAC and FM channel pointers
4 - Number of PSG channel pointers

This is the confusing part. The header is generally 48 bytes in size. However, changing bytes 3 and 4 can will change that theory. If byte 3 is equal to 06, that means that there will be a DAC channel, and 5 FM channels. If byte 3 was only 02, there would be a DAC channel and a single FM channel. The list below assumes that the song uses a DAC channel, 5 FM channels, and 3 PSG channels. Although, if you were to exclude FM channel 5 by making byte 3 equal to 05, then everything after that comes sooner. So, PSG channel 1 pointer for example would be bytes 27 and 28, instead of 31 and 32. If you exclude another FM channel, then PSG channel 1 pointer is bytes 23 and 24.

5 - Tempo cut-time (4-bit only)
6 - Tempo (4-bit only)

7 + 8 - DAC pointer

11 + 12 - FM channel 1 pointer
13 - FM channel 1 key
14 - FM channel 1 volume resistance
15 + 16 - FM channel 2 pointer
17 - FM channel 2 key
18 - FM channel 2 volume resistance
19 + 20 - FM channel 3 pointer
21 - FM channel 3 key
22 - FM channel 3 volume resistance
23 + 24 - FM channel 4 pointer
25 - FM channel 4 key
26 - FM channel 4 volume resistance
27 + 28 - FM channel 5 pointer
29 - FM channel 5 key
30 - FM channel 5 volume resistance

31 + 32 - PSG channel 1 pointer
33 - PSG channel 1 key
34 - PSG channel 1 volume resistance
37 + 38 - PSG channel 2 pointer
39 - PSG channel 2 key
40 - PSG channel 2 volume resistance
43 + 44 - PSG channel 3 pointer
45 - PSG channel 3 key
46 - PSG channel 3 volume resistance

Now, here are some things you should know for editing music.

00-7F - Note duration
80-DF - Notes (80 is a rest)
E0-FF - Coordination flags

Whenever you need to change the duration of a note, you simply type a number ranging from 00 to 7F. These define how many beats the note will be held for. So, for example, one note with a duration of 06 is the same as 6 notes with a duration of 01.

Not all the coordination flags are known yet, but here are the ones I do know of.

E0xx - panning, AMS, FMS
E6xx - subtract xx from channel volume
E7xx - prevent next note from attacking
E8xx - set note fill amount to xx
E9xx - add xx to channel key
EAxx - set music tempo to xx
EFxx - set voice selection to xx
F0aabbccdd - modulation
F2 - stop the track
F6yyyy - jump to position yyyy
F7eexxyyyy - repeat xx times at position yyyy before moving on
F8yyyy - jump to position yyyy (keep previous position in memory for returning)
F9 - return

aa - Wait aa, then modulate
bb - modulation speed (01 = fast, FF = slow)
cc - modulation change per step (01 = -0.2, 02 = -0.4, FF = +0.2, FE = +0.4, etc.)
dd - number of modulation steps (01 = down, up; 02 = down, up, up, down; etc.)
ee - if ee is 01, it will reset the repeat values (never-ending loop)

E0xx can be tricky since it is handled at bit-level. So, here is the format for 'xx' within the 'E0' coordination flag.

8-bits - L R A A x F F F

FFF - This value controls the FMS (frequency modulation sensitivity). The following is a listing of all the values and the results they produce

0 - 0
1 - add/sub 3.4%
2 - add/sub 6.7%
3 - add/sub 10%
4 - add/sub 14%
5 - add/sub 20%
6 - add/sub 40%
7 - add/sub 80%

AA - This value controls the AMS (amplitude modulation sensitivity). The following is a listing of all the values and the results they produce

0 - 0dB
1 - 1.4dB
2 - 5.9dB
3 - 11.8dB

R - When this bit is turned on, right stereo is enabled for the channel.
L - When this bit is turned on, left stereo is enabled for the channel.

 

003EA0 - Music playlist for 1 player levels
003EB2 - Music playlist for 2 player levels

These playlists use a single byte for every level to tell the game what music to play for each level. The song values are equivelent to those listed in the sound test, except 80 is added to the value. The following also add 80 to the actual value.

00392B - Sound to play for Sega logo
0051E5 - Sound to play for special stage
009765 - Sound to play for level select and debug codes
009795 - Sound to play for 14 continues code
0097A5 - Sound to play for Super Sonic code
00E731 - Sound to play for EHZ boss
00E827 - Sound to play for MZ boss
00F019 - Sound to play for HTZ boss
00F11D - Sound to play for OOZ boss
00F237 - Sound to play for MCZ boss
00F349 - Sound to play for CNZ boss
00F42B - Sound to play for CPZ boss
00F583 - Sound to play for ARZ boss
011FD7 - Sound to play for ring
012145 - Sound to play for loosing rings
0129CD - Sound to play for super ring
012A25 - Sound to play for super sneakers on
012A37 - Sound to play for shield
012A81 - Sound to play for invincibility
018A69 - Sound to play for spring up
018BBF - Sound to play for spring side
018D63 - Sound to play for spring down
018E97 - Sound to play for spring diag-up
018FA3 - Sound to play for spring diag-down
01926B - Sound to play for Sonic passing end-level sign
0192F9 - Sound to play for Tails passing end-level sign
0192CD - Sound to play for Sonic passing end-level sign (winner)
019349 - Sound to play for Tails passing end-level sign (winner)
01A153 - Sound to play for super sneakers off
01AAAF - Sound to play for Sonic jumping
01AB9D - Sound to play for Super Sonic
01C68B - Sound to play for Tails jumping
01F191 - Sound to play for starpost
0210FB - Sound to play for objects being destroyed (enemies, monitors, etc)
021C55 - Sound to play for seesaw
0223D8 - Sound to play for tire-spring
023D8F - Sound to play for jet-platform spring
024271 - Sound to play for upward pressure-spring
0244C9 - Sound to play for side pressure-spring
02BAA9 - Sound to play for using elevator
02BAFB - Sound to play for elevator returning

What's interesting is the 14 continues code. If you look at the initial value given in the ROM, you'll see why the sound doesn't play properly. They forgot to add 80 to the value! Add 80 to it and it'll play the "continue" sound.

0ED100 - Start of DAC sample data

DAC samples are the drum beats you hear in the music. The format is very simple and easy to understand. Each set of 4-bits represents a pitch. All pitches are played in the piano C key. 'F' represents the highest pitched C you can have, and '1' represents the lowest. Zero is a null, which means that it won't play a note. Listed below are some pointers. All of it is written in little-endian format, so read it backwards. So, the pointer for sample 81 is '00 D1', when in fact this is actually read 'D1 00'. This means that sample 81 is located at address 0ED100. The length is simply 16-bits (2 bytes) that say how long the sample is. So, the 81 length is '94 02'. This means that it is 0294 (660 in decimal) bytes in length.

0ECF7C - Sample 81 pointer
0ECF7E - Sample 81 length
0ECF81 - Sample 82 pointer
0ECF83 - Sample 82 length
0ECF85 - Sample 83 pointer
0ECF87 - Sample 83 length
0ECF8A - Sample 84 pointer
0ECF8C - Sample 84 length
0ECF8E - Sample 85 pointer
0ECF90 - Sample 85 length
0ECF93 - Sample 86 pointer
0ECF95 - Sample 86 length

0ECF9C - DAC master list

FORMAT:
#1 #2

1 - Sample ID
2 - Rate (the lower the value, the faster the rate is)

Sample 81 - Kick
Sample 82 - Snare
Sample 83 - Clap
Sample 84 - Scratch
Sample 85 - Timpani
Sample 86 - Tom

0EC23D - Change to '00' to disable DAC

0F1E8C-0F7FFF - Sega PCM sound

You can replace the Sega PCM sound easily. You simply need a WAV file that is encoded in 16kHz 8-bit mono format. Then, copy the data in the WAV file starting at address 000038, and put it in place of the Sega PCM sound already in the game.

0ECF36 - Master playlist definitions

The master playlist tells the game exactly what value will play what song. This is different from the regular music playlist because when changing these, it affects any point in the game that uses the specific sound value being changed. Here is the list of songs and their values.

Sound #01 - 92
Sound #02 - 81
Sound #03 - 85
Sound #04 - 8F
Sound #05 - 82
Sound #06 - 94
Sound #07 - 86
Sound #08 - 80
Sound #09 - 83
Sound #0A - 87
Sound #0B - 84
Sound #0C - 91
Sound #0D - 8E
Sound #0E - 8C
Sound #0F - 90
Sound #10 - 9B
Sound #11 - 89
Sound #12 - 88
Sound #13 - 8D
Sound #14 - 8B
Sound #15 - 9A
Sound #16 - 93
Sound #17 - 95
Sound #18 - B5
Sound #19 - 96
Sound #1A - 97
Sound #1B - B8
Sound #1C - ??
Sound #1D - BA
Sound #1E - BD
Sound #1F - 9C

The master playlist goes in order from sound #01 and goes up to #1F. If you see an 'FF', ignore it and move to the next byte.

If you want to modify voices, it's not too difficult. As long as you understand how FM synthesis works, you should be fine. If you don't know anything about FM synthesis, you're probably going to have some trouble modifying voices.

A voice is simply an FM 'instrument'. You can create up to 128 different voices. That's more than enough for a song. Most songs only need about 4 or 5. Each voice is 25 bytes in size. There isn't a header for voices. They're simply listed one after the other.

FORMAT:
#1 - #25

1 - Feedback (next 3 bits) / Algorithm (lower 3 bits)
2 - Detune of operator 4 (nybble 1) / Coarse-frequency of operator 4 (nybble 2)
3 - Detune of operator 3 (nybble 1) / Coarse-frequency of operator 3 (nybble 2)
4 - Detune of operator 2 (nybble 1) / Coarse-frequency of operator 2 (nybble 2)
5 - Detune of operator 1 (nybble 1) / Coarse-frequency of operator 1 (nybble 2)
6 - [RS] of operator 4 (upper 2 bits) / Attack rate [AR] of operator 4 (lower 5 bits)
7 - [RS] of operator 3 (upper 2 bits) / Attack rate [AR] of operator 3 (lower 5 bits)
8 - [RS] of operator 2 (upper 2 bits) / Attack rate [AR] of operator 2 (lower 5 bits)
9 - [RS] of operator 1 (upper 2 bits) / Attack rate [AR] of operator 1 (lower 5 bits)
10 - [AM] of operator 4 / First decay rate [D1R] of operator 4 (lower 5 bits)
11 - [AM] of operator 3 / First decay rate [D1R] of operator 3 (lower 5 bits)
12 - [AM] of operator 2 / First decay rate [D1R] of operator 2 (lower 5 bits)
13 - [AM] of operator 1 / First decay rate [D1R] of operator 1 (lower 5 bits)
14 - Second decay rate [D2R] of operator 4 (00-14)
15 - Second decay rate [D2R] of operator 3 (00-14)
16 - Second decay rate [D2R] of operator 2 (00-14)
17 - Second decay rate [D2R] of operator 1 (00-14)
18 - First decay level [D1L] of operator 4 (nybble 1) / Release rate [RR] of operator 4 (nybble 2)
19 - First decay level [D1L] of operator 3 (nybble 1) / Release rate [RR] of operator 3 (nybble 2)
20 - First decay level [D1L] of operator 2 (nybble 1) / Release rate [RR] of operator 2 (nybble 2)
21 - First decay level [D1L] of operator 1 (nybble 1) / Release rate [RR] of operator 1 (nybble 2)
22 - Output level of operator 4
23 - Output level of operator 3
24 - Output level of operator 2
25 - Output level of operator 1

Use only odd numbers for velocity. Also, detune 0-7 is negative, and detune 8-F is positive.

The YM2612 algorithms are very specific. There's 8 algorithms total. In fact, they're identical to the algorithms on the Yamaha TX81Z. Click here if you would like to see what the algorithms are. Keep in mind that the algorithm number in the voice is always one less than what is listed in the chart.

 

If you're interested in putting music into Sonic 2 without copying the sound driver information from the beta version, you'll need to know the format of the compression. Here's how the compression works.

There's a compression byte at the beginning of a song. To understand how it functions, you need to examine it at a bit-level. So, lets take '2B' for example.

2B - 00101011

Bits are read from right to left. A '1' means that there's no special copy instructions applied. The byte is read 'as-is'. A '0' is a flag. A flag tells the game to read bytes from a given location. So, using compression byte '2B', we can have something like the following.

2B 00 01 (24 00) 05 (53 00) 09 (21 00) (3A 00)

A flag is handled by 2 bytes. 24 00 for example means that the game will grab 3 bytes from address 24 and read those before it continues. If you make the '00' into a '01', it will read 4 bytes from the address; '02' will read 5 bytes, etc. Flag addresses recognize the address 001E from the beginning of the song as address 00.

After the jobs of all 8 bits from the compression byte have been performed, the very next byte will be a compression byte that will have the same functions.

Also, something important to keep in mind -- whenever you need to make jumps, the beginning of the song is recognized as address 1380 (starting from the first non-compression byte).

Finally, at the very beginning of the song, there is a little-endian word (2 bytes) that defines the total size of the song. Although, whatever it reads will actually represent 2 bytes more than shown. So, if the word is C102 (02C1 bytes), it actually represents 02C3 bytes in the song.