Difference between revisions of "Sonic the Hedgehog (8-bit)"
From Sonic Retro
(Rewrote palettes section, many fixes elsewhere) |
m (Marked SMS / GG addresses with icons) |
||
Line 756: | Line 756: | ||
*<tt>FN</tt>: "Fifty-Nine". Unknown purpose, but in all headers this value is <tt>59</tt> | *<tt>FN</tt>: "Fifty-Nine". Unknown purpose, but in all headers this value is <tt>59</tt> | ||
*<tt>DR</tt>: "Duplicate Rows". An offset from the start of the level art header, to the where the duplicate rows list begins. For tile sets this value is always "<tt>0108</tt>" (256 + 8 in hexadecimal). For sprite sets it's "<tt>0088</tt>" (128 + 8 in hexadecimal) | *<tt>DR</tt>: "Duplicate Rows". An offset from the start of the level art header, to the where the duplicate rows list begins. For tile sets this value is always "<tt>0108</tt>" (256 + 8 in hexadecimal). For sprite sets it's "<tt>0088</tt>" (128 + 8 in hexadecimal) | ||
− | *<tt>AD</tt>: "Art Data". An offset, from the beginning of the level art header (e.g. <tt>$32FE6</tt>), to the start of the [[#Art_Data|Art Data]] section. This is critically important because the length of the [[#Duplicate_Rows_List|duplicate rows list]] can vary | + | *<tt>AD</tt>: "Art Data". An offset, from the beginning of the level art header (e.g. {{SMS}} <tt>$32FE6</tt>), to the start of the [[#Art_Data|Art Data]] section. This is critically important because the length of the [[#Duplicate_Rows_List|duplicate rows list]] can vary |
*<tt>X0</tt>: Unknown, but in all headers, this value is "<tt>0</tt>" | *<tt>X0</tt>: Unknown, but in all headers, this value is "<tt>0</tt>" | ||
*<tt>TY</tt>: "Type". <tt>08</tt> for [[#Level_Art|tile sets]], <tt>04</tt> for sprite sets. Could be something to do with the number of tiles (divided by 32) or with where in VRAM they go | *<tt>TY</tt>: "Type". <tt>08</tt> for [[#Level_Art|tile sets]], <tt>04</tt> for sprite sets. Could be something to do with the number of tiles (divided by 32) or with where in VRAM they go | ||
Line 783: | Line 783: | ||
Begin by walking the [[#Unique_Rows_List|unique rows list]] again in the same order as before, but this time when a bit value is 1 it means that row is a duplicate: read a byte from the duplicate rows list. This value is an index to where in the [[#Art_Data|art data]] the row is located, i.e. a value of <tt>80</tt> (hex) means: | Begin by walking the [[#Unique_Rows_List|unique rows list]] again in the same order as before, but this time when a bit value is 1 it means that row is a duplicate: read a byte from the duplicate rows list. This value is an index to where in the [[#Art_Data|art data]] the row is located, i.e. a value of <tt>80</tt> (hex) means: | ||
− | + | $30000 base address (Master System) | |
− | $30000 | + | + 2FE6 "Level Art" pointer in the level header, Green Hill for example |
− | + 2FE6 | + | + 7C2 Art Data pointer in the level art header, again Green Hill |
− | + 7C2 | + | + 80*4 Skip to the 128th, decimal, row in the art data |
− | + 80*4 | ||
− | |||
For values <tt>00</tt> to <tt>EF</tt> (0 to 239), there is only one byte, indicating the row index in the [[#Art_Data|Art Data]]. However, for values after <tt>EF</tt>, there are two bytes. The first one starts with an <tt>F</tt>, so the actual line number is the two bytes number minus <tt>F0 00</tt>. E.g.: <tt>F3 A2</tt> is for art data row number <tt>3A2</tt>. Note that you can also write line numbers <tt>00</tt> to <tt>EF</tt> using two bytes numbers, but this is a waste of space (that's why they are stored with one byte!). | For values <tt>00</tt> to <tt>EF</tt> (0 to 239), there is only one byte, indicating the row index in the [[#Art_Data|Art Data]]. However, for values after <tt>EF</tt>, there are two bytes. The first one starts with an <tt>F</tt>, so the actual line number is the two bytes number minus <tt>F0 00</tt>. E.g.: <tt>F3 A2</tt> is for art data row number <tt>3A2</tt>. Note that you can also write line numbers <tt>00</tt> to <tt>EF</tt> using two bytes numbers, but this is a waste of space (that's why they are stored with one byte!). | ||
Line 820: | Line 818: | ||
===Level Headers Pointers=== | ===Level Headers Pointers=== | ||
− | A level header pointer is comprised of two bytes. The data for the pointer is stored in little endian format. The value stored by this pointer specifies the number of bytes away a level header is from <tt>$15580</tt> | + | A level header pointer is comprised of two bytes. The data for the pointer is stored in little endian format. The value stored by this pointer specifies the number of bytes away a level header is from {{SMS}} <tt>$15580</tt> {{GG}} <tt>$15600</tt>. |
There are 37 Level Headers in total. Some levels have more than one pointer because they can be accessed from different locations, and Sonic's starting position differs at level start. Also two invalid level pointers exist that act as dividers between the main sequence of levels and the out-of-sequence levels (Scrap Brain's sub-maps and the Special Stages). See the [[#ROM_Map|ROM map]] for the full list of level pointers. | There are 37 Level Headers in total. Some levels have more than one pointer because they can be accessed from different locations, and Sonic's starting position differs at level start. Also two invalid level pointers exist that act as dividers between the main sequence of levels and the out-of-sequence levels (Scrap Brain's sub-maps and the Special Stages). See the [[#ROM_Map|ROM map]] for the full list of level pointers. | ||
''Example:'' | ''Example:'' | ||
− | The two first bytes are <tt>4A 00</tt>. So, at <tt>$15580</tt> + <tt>$004A</tt>, we will find the level header for the first level (Green Hill 1). | + | The two first bytes are <tt>4A 00</tt>. So, at {{SMS}} <tt>$15580</tt> + <tt>$004A</tt>, we will find the level header for the first level (Green Hill 1). |
===Level Headers=== | ===Level Headers=== | ||
− | The level headers are located at <tt>$155CA</tt> – <tt>$15AB3</tt> | + | The level headers are located at {{SMS}} <tt>$155CA</tt> – <tt>$15AB3</tt> {{GG}} <tt>$1564A</tt> – <tt>$15B34</tt>. |
Each level header use 37 bytes. Here is the format (partial): | Each level header use 37 bytes. Here is the format (partial): | ||
Line 840: | Line 838: | ||
*LW,LH (Level Width, Level Height): Real level dimensions (divided by 32), used to limit the view | *LW,LH (Level Width, Level Height): Real level dimensions (divided by 32), used to limit the view | ||
*SX,SY (Start X, Start Y): Player starting position (divided by 32) | *SX,SY (Start X, Start Y): Player starting position (divided by 32) | ||
− | *FL (Floor Location): How many bytes away from <tt>$14000</tt> | + | *FL (Floor Location): How many bytes away from {{SMS}} <tt>$14000</tt> the [[#Floor_Layout|floor]] is located (Little Endian) |
*FS (Floor Size): Floor data size, in bytes (Little Endian) | *FS (Floor Size): Floor data size, in bytes (Little Endian) | ||
− | *ML (Mappings Location): How many bytes away from <tt>$10000</tt> | + | *ML (Mappings Location): How many bytes away from {{SMS}}{{GG}} <tt>$10000</tt> the [[#Block_Mappings|mappings]] for this level are located (Little Endian) |
− | *LA (Level Art): How many bytes away from <tt>$30000</tt> | + | *LA (Level Art): How many bytes away from {{SMS}} <tt>$30000</tt> the [[#Level_Art|level art]] is located (Little Endian) |
− | *SA (Sprite Art): How many bytes away from <tt>$24000</tt> | + | *SA (Sprite Art): How many bytes away from {{SMS}} <tt>$24000</tt> is the sprite art located (Little Endian) |
*IP (Initial Palette): Indicates the number of the initial [[#Level_Palettes|palette pointer]] to use, in the pointer order of appearance (so, indicates the palette) | *IP (Initial Palette): Indicates the number of the initial [[#Level_Palettes|palette pointer]] to use, in the pointer order of appearance (so, indicates the palette) | ||
*CC (Color Cycles): Indicates the number of color cycles for the level palette | *CC (Color Cycles): Indicates the number of color cycles for the level palette | ||
*CP (Cyclic Palette): Indicates the number of the [[#Level_Cycle_Palettes|cyclic palette]] pointer to use, in the pointer order of appearance (so, indicates the palette) | *CP (Cyclic Palette): Indicates the number of the [[#Level_Cycle_Palettes|cyclic palette]] pointer to use, in the pointer order of appearance (so, indicates the palette) | ||
− | *SL (Sprites Location): How many bytes away from <tt>$15580</tt> | + | *SL (Sprites Location): How many bytes away from {{SMS}} <tt>$15580</tt> {{GG}} <tt>$15600</tt> the [[#Sprite_Layout|sprite layout]] is located (Little Endian) |
*UW (Under Water flag): Controls the under-water effect (slow movement / water colour / drowning) in Labyrinth (<tt>80</tt> is on, <tt>00</tt> is off). Appears to only affect Labyrinth, using this flag on other levels does not create the water effect so either it's hard-coded to Labyrinth or some other undocumented data controls it | *UW (Under Water flag): Controls the under-water effect (slow movement / water colour / drowning) in Labyrinth (<tt>80</tt> is on, <tt>00</tt> is off). Appears to only affect Labyrinth, using this flag on other levels does not create the water effect so either it's hard-coded to Labyrinth or some other undocumented data controls it | ||
*MU (Music): | *MU (Music): | ||
Line 980: | Line 978: | ||
A palette of 32 colors is used, the first 16 reserved for the level and the second 16 for the sprites. | A palette of 32 colors is used, the first 16 reserved for the level and the second 16 for the sprites. | ||
− | The | + | The Master System uses 6-bit colors, each colour in a palette is one byte (32 bytes for a full palette, 16 bytes for a half-palette). 2 bits are assigned to each color (R:0–2, G:0–2, B:0–2), for a total of 64 possible colors. The extra two bits in the byte are unused, therefore the format of the byte is: <tt>00BBGGRR</tt>. The corresponding 24-bit color byte value for the 2-bit numbers are: 0 = 0, 1 = 80, 2 = 175, 3 = 255. |
The Game Gear uses 9-bit colors, so each color use two bytes (the first nybble of the second byte is 0, and values for the color nybble are in steps of 2). This color can be defined like that : R(0–7), G(0–7), B(0–7). So, there are only 8 possible values for each primary color. Here are the RGB correspondence : <tt>0/1 = 0</tt>, <tt>2/3 = 36</tt>, <tt>4/5 = 72</tt>, <tt>6/7 = 109</tt>, <tt>8/9 = 145</tt>, <tt>A/B = 182</tt>, <tt>C/D = 218</tt>, <tt>E/F = 255</tt>. So, you can have a maximum of 512 colors. The format for the two bytes is : <tt>GGGGRRRR 0000BBBB</tt> | The Game Gear uses 9-bit colors, so each color use two bytes (the first nybble of the second byte is 0, and values for the color nybble are in steps of 2). This color can be defined like that : R(0–7), G(0–7), B(0–7). So, there are only 8 possible values for each primary color. Here are the RGB correspondence : <tt>0/1 = 0</tt>, <tt>2/3 = 36</tt>, <tt>4/5 = 72</tt>, <tt>6/7 = 109</tt>, <tt>8/9 = 145</tt>, <tt>A/B = 182</tt>, <tt>C/D = 218</tt>, <tt>E/F = 255</tt>. So, you can have a maximum of 512 colors. The format for the two bytes is : <tt>GGGGRRRR 0000BBBB</tt> | ||
===Level Palettes=== | ===Level Palettes=== | ||
− | A table of Level Palette Pointers are located at: <tt>$0627C</tt> – <tt>$0628B</tt> | + | A table of Level Palette Pointers are located at: {{SMS}} <tt>$0627C</tt> – <tt>$0628B</tt> {{GG}} <tt>$23440</tt> – <tt>$23450</tt>. Each pointer (2 bytes, little-endian) in the table points to the beginning of a palette in the ROM. On the Master System, these pointers are absolute (give the actual ROM address), but on the Game Gear, are relative, specifying how many bytes from {{GG}} <tt>$23400</tt> the palette can be found. Each level palette is a full-palette (Tiles and Sprites) of 32-colours. |
− | The level palettes are located at: <tt>$0629E</tt> – <tt>$065ED</tt> | + | The level palettes are located at: {{SMS}} <tt>$0629E</tt> – <tt>$065ED</tt> {{GG}} <tt>$23450</tt> – <tt>$23C00</tt>. See the [[#ROM_Map|ROM map]] for a more detailed listing. |
The Initial Palette ("<tt>IP</tt>") value of a [[#Level_Headers|Level Header]] is an index to the level palette pointers, i.e. 0–7, specifying which palette to load. | The Initial Palette ("<tt>IP</tt>") value of a [[#Level_Headers|Level Header]] is an index to the level palette pointers, i.e. 0–7, specifying which palette to load. | ||
Line 994: | Line 992: | ||
To create a simple animation effect, such as flowing water, the palettes are "cycled" through a list of other palettes allowing the colours to rapidly change without having to change actual pixel data. | To create a simple animation effect, such as flowing water, the palettes are "cycled" through a list of other palettes allowing the colours to rapidly change without having to change actual pixel data. | ||
− | A table of cycle palette pointers exists at <tt>$0628C</tt> – <tt>$0629D</tt> | + | A table of cycle palette pointers exists at {{SMS}} <tt>$0628C</tt> – <tt>$0629D</tt> {{GG}} <tt>$23400</tt> – <tt>$23450</tt>. Each pointer (2 bytes, little-endian) in the table points to the beginning of a cycle palette. Each cycle palette is a half-palette of 16 colours and the number of cycle palettes in a cycle is determined in the [[#Level_Headers|Level Header]] by the Cycle Count ("<tt>CC</tt>") value. The Cycle Palette ("<tt>CP</tt>") value in the [[#Level_Headers|Level Header]] is an index to the Cycle Palette Pointers table, determining which palette cycle to use. |
Note that the Level Palettes and Cycle Palettes are intermixed, which is why the pointer tables are necessary. See the [[#ROM_Map|ROM Map]] for a detailed listing of the palette locations. | Note that the Level Palettes and Cycle Palettes are intermixed, which is why the pointer tables are necessary. See the [[#ROM_Map|ROM Map]] for a detailed listing of the palette locations. | ||
Line 1,018: | Line 1,016: | ||
:<tt>00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F</tt> | :<tt>00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F</tt> | ||
− | Block Mappings are stored uncompressed in the ROM. The number of blocks in each mapping is apparently not stored in the ROM, so to determine the number of blocks in each mapping you need to compare the distance between "Mapping Location" Level Headers. For your convenience the size of the mappings are charted below. | + | Block Mappings are stored uncompressed in the ROM. The number of blocks in each mapping is apparently not stored in the ROM, so to determine the number of blocks in each mapping you need to compare the distance between "Mapping Location" [[#Level_Headers|Level Headers]]. For your convenience the size of the mappings are charted below. |
===Master System Version=== | ===Master System Version=== | ||
Line 1,080: | Line 1,078: | ||
==Floor Layout== | ==Floor Layout== | ||
− | The floor layout is composed of multiple 4×4 tile blocks (See Block Mappings). Each byte indicates the index of the tile to which to use. However, the data is compressed, so you will have to decompress it first | + | The floor layout is composed of multiple 4×4 tile blocks (See [[#Block_Mappings|Block Mappings]]). Each byte indicates the index of the tile to which to use. However, the data is compressed, so you will have to [[#RLE_Compression|decompress]] it first. |
− | Floor layouts are located at: <tt>$16DEA</tt> – <tt>$1FFFF</tt> | + | Floor layouts are located at: {{SMS}} <tt>$16DEA</tt> – <tt>$1FFFF</tt> {{GG}} <tt>$17430</tt> – <tt>$1F600</tt>. You'll have to use the pointers ([[#Level_Headers|Level Headers]]), in order to determine their starting address. |
− | You'll have to use the pointers ([[#Level_Headers|Level Headers]]), in order to determine their starting address. | ||
==Sprite Layout== | ==Sprite Layout== | ||
Line 1,092: | Line 1,089: | ||
:<tt>OO XX YY</tt> | :<tt>OO XX YY</tt> | ||
− | <tt>XX</tt> and <tt>YY</tt> are the object's coordinates divided by 32. <tt>OO</tt> is one of the object listed below. (Both the | + | <tt>XX</tt> and <tt>YY</tt> are the object's coordinates divided by 32. <tt>OO</tt> is one of the object listed below. (Both the Game Gear and Master System versions share the same Sprite Layout Data) |
{|class="prettytable" | {|class="prettytable" | ||
Line 1,318: | Line 1,315: | ||
{|class="prettytable" | {|class="prettytable" | ||
− | ! Zone || Offset | + | ! Zone || {{SMS}} Offset || {{GG}} Offset |
|- | |- | ||
|Green Hill Act 1 | |Green Hill Act 1 | ||
Line 1,460: | Line 1,457: | ||
==Blinking Items Art== | ==Blinking Items Art== | ||
− | In the game, there are some blinking items. The most common are the box items. You can easily edit them. Each of these items is 16×16, but you must understand that it is composed of four 8×8 tiles. The tiles are displayed from up to down and from left to right. The format is the same as the art in savestates (32 bytes for each 8×8 tile, 128 bytes for the item) | + | In the game, there are some blinking items. The most common are the box items. You can easily edit them. Each of these items is 16×16, but you must understand that it is composed of four 8×8 tiles. The tiles are displayed from up to down and from left to right. The format is the same as the art in savestates (32 bytes for each 8×8 tile, 128 bytes for the item). |
− | Blinking items are located at: <tt>$15200</tt> – <tt>$15600</tt> | + | Blinking items are located at: {{SMS}} <tt>$15180</tt> – <tt>$1557F</tt> {{GG}} <tt>$15200</tt> – <tt>$15600</tt> |
Here are the items you can edit : | Here are the items you can edit : | ||
Line 1,469: | Line 1,466: | ||
! ID || Description | ! ID || Description | ||
|- | |- | ||
− | |1 | + | |1 || Super Rings |
− | |Super Rings | ||
|- | |- | ||
− | |2 | + | |2 || Power Sneakers |
− | |Power Sneakers | ||
|- | |- | ||
− | |3 | + | |3 || One-Up |
− | |One-Up | ||
|- | |- | ||
− | |4 | + | |4 || Shield |
− | |Shield | ||
|- | |- | ||
− | |5 | + | |5 || Invincible |
− | |Invincible | ||
|- | |- | ||
− | |6 | + | |6 || Chaos Emerald |
− | |Chaos Emerald | ||
|- | |- | ||
− | |7 | + | |7 || Starpost (Checkpoint) |
− | |Starpost | ||
|- | |- | ||
− | |8 | + | |8 || Continue |
− | |Continue | ||
|} | |} | ||
==Level Art== | ==Level Art== | ||
− | The level art starts at: <tt>$32FE6</tt> | + | The level art starts at: {{SMS}} <tt>$32FE6</tt> {{GG}} <tt>$32ED5</tt>. The "Level Art" value in the [[#Level_Headers|Level Header] specifies how far from {{SMS}}{{GG}} <tt>$30000</tt> the level art for that zone begins. See the [[#ROM_Map|ROM Map]] for a full list of level art addresses. |
− | The graphics for a level consist of 256 tiles. Each tile consists of 8 rows (of 8 pixels). See the | + | The graphics for a level consist of 256 tiles. Each tile consists of 8 rows (of 8 pixels). See the [[#Art_Compression|Art Compression]] section for how to fully read and decompress the tile graphics. |
==Game Text== | ==Game Text== | ||
+ | |||
Strings of text in the game are stored in a simple format that begins with an X / Y location on the screen to begin printing, are terminated with <tt>FF</tt> and may contain special control-codes, such as <tt>FE</tt> to move the cursor. | Strings of text in the game are stored in a simple format that begins with an X / Y location on the screen to begin printing, are terminated with <tt>FF</tt> and may contain special control-codes, such as <tt>FE</tt> to move the cursor. | ||
Line 1,523: | Line 1,513: | ||
===Zone Titles=== | ===Zone Titles=== | ||
− | The zone titles ("GREEN HILL", "BRIDGE", …) shown on the map screen are stored at <tt>$0122D</tt> – <tt>$01286</tt> | + | The zone titles ("GREEN HILL", "BRIDGE", …) shown on the map screen are stored at {{SMS}} <tt>$0122D</tt> – <tt>$01286</tt>. Each title is padded with spaces so that all titles are always 12 bytes long. |
The first three zones use the character codes from the first map screen, therefore the data looks like this: | The first three zones use the character codes from the first map screen, therefore the data looks like this: | ||
Line 1,550: | Line 1,540: | ||
===Final Score Titles=== | ===Final Score Titles=== | ||
− | Upon completion of the game, a final score screen is shown and bonuses are awarded for the number of emeralds, lives remaining and a "Special Bonus". These titles are stored at <tt>$0197E</tt> – <tt>$019AD</tt> | + | Upon completion of the game, a final score screen is shown and bonuses are awarded for the number of emeralds, lives remaining and a "Special Bonus". These titles are stored at {{SMS}} <tt>$0197E</tt> – <tt>$019AD</tt>. |
Each string is padded with spaces to be 13 characters in length. The first tile set is used. | Each string is padded with spaces to be 13 characters in length. The first tile set is used. | ||
Line 1,565: | Line 1,555: | ||
===Credits Text=== | ===Credits Text=== | ||
− | The text for the credits that roll at the end of the game is stored at <tt>$02095</tt> – <tt>$02AD5</tt> | + | The text for the credits that roll at the end of the game is stored at {{SMS}} <tt>$02095</tt> – <tt>$02AD5</tt>. |
Additional control codes appear in the credits: | Additional control codes appear in the credits: | ||
Line 1,577: | Line 1,567: | ||
Here is a full decode of the credits roll: | Here is a full decode of the credits roll: | ||
− | + | $02905 14 03 AE 9E 7F 5E 2E SONIC | |
− | $02905 14 03 AE 9E 7F 5E 2E SONIC | + | FE 15 04 AF 4F 3E THE |
− | + | FE 13 05 4F 3E 2F 4E 3E 4F 9E 4E HEDGEHOG | |
− | + | FD 3C 00 | |
− | + | FE 12 0C 7E 1E AE AF 3E 9F MASTER | |
− | + | FE 13 0D AE DE AE AF 3E 7E SYSTEM | |
− | + | FE 14 0E BF 3E 9F AE 5E 9E 7F VERSION | |
− | + | FD 3C 00 | |
− | + | FC 09 | |
− | + | FE 14 0B AE 9E 7F 5E 2E SONIC | |
− | + | FE 15 0C AF 4F 3E THE | |
− | + | FE 13 0D 4F 3E 2F 4E 3E 4F 9E 4E HEDGEHOG | |
− | + | FD 3C 00 | |
− | + | FE 12 0F 8E 9F 5E 4E 5E 7F 1E 6F ORIGINAL | |
− | + | FE 13 10 2E 4F 1E 9F 1E 2E AF 3E 9F CHARACTER | |
− | + | FE 14 11 2F 3E AE 5E 4E 7F DESIGN | |
− | + | FD 3C 00 | |
− | + | FC 04 | |
− | + | FE 14 10 AB AE 3E 4E 1E ©SEGA | |
− | + | FD B4 00 | |
− | + | FC 09 | |
− | + | FE 14 0E AE AF 1E 3F 3F STAFF | |
− | + | FD B4 00 | |
− | + | FC 09 | |
− | + | FE 12 0B 4E 1E 7E 3E GAME | |
− | + | FE 13 0C 8F 9F 9E 4E 9F 1E 7E PROGRAM | |
− | + | FD 3C 00 | |
− | + | FE 13 0E AE 4F 5E 7F 9E 1F BE SHINOBU | |
− | + | FE 14 0F 4F 1E DE 1E AE 4F 5E HYASHI | |
− | + | FD F0 00 | |
− | + | FC 09 | |
− | + | FE 12 0B 4E 9F 1E 8F 4F 5E 2E GRAPHIC | |
− | + | FE 14 0C 2F 3E AE 5E 4E 7F DESIGN | |
− | + | FD 3C 00 | |
− | + | FE 13 0E 1E DE 1E 7F 9E AYANO | |
− | + | FE 14 0F 6E 9E AE 4F 5E 9F 9E KOSHIRO | |
− | + | FD 3C 00 | |
− | + | FE 13 11 AF 1E CF 3E 3F BE 7F 5E TAKEFUNI | |
− | + | FE 14 12 DE BE 7F 9E BE 3E YUNOUE | |
− | + | FD F0 00 | |
− | + | FC 09 | |
− | + | FE 12 0B AE 9E BE 7F 2F SOUND | |
− | + | FE 13 0C 8F 9F 9E 2F BE 2E 3E PRODUCE | |
− | + | FD 3C 00 | |
− | + | FE 13 0E 7E 1E AE 1E AF 9E MASATO | |
− | + | FE 14 0F 7F 1E CF 1E 7E BE 9F 1E NAKAMURA | |
− | + | FD F0 00 | |
− | + | FC 09 | |
− | + | FE 12 0B 9F 3E 1E 9F 9F 1E 7F 4E 3E REARRANGE | |
− | + | FE 15 0C 1E 7F 2F AND | |
− | + | FE 12 0D 9E 9F 5E 4E 5E 7F 1E 6F ORIGINAL | |
− | + | FE 16 0E 7E BE AE 5E 2E MUSIC | |
− | + | FD 3C 00 | |
− | + | FE 13 10 DE BE DF 9E YUZO | |
− | + | FE 14 11 6E 9E AE 4F 5E 9F 9E KOSHIRO | |
− | + | FD F0 00 | |
− | + | FC 09 | |
− | + | FE 13 0D AE 8F 3E 2E 5E 1E 6F SPECIAL | |
− | + | FE 15 0E AF 4F 1E 7F 6E AE THANKS | |
− | + | FD B4 00 | |
− | + | FC 02 | |
− | + | FE 13 0E DE 8E AE 4F 5E 8E EB DE YOSHIO Y | |
− | + | FD 3C 00 | |
− | + | FE 13 11 6F BE 7F 1E 9F 5E 1E 7F LUNARIAN | |
− | + | FE 1A 12 AE 4E SG | |
− | + | FD B4 00 | |
− | + | FC 09 | |
− | + | FE 12 0C 8F 9F 3E AE 3E 7F AF 3E 2F PRESENTED | |
− | + | FE 16 0E 1F DE BY | |
− | + | FE 15 10 AE 3E 4E 1E SEGA | |
− | + | FD B4 00 | |
− | + | FE 19 13 3E 7F 2F END | |
− | + | $02AD5 FF | |
− | $02AD5 FF | ||
− | |||
==RAM Editing== | ==RAM Editing== |
Revision as of 09:30, 16 June 2013
This is the Sonic Community Hacking Guide for Sonic the Hedgehog. The Guide is based on notes by David Declerck[1][2] & Kroc Camen. The Music Hacking Guide is based on notes by ValleyBell.
Contents
ROM Map
Master System
Offset | Description | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
$00000 – ? | Main Game Code | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0024B – $0026A | Labyrinth Act 1-2 Underwater Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0026B – $0028A | Labyrinth Act 3 Underwater Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$00F0E – $00F2D | Map Screen 1 Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$00F2E – $00F4D | Map Screen 2 Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0122D – $01286 | Zone Titles: (Text Format)
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$013E1 – $01400 | Title Screen Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0197E – $019AD | Final Score Titles: (Text Format) The text used for the score bonuses given on the completion of the game
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$01F9D – $01FA8 | Lightning Palette Control | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$01B8D – $01BAC | "Sonic Has Passed" Screen Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$02095 – $02AD5 | Credits Text (Text Format) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$02AD6 – $02AF5 | Credits Screen Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0626C – $0627B | End Sign Sprite Palette | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0627C – $0628B | Palette Pointers:
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0628C – $0629D | Palette Cycle Pointers:
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0629E – $065ED | Palettes:
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0731C – $0732B | Boss Sprite Palette (including end capsule) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$0C7F0 – $0FFFF | Music, sounds, and other stuff | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$10000 – $14CA0 | Block Mappings:
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$14CA0 – $1517F | UNKNOWN | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$15180 – $1557F | Blinking Items Art (Box, etc...) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$15580 – $155C9 | Level Header Pointers:
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$155CA – $15AB3 | Level Headers:
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$15AB4 – $15FFF | Sprite Layout | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$16000 – $16DE9 | Misc Mappings: (RLE Compressed)
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$16DEA – $1FFFF | Level Layout: (RLE Compressed)
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$20000 – $32FE5 | Contains sprite art and/or sprite mappings: (Compressed Art)
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$32FE6 – $3DA27 | Level Art: (Compressed Art)
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
$3DA28 – $40000 | Contains sprite art and/or sprite mappings |
Game Gear
Offset | Description | ||||||||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
$00000 – $10000 | Main Game Code, musics, sounds... | ||||||||||||||||||||||||||||||||||||
$10000 – $14D00 | Block Mappings | ||||||||||||||||||||||||||||||||||||
$14D00 – $15200 | Unknown | ||||||||||||||||||||||||||||||||||||
$15200 – $15600 | Blinking Items Art (Box, etc...) | ||||||||||||||||||||||||||||||||||||
$15600 – $1564A | Level Headers Pointers | ||||||||||||||||||||||||||||||||||||
$1564A – $15B34 | Level Headers | ||||||||||||||||||||||||||||||||||||
$15B34 – $16200 | Sprite Layout | ||||||||||||||||||||||||||||||||||||
$16200 – $16738 | Unknown | ||||||||||||||||||||||||||||||||||||
$16738 – $17430 | Misc Mappings | ||||||||||||||||||||||||||||||||||||
$17430 – $1F600 | Level Layout | ||||||||||||||||||||||||||||||||||||
$1F600 – $20000 | Sega Screen Art / Mappings | ||||||||||||||||||||||||||||||||||||
$20000 – $23440 | Sonic Art / Mappings | ||||||||||||||||||||||||||||||||||||
$23400 – $23450 | Palette Cycle Pointers:
| ||||||||||||||||||||||||||||||||||||
$23450 – $23C00 | Palettes | ||||||||||||||||||||||||||||||||||||
$23C00 – $25500 | 'Sega' sound | ||||||||||||||||||||||||||||||||||||
$25500 – $30000 | Art : Title Screen / Map / Levels / Stats / Sprites | ||||||||||||||||||||||||||||||||||||
$30000 – $40000 | Art : Sega Screen / Map / Levels | ||||||||||||||||||||||||||||||||||||
$3DA28 – $40000 | Contains sprite art and/or sprite mappings |
Compressed Data
RLE Compression
Some data (level layouts, misc. mappings) in the ROM is compressed using a form of Run-Length-Encoding, where bytes that repeat themselves many times in a row are reduced by specifying the number of times to repeat a byte.
In practice, the ROM stores this data normally byte-for-byte but indicates a value to repeat by a duplicate byte followed by another byte that specifies the number of successive bytes to repeat.
A bug / oversight made by the developers means that the byte that specifies the number of times to repeat is off-by-one (causing an overflow (255 → 0). This means that a repeating-value of 01 means zero repeats (therefore wasting space!), 02 means 1 repeat, FF means 255 repeats, but 00 actually means 256 repeats! Be keenly aware of this when de/compressing!
Example:
- 06 7C 32 2E 2E 01 D1 → 06 7C 32 2E 2E D1
- 6B 3F 3F 02 51 2D C0 → 6B 3F 3F 3F 51 2D C0
- 05 07 5A 5A 03 08 B2 → 05 07 5A 5A 5A 5A 08 B2
- 05 07 5A 5A 03 08 B2 → 05 07 5A 5A 5A 5A 08 B2
- 29 EF 00 00 00 BB D2 → 29 EF 00 00 […00x256…] BB D2
As you can see, this format wastes one byte of space if a byte is only repeated twice. If a byte is repeated three times, there is no size difference. Only when a byte is repeated four or more times is there a savings in space usage.
Art Compression
WARNING: Here comes the science bit! If you want to understand how this works then read very carefully. First, some background info: The Master System uses character-based graphics, that is, 8×8 pixel tiles arranged into a 32×24 grid. The screen is not drawn to directly, instead up to 448 tiles can be defined and images are crafted by arranging different tiles on the grid.
The graphics for a level consist of 256 tiles and sprite sets are 128 tiles. Each tile consists of 8 rows (of 8 pixels), each row is 4 bytes (more on that later). The graphic art is compressed in a very complex, but effective, manner. The rows of all the tiles are divided into unique rows and duplicate rows. The data is stored like this:
- Header (8-bytes)
- List of unique rows
- List of duplicate rows
- Art Data (the actual graphics)
Header
The 8-byte header is in the format of:
- FE FN DR DR AD AD X0 TY
(Note that dual-byte values "DR" and "AD" are Little-Endian, the lowest byte first. e.g. "08 01" = "0108")
- FE: "Forty-Eight". Unknown purpose, but in all headers this value is 48
- FN: "Fifty-Nine". Unknown purpose, but in all headers this value is 59
- DR: "Duplicate Rows". An offset from the start of the level art header, to the where the duplicate rows list begins. For tile sets this value is always "0108" (256 + 8 in hexadecimal). For sprite sets it's "0088" (128 + 8 in hexadecimal)
- AD: "Art Data". An offset, from the beginning of the level art header (e.g. $32FE6), to the start of the Art Data section. This is critically important because the length of the duplicate rows list can vary
- X0: Unknown, but in all headers, this value is "0"
- TY: "Type". 08 for tile sets, 04 for sprite sets. Could be something to do with the number of tiles (divided by 32) or with where in VRAM they go
Unique Rows List
The list of unique rows is one byte for each tile we are defining (256 for tile sets, 128 for sprite sets). To process this data begin with the first byte of the unique rows list. Each bit in this byte refers to a row in the first tile of the tile set that we are decompressing.
Note that bits in a byte are ordered right to left, as such:
Bit# | 8 | 7 | 6 | 5 | 4 | 3 | 2 | 1 |
---|---|---|---|---|---|---|---|---|
Value: | 1 | 1 | 0 | 1 | 0 | 0 | 1 | 1 |
Therefore bit #1 (on the right), refers to the first row of the current tile we are decoding and bit #8 (on the left) refers to the 8th row of the tile.
When a bit value is 0, it means that the tile row it corresponds to is a unique row. Read in 4 bytes from the Art Data section and decode into the 8 pixels for that row (see the Art Data heading below). In the example above, rows 3, 4 & 6 and of the tile are unique, and 4 bytes would be read from the Art Data for each.
Walk through the whole unique rows list decoding in this way and you should have a partial tile set with all the unique rows filled in.
Duplicate Rows List
The list of duplicate rows "fills in the blanks" in the rows missed by the unique list. For each row in the tile set that was missed by the unique rows list the duplicate rows list will contain an index value to where in the Art Data the row is.
Begin by walking the unique rows list again in the same order as before, but this time when a bit value is 1 it means that row is a duplicate: read a byte from the duplicate rows list. This value is an index to where in the art data the row is located, i.e. a value of 80 (hex) means:
$30000 base address (Master System) + 2FE6 "Level Art" pointer in the level header, Green Hill for example + 7C2 Art Data pointer in the level art header, again Green Hill + 80*4 Skip to the 128th, decimal, row in the art data
For values 00 to EF (0 to 239), there is only one byte, indicating the row index in the Art Data. However, for values after EF, there are two bytes. The first one starts with an F, so the actual line number is the two bytes number minus F0 00. E.g.: F3 A2 is for art data row number 3A2. Note that you can also write line numbers 00 to EF using two bytes numbers, but this is a waste of space (that's why they are stored with one byte!).
Once you've walked the unique rows list a second time, reading the duplicate row list for each bit-value of 1 you see, all the blank rows in the title set should be filled in and you should have a complete tile set — if you've understood everything correctly!
Art Data
The SMS uses a palette of 16 colours for tiles, therefore the data that defines the tile graphics do not specify the actual R/G/B values, but just an index (0-15) to the palette colour to use. Therefore an 8-pixel row is stored as 4 bytes, where 4 bits (values 0-15) are assigned to each pixel.
However, instead of being stored as nybbles (4-bits in a row), the data is stored across 4 bit-planes. To understand what bit-planes are, imagine 4 bytes stacked on top of each other like layers in a cake. A bit plane would be a slice of the cake — 1 bit from each of the 4 bytes.
To decode the 4 bytes into 8 colour pixels, slice the bit-planes to get the index values (0-15) for each pixel and then look up the final colour from the palette.
In psuedo code, something like this:
input byte1, byte2, byte3, byte4 pixel = array (0 to 7) for bit = 0 to 7 if byte1 AND 2 ^ (7-bit) then pixel[bit] = pixel[bit] OR 1 if byte2 AND 2 ^ (7-bit) then pixel[bit] = pixel[bit] OR 2 if byte3 AND 2 ^ (7-bit) then pixel[bit] = pixel[bit] OR 4 if byte4 AND 2 ^ (7-bit) then pixel[bit] = pixel[bit] OR 8 pixel[bit] = palette-color-from-index: pixel[bit] next bit
Level Headers / Level Headers Pointers
Each level has a header. This header contains several pieces of data, such as starting position, music location, etc. Each level header is 37 bytes long and is referenced by a pointer.
Level Headers Pointers
A level header pointer is comprised of two bytes. The data for the pointer is stored in little endian format. The value stored by this pointer specifies the number of bytes away a level header is from $15580 $15600.There are 37 Level Headers in total. Some levels have more than one pointer because they can be accessed from different locations, and Sonic's starting position differs at level start. Also two invalid level pointers exist that act as dividers between the main sequence of levels and the out-of-sequence levels (Scrap Brain's sub-maps and the Special Stages). See the ROM map for the full list of level pointers.
Example:
The two first bytes are 4A 00. So, at $15580 + $004A, we will find the level header for the first level (Green Hill 1).Level Headers
The level headers are located at $155CA – $15AB3 $1564A – $15B34.Each level header use 37 bytes. Here is the format (partial):
- SP TW TW TH TH ?? ?? LW LH ?? ?? ?? ??
- SX SY FL FL FS FS ML ML LA LA ?? SA SA
- IP ?? CC CP SL SL ?? UW ?? ?? MU
- SP (Solidity Pointer): Indicates what solidity data to use
- TW,TH (Tiles Wide, Tiles High): Rough level dimension, in other words how many tiles wide and high the level is (low byte is first)
- LW,LH (Level Width, Level Height): Real level dimensions (divided by 32), used to limit the view
- SX,SY (Start X, Start Y): Player starting position (divided by 32)
- FL (Floor Location): How many bytes away from $14000 the floor is located (Little Endian)
- FS (Floor Size): Floor data size, in bytes (Little Endian)
- ML (Mappings Location): How many bytes away from $10000 the mappings for this level are located (Little Endian)
- LA (Level Art): How many bytes away from $30000 the level art is located (Little Endian)
- SA (Sprite Art): How many bytes away from $24000 is the sprite art located (Little Endian)
- IP (Initial Palette): Indicates the number of the initial palette pointer to use, in the pointer order of appearance (so, indicates the palette)
- CC (Color Cycles): Indicates the number of color cycles for the level palette
- CP (Cyclic Palette): Indicates the number of the cyclic palette pointer to use, in the pointer order of appearance (so, indicates the palette)
- SL (Sprites Location): How many bytes away from $15580 $15600 the sprite layout is located (Little Endian)
- UW (Under Water flag): Controls the under-water effect (slow movement / water colour / drowning) in Labyrinth (80 is on, 00 is off). Appears to only affect Labyrinth, using this flag on other levels does not create the water effect so either it's hard-coded to Labyrinth or some other undocumented data controls it
- MU (Music):
- 00–05: Level Music
- 06: Title Music
- 08: Invincibility
- 09: Level Complete
- 0A: Dead
- 0B/0C/0D: Boss
- 0E: Credits
- 10: Bonus Stage
This is a table of the complete level headers for the Master System version: (all values are hexadecimal)
Name | SP | TW | TH | ?? | ?? | LW | LH | ?? | ?? | ?? | ?? | SX | SY | FL | FS | ML | LA | ?? | SA | IP | ?? | CC | CP | SL | ?? | UW | ?? | ?? | MU | ||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Green Hill Act 1 | 0 | 0100 | 0010 | 40 | 0 | C0 | 18 | 20 | 0 | 40 | 01 | 08 | 0B | 2DEA | 083E | 0000 | 2FE6 | 9 | 612A | 0 | A | 3 | 0 | 0534 | 04 | 0 | 20 | 0 | 0 | ||||||
Green Hill Act 2 | 0080 | 0020 | 01 | A0 | 0C | 01 | 0 | 40 | 03 | 02 | 03 | 3628 | 0661 | 0580 | 04 | 20 | |||||||||||||||||||
Green Hill Act 3 | 0080 | 0020 | 01 | 00 | 0A | E8 | 0 | 40 | 03 | 07 | 16 | 3C89 | 032D | 05C3 | 00 | 00 | |||||||||||||||||||
Bridge Act 1 | 1 | 0100 | 0010 | 01 | 0 | 00 | 1F | 01 | 0 | 40 | 01 | 03 | 0C | 7ED1 | 0694 | 0B80 | 4578 | 9 | 6C3D | 1 | 8 | 3 | 1 | 05D6 | 04 | 0 | 20 | 0 | 1 | ||||||
Bridge 2 | 0080 | 0020 | 0F | 01 | 0 | 40 | 03 | 02 | 1C | A2A8 | 0499 | 061C | 0C | 20 | |||||||||||||||||||||
Bridge 3 | 0080 | 0020 | 0F | 00 | 3 | 40 | 03 | 06 | 1B | B301 | 0140 | 0656 | 00 | 00 | |||||||||||||||||||||
Name | SP | TW | TH | ?? | ?? | LW | LH | ?? | ?? | ?? | ?? | SX | SY | FL | FS | ML | LA | ?? | SA | IP | ?? | CC | CP | SL | ?? | UW | ?? | ?? | MU | ||||||
Jungle Act 1 | 2 | 0100 | 0010 | 01 | 0 | 00 | 1F | 01 | 0 | 20 | 01 | 02 | 0B | 3FB6 | 0AAC | 1480 | 5B00 | 9 | 77CD | 2 | 5 | 3 | 2 | 066C | 04 | 0 | 20 | 0 | 2 | ||||||
Jungle Act 2 | 0010 | 0100 | 01 | 01 | 0 | 20 | 1F | 02 | FA | 4A62 | 08DB | 06C4 | 84 | 20 | |||||||||||||||||||||
Jungle Act 3 | 0080 | 0020 | 0F | 00 | 3 | 40 | 03 | 06 | 1B | B301 | 0140 | 0656 | 00 | 00 | |||||||||||||||||||||
Labyrinth Act 1 | 3 | 0040 | 0040 | 01 | 0 | 00 | 07 | 01 | 0 | 40 | 07 | 02 | 05 | 8565 | 08C2 | 1E80 | 71BF | 9 | 83B6 | 3 | 5 | 3 | 3 | 0723 | 04 | 80 | 20 | 0 | 3 | ||||||
Labyrinth Act 2 | 0040 | 0040 | 03 | 09 | 8E27 | 0D13 | 0772 | 04 | 20 | ||||||||||||||||||||||||||
Labyrinth Act 3 | 0040 | 0040 | 03 | 25 | AFF6 | 030B | 07CA | 00 | 10 | ||||||||||||||||||||||||||
Name | SP | TW | TH | ?? | ?? | LW | LH | ?? | ?? | ?? | ?? | SX | SY | FL | FS | ML | LA | ?? | SA | IP | ?? | CC | CP | SL | ?? | UW | ?? | ?? | MU | ||||||
Scrap Brain Act 1 | 4 | 0100 | 0010 | 01 | 0 | 00 | 1E | 01 | 0 | 20 | 01 | 03 | 0B | 533D | 069A | 2980 | 884B | 9 | 8F75 | 4 | 6 | 4 | 4 | 07E9 | 04 | 0 | 20 | 0 | 4 | ||||||
Scrap Brain Act 2 | 0080 | 0020 | 0F | 01 | 0 | 40 | 03 | 04 | 16 | 59D7 | 0904 | 082C | 20 | ||||||||||||||||||||||
Scrap Brain Act 3 | 0040 | 0040 | 07 | 20 | 2 | 40 | 07 | 03 | 36 | 7282 | 08B2 | 08CE | 00 | ||||||||||||||||||||||
Sky Base Act 1 | 5 | 0080 | 0020 | 01 | 0 | 00 | 0F | 01 | 0 | 40 | 03 | 02 | 1D | 9B3A | 076E | 3580 | 9CEE | 9 | 99E0 | 5 | 6 | 4 | 5 | 091A | 04 | 0 | 22 | 0 | 4 | ||||||
Sky Base Act 2 | 5 | 0040 | 0040 | 07 | 40 | 06 | 0A | 17 | 7B34 | 039D | 3580 | 9CEE | 5 | 6 | 8 | 0954 | 40 | 20 | 5 | ||||||||||||||||
Sky Base Act 3 | 7 | 0040 | 0040 | 07 | 20 | 01 | 02 | 01 | A741 | 04C0 | 4300 | B3B5 | 6 | 8 | 6 | 0997 | 00 | 00 | 4 | ||||||||||||||||
End Sequence | 0 | 0100 | 0010 | 40 | 1A | 00 | 1D | E0 | 0 | E8 | 00 | D9 | 0A | 2DEA | 083E | 0000 | 2FE6 | 9 | AEB1 | 0 | A | 3 | 0 | 0A3A | 00 | 0 | 00 | 0 | FF | ||||||
Name | SP | TW | TH | ?? | ?? | LW | LH | ?? | ?? | ?? | ?? | SX | SY | FL | FS | ML | LA | ?? | SA | IP | ?? | CC | CP | SL | ?? | UW | ?? | ?? | MU | ||||||
Scrap Brain Act 2 (Emerald Maze), From Corridor |
4 | 0040 | 0040 | 01 | 0 | 00 | 07 | 01 | 0 | 40 | 07 | 03 | 3D | 62DB | 08F8 | 2980 | 884B | 9 | 8F75 | 4 | 6 | 4 | 4 | 0869 | 04 | 0 | 20 | 0 | 4 | ||||||
Scrap Brain Act 2 (Ballhog Area) |
0020 | 0080 | 03 | A0 | 0A | 03 | 03 | 6BD3 | 06AF | 08B5 | |||||||||||||||||||||||||
Scrap Brain Act 2, From Transporter |
0080 | 0020 | 0F | 40 | 03 | 50 | 10 | 59D7 | 0904 | 082C | |||||||||||||||||||||||||
Scrap Brain Act 2 (Emerald Maze), From Transporter |
0040 | 0040 | 07 | 40 | 07 | 27 | 1C | 62DB | 08F8 | 0869 | |||||||||||||||||||||||||
Scrap Brain Act 2, From Emerald Maze |
0080 | 0020 | 0F | 40 | 03 | 7B | 03 | 59D7 | 0904 | 082C | |||||||||||||||||||||||||
Scrap Brain Act 2, From Ballhog Area |
0080 | 0020 | 0F | 40 | 03 | 7B | 1B | 59D7 | 0904 | 082C | |||||||||||||||||||||||||
Sky Base Act 2 (Interior) | 7 | 0040 | 0040 | 01 | 0 | 00 | 07 | 01 | 0 | 40 | 07 | 03 | 3B | A741 | 04C0 | 4300 | B3B5 | 9 | 99E0 | 6 | 8 | 4 | 6 | 09A1 | 00 | 0 | 00 | 0 | 4 | ||||||
Name | SP | TW | TH | ?? | ?? | LW | LH | ?? | ?? | ?? | ?? | SX | SY | FL | FS | ML | LA | ?? | SA | IP | ?? | CC | CP | SL | ?? | UW | ?? | ?? | MU | ||||||
Special Stage 1 | 6 | 0040 | 0040 | 01 | 0 | 00 | 07 | 01 | 0 | 40 | 02 | 02 | 06 | B441 | 0760 | 4890 | C7FE | 9 | A511 | 7 | 1 | 1 | 7 | 09A5 | 4 | 0 | 21 | 0 | 10 | ||||||
Special Stage 2 | 0040 | 0040 | 07 | 20 | 3 | C0 | 05 | 02 | 1E | B441 | 0760 | 09AC | |||||||||||||||||||||||
Special Stage 3 | 0040 | 0040 | 07 | 80 | 6 | 40 | 07 | 03 | 3B | B441 | 0760 | 09B6 | |||||||||||||||||||||||
Special Stage 4 | 0010 | 0100 | 01 | 01 | 0 | 20 | 1F | 06 | 40 | 4A62 | 08DB | 09C0 | |||||||||||||||||||||||
Special Stage 5 | 0040 | 0040 | 07 | 01 | 0 | 40 | 02 | 02 | 06 | B441 | 0760 | 09D3 | |||||||||||||||||||||||
Special Stage 6 | 0040 | 0040 | 07 | 20 | 3 | C0 | 05 | 02 | 1E | B441 | 0760 | 09E6 | |||||||||||||||||||||||
Special Stage 7 | 0040 | 0040 | 07 | 80 | 6 | 40 | 07 | 03 | 3B | B441 | 0760 | 09FF | |||||||||||||||||||||||
Special Stage 8 | 0010 | 0100 | 01 | 01 | 0 | 20 | 1F | 06 | 04 | 4A62 | 08DB | 0A15 |
Palettes
A palette of 32 colors is used, the first 16 reserved for the level and the second 16 for the sprites.
The Master System uses 6-bit colors, each colour in a palette is one byte (32 bytes for a full palette, 16 bytes for a half-palette). 2 bits are assigned to each color (R:0–2, G:0–2, B:0–2), for a total of 64 possible colors. The extra two bits in the byte are unused, therefore the format of the byte is: 00BBGGRR. The corresponding 24-bit color byte value for the 2-bit numbers are: 0 = 0, 1 = 80, 2 = 175, 3 = 255.
The Game Gear uses 9-bit colors, so each color use two bytes (the first nybble of the second byte is 0, and values for the color nybble are in steps of 2). This color can be defined like that : R(0–7), G(0–7), B(0–7). So, there are only 8 possible values for each primary color. Here are the RGB correspondence : 0/1 = 0, 2/3 = 36, 4/5 = 72, 6/7 = 109, 8/9 = 145, A/B = 182, C/D = 218, E/F = 255. So, you can have a maximum of 512 colors. The format for the two bytes is : GGGGRRRR 0000BBBB
Level Palettes
A table of Level Palette Pointers are located at: $0627C – $0628B $23440 – $23450. Each pointer (2 bytes, little-endian) in the table points to the beginning of a palette in the ROM. On the Master System, these pointers are absolute (give the actual ROM address), but on the Game Gear, are relative, specifying how many bytes from $23400 the palette can be found. Each level palette is a full-palette (Tiles and Sprites) of 32-colours. The level palettes are located at: $0629E – $065ED $23450 – $23C00. See the ROM map for a more detailed listing.The Initial Palette ("IP") value of a Level Header is an index to the level palette pointers, i.e. 0–7, specifying which palette to load.
Level Cycle Palettes
To create a simple animation effect, such as flowing water, the palettes are "cycled" through a list of other palettes allowing the colours to rapidly change without having to change actual pixel data.
A table of cycle palette pointers exists at $0628C – $0629D $23400 – $23450. Each pointer (2 bytes, little-endian) in the table points to the beginning of a cycle palette. Each cycle palette is a half-palette of 16 colours and the number of cycle palettes in a cycle is determined in the Level Header by the Cycle Count ("CC") value. The Cycle Palette ("CP") value in the Level Header is an index to the Cycle Palette Pointers table, determining which palette cycle to use.Note that the Level Palettes and Cycle Palettes are intermixed, which is why the pointer tables are necessary. See the ROM Map for a detailed listing of the palette locations.
Labyrinth's Underwater Palettes
Description pending
Sky Base Act 1 Lightning Palettes
Description pending
On-Demand Sprite Palettes
Description pending
Block Mappings
The floor layout for each level is comprised of "blocks": prearranged 4×4 tile (32×32 px) patterns. This reduces the amount of memory required for storing levels ("Floor Layouts") as levels are constructed out of these larger blocks rather than storing every tile seen.
Each block is composed of 16 smaller 8×8 px tiles. The block is 16 bytes, each byte is an index to which tile to display in the Level Art. The bytes are arranged on screen in this order:
And the corresponding data is:
- 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F
Block Mappings are stored uncompressed in the ROM. The number of blocks in each mapping is apparently not stored in the ROM, so to determine the number of blocks in each mapping you need to compare the distance between "Mapping Location" Level Headers. For your convenience the size of the mappings are charted below.
Master System Version
Offset | Description |
---|---|
$10000 – $10B80 | Green Hill (184 blocks) |
$10B80 – $11480 | Bridge (144 blocks) |
$11480 – $11E80 | Jungle (160 blocks) |
$11E80 – $12980 | Labyrinth (176 blocks) |
$12980 – $13580 | Scrap Brain (192 blocks) |
$13580 – $14300 | Sky Base 1-2 (216 blocks) |
$14300 – $14980 | Sky Base 3 (104 blocks) |
$14980 – $14C9F | Bonus Stage (50 blocks) |
Game Gear Version
Offset | Description |
---|---|
$10000 – $10BB0 | Green Hill (187 blocks) |
$10BB0 – $11510 | Bridge (150 blocks) |
$11510 – $11FE0 | Jungle (128 blocks) |
$11FE0 – $12A10 | Labyrinth (208 blocks) |
$12A10 – $135B0 | Scrap Brain (186 blocks) |
$135B0 – $14330 | Sky Base 1-2 (216 blocks) |
$14330 – $149B0 | Sky Base 3 (104 blocks) |
$149B0 – $14D00 | Bonus Stage (53 blocks) |
Floor Layout
The floor layout is composed of multiple 4×4 tile blocks (See Block Mappings). Each byte indicates the index of the tile to which to use. However, the data is compressed, so you will have to decompress it first.
Floor layouts are located at: $16DEA – $1FFFF $17430 – $1F600. You'll have to use the pointers (Level Headers), in order to determine their starting address.Sprite Layout
Sprites are special parts of a level. They can move, attack, give you rings, and do a lot of other things, even if they are not visible.
Sprite Layout Data begins with one byte, which is the total number of sprites in the zone plus one. Immediately following is the sprite data itself. Each sprite uses 3 bytes. Here is the format:
- OO XX YY
XX and YY are the object's coordinates divided by 32. OO is one of the object listed below. (Both the Game Gear and Master System versions share the same Sprite Layout Data)
ID | Description |
---|---|
00 | Empty (no object) |
01 | Super Ring monitor |
02 | Power Sneakers monitor |
03 | One-Up monitor |
04 | Shield monitor |
05 | Invincibility monitor |
06 | Chaos Emerald |
07 | End sign |
08 | Badnik "Crabmeat" (GH) |
09 | Wooden platform - Swinging (GH) |
0B | Wooden platform (GH) |
0C | Wooden platform - Falls when touched (GH) |
0E | Badnik "Buzz Bomber" (GH/B) |
0F | Wooden platform - Sliding left-right (GH) |
10 | Badnik "Moto Bug" (GH) |
11 | Badnik "Newtron" (GH) |
12 | Robotnik - Green Hill Boss (GH) |
16 | Flame Thrower (SB) |
17 | Door - Opens from left only (SB) |
18 | Door - Opens from right only (SB) |
19 | Door - Two ways (SB) |
1A | Electric sphere (SB) |
1B | Badnik "Ball Hog" (SB) |
1C | Unknown - Ball from the "Ball Hog" ? |
1D | Switch (SB, L, others ?) |
1E | Switch Activated Door (SB) |
1F | Badnik "Caterkiller" (SB) |
21 | Bumper - Sliding left-right (Bonus Stage ?) |
22 | Robotnik - Scrap Brain Boss (SB) |
23 | Free animal - Rabbit |
24 | Free animal - Bird |
25 | Animal Cell |
26 | Badnik "Chopper" (J, B) |
27 | Vertical Step - Falling from a waterfall (J) |
28 | Horizontal Step - Falling from a waterfall (J) |
29 | Floating Step - Sonic can travel with it (J) |
2C | Robotnik - Jungle Boss (J) |
2D | Badnik "Yadrin" (B) |
30 | Passing Clouds (SKYB) |
31 | Propeller (SKYB) |
32 | Badnik "Bomb" (SKYB) |
33 | Large Cannons in Sky Base Act 2 (SKYB) |
35 | Badnik "Unidus" (SKYB) |
37 | Rotating cannon (SKYB) |
38 | Flying platform (SKYB) |
39 | Spiked wall slowly moving right (SKYB) |
3A | Small cannon in Sky Base Act 1 (SKYB) |
3B | Flying platform moving up-down (SKYB) |
3C | Badnik "Jaws" (L) |
3D | Rotating spiked ball (L) |
3E | Spear, shifting up-down (L) |
3F | Fire ball thrower (L) |
40 | Water Level Object (L) |
41 | Bubble Maker (L) |
44 | Badnik "Burrobot" (L) |
45 | Platform, move up when touched (L) |
46 | Electrical Hazard for the Sky Base Boss (SKYB) |
48 | Robotnik - Bridge Boss (SB) |
49 | Robotnik - Labyrinth Boss (L) |
4A | Robotnik - Sky Base Boss (SKYB) |
4B | Zone that makes you fall (like in GH2) |
4C | Flipper (Bonus Stage) |
4D | Reset! |
4E | Balance (B) |
4F | Reset! |
50 | Flower (GH) |
51 | Box - Starpost |
52 | Box - Continue |
53 | Final animation in GH, when Sonic falls on Robotnik (then, goes to the next level) |
54 | Emeralds animation (on the map), when Sonic has them all (and goes to the next level) |
55 | Makes Sonic blink for a short time |
It seems that no more sprites are defined.
Sprite Layout Data Locations
You can use the Level Headers to determine where are the sprites located at. Or you can use this table.
Zone | Offset | Offset |
---|---|---|
Green Hill Act 1 | $15AB4 | $15B34 |
Green Hill Act 2 | $15B00 | $15B80 |
Green Hill Act 3 | $15B43 | $15BC3 |
Bridge Act 1 | $15B56 | $15BD6 |
Bridge Act 2 | $15B9C | $15C1C |
Bridge Act 3 | $15BD6 | $15C50 |
Jungle Act 1 | $15BEC | $15C66 |
Jungle Act 2 | $15C44 | $15CC1 |
Jungle Act 3 | $15C8D | $15D04 |
Labyrinth Act 1 | $15CA3 | $15D1A |
Labyrinth Act 2 | $15CF2 | $15D5A |
Labyrinth Act 3 | $15D4A | $15DB2 |
Scrap Brain Act 1 | $15D69 | $15DD1 |
Scrap Brain Act 2 | $15DAC | $15E20 |
Scrap Brain Act 2 (Emerald Maze) | $15DE9 | $15E60 |
Scrap Brain Act 2 (Ballhog Area) | $15E35 | $15EAC |
Scrap Brain Act 3 | $15E4E | $15ECE |
Sky Base Act 1 | $15E9A | $15F1A |
Sky Base Act 2 | $15ED4 | $15F54 |
Sky Base Act 2 (Interior) | $15F21 | $15FAD |
Sky Base Act 3 | $15F17 | $15FA3 |
Special Stage 1 | $15F26 | $15FB1 |
Special Stage 2 | $15F2C | $15FC1 |
Special Stage 3 | $15F36 | $15FCB |
Special Stage 4 | $15F40 | $15FD2 |
Special Stage 5 | $15F53 | $15FE5 |
Special Stage 6 | $15F66 | $15FFE |
Special Stage 7 | $15F7F | $16014 |
Special Stage 8 | $15F95 | $1602A |
Final "Cutscene" | $15FBA | $16046 |
Misc Mappings
This section contains the mappings for some screens. It looks like the Blocks Mappings, except that the 8×8 tiles are written to the screen, so there is more than 16 tiles. Another thing is that they are compressed (see The compression format).
Mappings Offset | Description |
---|---|
$16738 – $16865 | Title Screen |
$16962 – $163F6 | Map 1 Background |
$163F6 – $16AFD | Map 1 Foreground |
Blinking Items Art
In the game, there are some blinking items. The most common are the box items. You can easily edit them. Each of these items is 16×16, but you must understand that it is composed of four 8×8 tiles. The tiles are displayed from up to down and from left to right. The format is the same as the art in savestates (32 bytes for each 8×8 tile, 128 bytes for the item).
Blinking items are located at: $15180 – $1557F $15200 – $15600Here are the items you can edit :
ID | Description |
---|---|
1 | Super Rings |
2 | Power Sneakers |
3 | One-Up |
4 | Shield |
5 | Invincible |
6 | Chaos Emerald |
7 | Starpost (Checkpoint) |
8 | Continue |
Level Art
The level art starts at: $32FE6 $32ED5. The "Level Art" value in the [[#Level_Headers|Level Header] specifies how far from $30000 the level art for that zone begins. See the ROM Map for a full list of level art addresses.The graphics for a level consist of 256 tiles. Each tile consists of 8 rows (of 8 pixels). See the Art Compression section for how to fully read and decompress the tile graphics.
Game Text
Strings of text in the game are stored in a simple format that begins with an X / Y location on the screen to begin printing, are terminated with FF and may contain special control-codes, such as FE to move the cursor.
Note that the character codes used for the letters are dependent on the tile map currently being used! There are two tile maps used, one for each of the map screens in the game.
The first map screen shows the overview of the island and is used for the first three zones (Green Hill, Bridge & Jungle). These are the character codes used on this screen:
A | B | C | D | E | F | G | H | I | J | K | L | M | N | O | P | Q | R | S | T | U | V | W | X | Y | Z | © | ␣ |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
34 | 35 | 36 | 37 | 44 | 45 | 46 | 47 | 40 | 41 | 42 | 43 | 50 | 51 | 52 | 60 | 61 | 62 | 70 | 80 | 81 | 54 | 3C | 3D | 3E | 3F | CF | EB |
The second map screen shows the close-up of the mountain top with Robotnik's fortress, and uses the following character codes:
A | B | C | D | E | F | G | H | I | J | K | L | M | N | O | P | Q | R | S | T | U | V | W | X | Y | Z | © | ␣ |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
1E | 1F | 2E | 2F | 3E | 3F | 4E | 4F | 5E | 5F | 6E | 6F | 7E | 7F | 8E | 8F | 9E | 9F | AE | AF | BE | BF | CE | CF | DE | DF | AB | EB |
Zone Titles
The zone titles ("GREEN HILL", "BRIDGE", …) shown on the map screen are stored at $0122D – $01286. Each title is padded with spaces so that all titles are always 12 bytes long.The first three zones use the character codes from the first map screen, therefore the data looks like this:
Address | Bytes | Text |
---|---|---|
$0122D | 10 13 46 62 44 44 51 EB 47 40 43 43 EB EB FF | GREEN HILL |
$0123C | 10 13 35 62 40 37 46 44 EB EB EB EB EB EB FF | BRIDGE |
$0124B | 10 13 41 81 51 46 43 44 EB EB EB EB EB EB FF | JUNGLE |
The next three zones use the second map screen, therefore the letters appear differently:
Address | Bytes | Text |
---|---|---|
$0125A | 10 13 6F 1E 1F DE 9F 5E 7F AF 4F EB EB EB FF | LABYRINTH |
$01269 | 10 13 AE 2E 9F 1E 8F EB 1F 9F 1E 5E 7F EB FF | SCRAP BRAIN |
$01278 | 10 13 AE 6E DE EB 1F 1E AE 3E EB EB EB EB FF | SKY BASE |
Final Score Titles
Upon completion of the game, a final score screen is shown and bonuses are awarded for the number of emeralds, lives remaining and a "Special Bonus". These titles are stored at $0197E – $019AD.Each string is padded with spaces to be 13 characters in length. The first tile set is used.
Address | Bytes | Text |
---|---|---|
$0197E | 08 0A 36 47 34 61 70 EB 44 50 44 62 34 43 37 FF | CHAOS EMERALD |
$0198E | 08 0A 70 52 51 40 36 EB 43 44 45 80 EB EB EB FF | SONIC LEFT |
$0199E | 08 0A 70 60 44 36 40 34 43 EB 35 52 51 81 70 FF | SPECIAL BONUS |
Credits Text
The text for the credits that roll at the end of the game is stored at $02095 – $02AD5.Additional control codes appear in the credits:
- FE XX YY: Moves the cursor to XX, YY on the screen
- FD XX 00: Pauses for XX length. Values 3C, 4B & F0 are used in the credits roll
- FC XX: Number of lines to scroll the credits screen
Note that the credits use the second tile map.
Here is a full decode of the credits roll:
$02905 14 03 AE 9E 7F 5E 2E SONIC FE 15 04 AF 4F 3E THE FE 13 05 4F 3E 2F 4E 3E 4F 9E 4E HEDGEHOG FD 3C 00 FE 12 0C 7E 1E AE AF 3E 9F MASTER FE 13 0D AE DE AE AF 3E 7E SYSTEM FE 14 0E BF 3E 9F AE 5E 9E 7F VERSION FD 3C 00 FC 09 FE 14 0B AE 9E 7F 5E 2E SONIC FE 15 0C AF 4F 3E THE FE 13 0D 4F 3E 2F 4E 3E 4F 9E 4E HEDGEHOG FD 3C 00 FE 12 0F 8E 9F 5E 4E 5E 7F 1E 6F ORIGINAL FE 13 10 2E 4F 1E 9F 1E 2E AF 3E 9F CHARACTER FE 14 11 2F 3E AE 5E 4E 7F DESIGN FD 3C 00 FC 04 FE 14 10 AB AE 3E 4E 1E ©SEGA FD B4 00 FC 09 FE 14 0E AE AF 1E 3F 3F STAFF FD B4 00 FC 09 FE 12 0B 4E 1E 7E 3E GAME FE 13 0C 8F 9F 9E 4E 9F 1E 7E PROGRAM FD 3C 00 FE 13 0E AE 4F 5E 7F 9E 1F BE SHINOBU FE 14 0F 4F 1E DE 1E AE 4F 5E HYASHI FD F0 00 FC 09 FE 12 0B 4E 9F 1E 8F 4F 5E 2E GRAPHIC FE 14 0C 2F 3E AE 5E 4E 7F DESIGN FD 3C 00 FE 13 0E 1E DE 1E 7F 9E AYANO FE 14 0F 6E 9E AE 4F 5E 9F 9E KOSHIRO FD 3C 00 FE 13 11 AF 1E CF 3E 3F BE 7F 5E TAKEFUNI FE 14 12 DE BE 7F 9E BE 3E YUNOUE FD F0 00 FC 09 FE 12 0B AE 9E BE 7F 2F SOUND FE 13 0C 8F 9F 9E 2F BE 2E 3E PRODUCE FD 3C 00 FE 13 0E 7E 1E AE 1E AF 9E MASATO FE 14 0F 7F 1E CF 1E 7E BE 9F 1E NAKAMURA FD F0 00 FC 09 FE 12 0B 9F 3E 1E 9F 9F 1E 7F 4E 3E REARRANGE FE 15 0C 1E 7F 2F AND FE 12 0D 9E 9F 5E 4E 5E 7F 1E 6F ORIGINAL FE 16 0E 7E BE AE 5E 2E MUSIC FD 3C 00 FE 13 10 DE BE DF 9E YUZO FE 14 11 6E 9E AE 4F 5E 9F 9E KOSHIRO FD F0 00 FC 09 FE 13 0D AE 8F 3E 2E 5E 1E 6F SPECIAL FE 15 0E AF 4F 1E 7F 6E AE THANKS FD B4 00 FC 02 FE 13 0E DE 8E AE 4F 5E 8E EB DE YOSHIO Y FD 3C 00 FE 13 11 6F BE 7F 1E 9F 5E 1E 7F LUNARIAN FE 1A 12 AE 4E SG FD B4 00 FC 09 FE 12 0C 8F 9F 3E AE 3E 7F AF 3E 2F PRESENTED FE 16 0E 1F DE BY FE 15 10 AE 3E 4E 1E SEGA FD B4 00 FE 19 13 3E 7F 2F END $02AD5 FF
RAM Editing
To convert offset values to Gens Plus 0.0.9.61 savestate values, add $00A4.
Offset | Description |
---|---|
$0000 | Tile Layout Data |
$1400 | Object Status Table (?) |
$1403 | Sonic's X speed |
$1406 | Sonic's Y speed |
$202C | Palette |
$206C | Tile Graphics Data |
Tile Layout Data
Unlike in the ROM, the data here is uncompressed. Each byte directly corresponds to one 32×32 tile.
The number of tiles in a horizontal line before they wrap around differs depending on the width of the Zone. Here is table of the values.
Zone | Tile Line Data Size in Bytes |
---|---|
Green Hill Act 1 | 256 |
Green Hill Act 2 | 128 |
Green Hill Act 3 | 128 |
Bridge Act 1 | 256 |
Bridge Act 2 | 128 |
Bridge Act 3 | 128 |
Jungle Act 1 | 256 |
Jungle Act 2 | 16 |
Jungle Act 3 | 64 |
Labyrinth Act 1 | 64 |
Labyrinth Act 2 | 64 |
Labyrinth Act 3 | 64 |
Scrap Brain Act 1 | 256 |
Scrap Brain Act 2 | 128 |
Scrap Brain Act 2 (Emerald Maze) | 64 |
Scrap Brain Act 2 (Ballhog Area) | 32 |
Scrap Brain Act 3 | 64 |
Sky Base Act 1 | 128 |
Sky Base Act 2 | 64 |
Sky Base Act 2 (Interior) | 64 |
Sky Base Act 3 | 64 |
Music Hacking
Music Locations
- Music Pointers (These add to $8000): $C716
- Specifics...
Song ID | Location (SMS) | Location (GG) | Song |
---|---|---|---|
00 | C7D0 | C7D0 | Green Hill Zone |
01 | D74A | D74A | Bridge Zone |
02 | D24A | D24A | Jungle Zone |
03 | F60C | F60C | Labyrinth Zone |
04 | DB4F | DB4F | Scrap Brain Zone |
05 | E1A7 | E1A7 | Sky Base Zone |
06 | E4C3 | E4C3 | Title Screen |
07 | E63C | E63C | Map Screen (Act Intro) |
08 | E704 | E704 | Invincible |
09 | E8B4 | E8B4 | Act Complete |
0A | E991 | E991 | Death |
0B | EAC0 | EAC0 | Boss Theme |
0C | EAC0 | EAC0 | Boss Theme |
0D | EAC0 | EAC0 | Boss Theme |
0E | ED54 | ED54 | Ending |
0F | C7D0 | C7D0 | Green Hill Zone |
10 | F12C | F12C | Bonus Zone |
11 | C7D0 | C7D0 | Green Hill Zone |
12 | C7D0 | C7D0 | Green Hill Zone |
13 | F98C | F98C | Unused (some SFX) |
14 | FA26 | FA32 | Chaos Emerald |
The only difference in the music section of the SMS and GG version is, that the GG version of song 13 has an additional 83 (vibrato) command.
Song Format
All pointers in a song are absolute (i.e. relative to the beginning of the song) 16-bit pointers stored in Little Endian (Intel) format.
Song Header
Offset | Size | Description |
---|---|---|
00 | Word | Pointer to Channel 1 Data (usually points to 000A) |
02 | Word | Pointer to Channel 2 Data |
04 | Word | Pointer to Channel 3 Data |
06 | Word | Pointer to Channel 4/Noise Data |
08 | Word | unused (always zero) |
Channel Data
There's no header for channel data. Channel setup is done via commands.
The commands start directly at the offset specified in the header.
Command | Description |
---|---|
00–7F xx | Play Note with length xx
|
80 aaaa bbbb | Set song tempo (only present in channel 1)
|
81 aa | Set volume (0F = max, 00 = min) |
82 aa bb cc dd ee ff | Envelope Setup (only present in channels 1-3)
|
83 aa bb cc dd ee | Vibrato/Pitch Bend (only present in channels 1-3)
|
84 aaaa | Set Detune value to aaaa (aaaa is a signed byte that modifies the FNum)
|
85 aa | Unknown (only present in channel 1)
|
86 | Loop Start Marker
|
87 aa bbbb | Loop back
|
88 | Master Loop Start
|
8A aa | Set default note length to aa |
8B | Increase volume by 1 |
8C | Decrease volume by 1 |
8D | no attack for next note |
FF | Track End
|
Note on 86/87
The 86 command is used the make nested loops possible.
Example: 86 86 ... 87 04 aaaa ... 87 02 bbbb
Note on 88/FF
There's no need for an 88 command in non-looping songs.
However every jingle (with exception of the Death-Jingle) has a master loop, consisting of a rest.
Sonic the Hedgehog (8-bit) | |
---|---|
Manuals |
show;hide
|