(Link to AcmlmWiki) Offline: thank ||bass
Register | Login
Views: 13,040,846
Main | Memberlist | Active users | Calendar | Chat | Online users
Ranks | FAQ | ACS | Stats | Color Chart | Search | Photo album
04-29-24 10:34 AM
0 users currently in ROM Hacking.
Acmlm's Board - I3 Archive - ROM Hacking - SMB1 Map Data and Addressing (Long) New poll | |
Add to favorites | Next newer thread | Next older thread
User Post
QBRADQ

Goomba


 





Since: 01-18-06
From: Eastern Oklahoma

Last post: 6630 days
Last view: 6630 days
Posted on 02-02-06 05:57 PM Link | Quote
Welp, it looks like I'm going to be leaving SMB1 alone for a while. Too much real life (and SMW) getting in the way. So, I figured I'd share with you all what I've figured out about SMB1's map data and how it gets addressed.

Ok, I realize this is quite long (and unfinished). If you're already familiar with SMB1 map hacking, then you can probly skip down to section 5. The main thing this document brings to the table that has been a mystery in the past is how the map address tables are indexed. In his document, Dahrk Daiz leaves only the addressing in the dark. Basicaly this document fills in the gaps.

Hope you all enjoy! Also, how would I go about submitting this to acmlm.org when I get around to finishing it?

WOW! The forum really did a number on the HTML OpenOffice generated :D I'll try to figure something out...

EDIT: Here's a link to a MS 97-XP .doc file. Much easier on the eyes. It's Geocities though...
Can't read a DOC? Tired of MS Office? OpenOffice.Org is the answer :D

SMB1MapData.txt


by
QBRADQ





This
document describes in detail the addressing scheme used by SMB1's map
data. Further information is provided on various other map-related
topics. To seek to a specific section, do a find operation for the
string "S-X" where X is the section number, or "S-X-Y"

where X is the section number, and Y is the subsection letter.








S-1
Index



  1. Index


  2. Terminology


  3. Map
    Data Composition



  4. Map
    Numbering



    1. Level
      Progression Table


    2. World-Level
      Offset Table


    3. The
      Map "Number"




  5. Map
    Addressing



    1. Map
      Type Offset Tables


    2. Data
      Address Tables


    3. Notes
      about Addressing



    4. Address
      Table Memory Map


    5. Address
      Table Data


    6. Map
      Data Memory Map














S-2
Terminology


Before
we begin, I'd like to define a few terms that I will be using
throughout this document. First, we will cover some of the landmark
events in game, which will help us to further define sections of the
game itself in the next section of definitions. Finally, I'll cover a
few map-specific terms.





Basic
Terms





SMB1



This
is the common abbreviation for Super Mario Brothers 1. Sometimes it's
shortened to just SMB, and sometimes people call it Mario 1, but SMB1
is usually how the game is referred to in the ROM hacking community.





Mushroom
Retainer


These
are those toad-stool lookin' guys in castles 1-7. You know, the ones
that say, "Thank you Mario, but our princess is in another
castle".





The
Princess


This
is the nice lady in pink that you save at the end of level 8-4.






Warp
Pipe


These
are those big pipes that you can go down into, which lead to bonus
areas. A good example is the fourth pipe in 1-1, or the first pipe in
1-2.





Warp-Zone
Pipe


A
Warp-Zone Pipe is a pipe that takes you to the start of another
world. Examples (the only examples) are past the end of 1-2, past the
end of 4-2, and up the bean tree in 4-2.









Game
Sections





Level


A
level is simply all the game play between jumping onto flagpoles,
saving the Princess or a Mushroom Retainer, or going through a
warp-zone pipe. It doesn't matter how many different maps you have to
go through to reach a flag pole or any other level ending event, as
long as the top of the screen still says "1-1" (or what
ever it said at the beginning of the level), it's still only one
level.


This
is a point that I like to stress to people, mainly because my SMB1
hack is going to be displaying this principle. Anyway, just keep that
in mind.






Map


A
Map is any
continuous
section of level data. Basically, if you got to where you are by
running to the right, you are still on the same map. If you took a
warp pipe, a warp-zone pipe, a bean tree, a fall out of the clouds,
or anything else that didn't involve running to the right, you are on
a different map.


Again,
this is something I like to stress, and for the same reason as the
above.





World


A
World is all the game play between saving Mushroom Retainers or the
Princess, or going into a warp-zone pipe.






Map
Terms





Castle
(Map Type)


The
castle map type is only found in the last level of each world in the
original game. It's where the bricks are black and white, and there
are typically a lot of fire arms.





Ground
(Map Type)


Sometimes
referred to as Above Ground, this map type is the most common in the
game. It's what 1-1 is, with the hills, brown ground, etc.






Underground
(Map Type)


Underground
maps are typically used as bonus levels accessible through warp
pipes. Although underground maps are not used as levels much in the
original (just 1-2 and 4-2), they are very recognizable by their blue
bricks and Goombas.





Underwater
(Map Type)


Even
less used than the underground map type for levels, the only
underwater level in the entire game is 2-2/7-2 (same map repeated
with more enemies). Only having three maps of this type in the entire
game (2-2/7-2, the 5-3 bonus area, and the 8-4 underwater section),
some people never know what this is.


Basically,
all the bricks are green, there is hot-pink sea weed everywhere,
visually impaired fish, squid that want to make love to your head,
pits of doom that try to suck you under, and waves that never move.
Mario swims of course, and he can even still shoot fireballs!












S-3
Map Data Composition



Map data
in SMB1 is split between two different types of data, object (OBJ)
data and monster (MOB) data. These two data sets, when read together,
form an entire map.



Each map's
data is segmented into pages. A page is basically everything that can
fit on one screen. Pages are delimited by objects or monsters that
have the “new page flag�? bit set. When the game
encounters such an object or monster, it assumes that the object or
monster in question is the first to appear on the next page to the
right.




Finally,
the actual object and monster data for a given map are split into
separate data segments, which are stored in separate locations in the
ROM. The object data segments end with a 0xFD byte, and the monster
data segments end with a 0xFF byte.














S-4
Map Numbering



Each map
is referenced by a unique number. These numbers index a table of
addresses (covered in the next section) that tell the game where to
find the data for that map. Furthermore, the game keeps a table of
what map to load at the start of any given level, known as the Level
Progression Table. Finally, the game also keeps track of what map to
load at the start of each world in the World-Level Offset Table,
which is used to index the Level Progression Table.







S-4-A
Level Progression Table



The level
progression table is a 36 byte long array of data beginning at 0x1CCC
in ROM containing the number of each map to load at the start of a
given level. Note that there are only 32 levels in the game, yet this
table is 36 bytes long. This is because the intermission levels, or
rather the intermission level
(0x29)
is also indexed here. An example of this intermission
level is between 1-1 and 1-2, when Mario walks out of the small
castle and into the pipe.























Level
Progression Table (HEX)


























































































Lv. 1 (1)



Lv. 2 (I)



Lv. 3 (2)




Lv. 4 (3)



None (Lv. 4)




World Number



25




29



C0



26




60



World 1



28



29




01



27



62




World 2



24




35



20




63



-



World 3




22



29




41



2C




61



World 4




2A



31



26




62



-




World 5



2E




23



2D



60




-



World 6



33



29




01



27



64




World 7



30




32



21




65



-



World 8





Numbers
in parenthesis indicate the level number in a world without an
intermission level.







S-4-B
World-Level Offset Table



The
World-Level Offset Table is an eight byte long array of data starting
at 0x1CC4 in ROM containing offsets into the Level Progression Table
for the start of a given world. The game thus reads the map number
for the start of any given level in this way:








worldofs =
WorldLevelOffsetTable[CurrentWorldNum]



mapnum =
LevelProgressionTable[worldofs]











World-Level
Offset Table (HEX)


































































Value



World




00



World
1



05



World
2



0A



World
3



0E



World
4



13



World
5



17



World
6



1B



World
7



20



World
8






















S-4-C
The Map “Number�?




This term
is deceptive really. The map “numbers�? held in the level
progression table as well as those map numbers appearing in map
change objects are not really just numbers given to the maps. Rather,
they are a code describing what type of map is being dealt with and
how many maps of that type come before the current one in the address
tables.



OK, I know
that was a bit confusing, but it will all make sense in the next
section. For now, have a look at the following table.












The Map
“Number�? Breakdown



































Bit
#




7



6




5



4



3




2



1




0



Desc




Unused



Map
Type Code


00 =
Underwater


01 =
Ground


10 =
Underground



11 =
Castle



Actual
Map Number









As
you can see from the above table, two bits are used to indicate the
map's type, five are used for the map's number, and one bit goes
unused (as far as I can tell). This gives us a total maximum of 4 map
types (cloud world is not considered a map type, apparently), and a
maximum of 32 maps of each type. However, it is important to note
that the map type codes that are embedded into the map number have no
effect on the game play, only on how the game looks up the map's
address in the address tables (see next section).















S-5
Map Addressing




OK, here's
the real meat and potatoes of the whole thing. As we stated earlier,
each map's data is broken up into an object data section and a
monster data section. Each data section's address is stored in
separate tables that the game references on loading. There are four
address tables in total, referencing the low-byte and high-byte of
both the object data and monster data for a given map. Furthermore,
there are two additional tables used to tell the game where addresses
of a given map type begin in both the object- and monster-related
address tables.







S-5-A
Map Type Offset Tables



When
referencing the addresses of a given map's data, the game first
indexes the Map Type Offset Tables for both the object data and
monster data address tables. Then, the map's actual number (the lower
five bits of the map number) is added to the map type offset for the
given data set. This is used to index both the low byte address table
and high byte address table for the given data type (object or
monster). The basic procedure is as follows:








l5b = MapNumber &
0x1F (Lower Five Bits of the Map Number)



maptype = MapNumber
& 0x60 >> 5 (Bits 5 and 6 only)







mapobjofs =
MapObjOffsetTable[maptype]




mapobjLowByte =
MapObjectLowByteTable[mapobjofs + l5b]



mapobjHighByte =
MapObjectHighByteTable[mapobjofs + l5b]







mapmobofs =
MapMobOffsetTable[maptype]



mapmobLowByte =
MapMobLowByteTable[mapmobofs + l5b]



mapmobHighByte =
MapMobHighByteTable[mapmobofs + l5b]
















S-4-B
Data Address Tables



The map
data address tables (all four) are 34 bytes in length. Each entry is
one byte of an address for a particular map's data set. The Map
Object Low Byte Table contains the low byte of the address for the
object data of a map, and the Map Object High Byte Table contains the
high byte of the address for the object data of a map. The same is
true with the Map Monster Low Byte Table and the Map Monster High
Byte Table.




By storing
these two bytes into RAM, the game may then address the data of the
maps via indirect addressing. The following table shows where these
address bytes are stored in RAM.







Map Data
Address RAM Map (HEX)





































RAM
Address




Contents



0xE7




Map
Object Low Byte



0xE8




Map
Object High Byte



0xE9




Map
Monster Low Byte



0xEA




Map
Monster High Byte










See
S-5-C for notes about the above



address
RAM registers
















S-5-C
Notes about Addressing



The
original SMB1 code reads the map data on-the-fly as the various
objects of the map are presented to the player. It accomplishes this
by reading in all objects and monsters within the first page of a map
at load time, plus the first object and monster of the next page.
Then, when ever the last object or monster to be loaded becomes
visible to the player, the next object or monster is loaded. The game
keeps track of where it is at in the level data by updating offset
variables, and applying them to the addresses found in 0xE7-0xEA.
This gives us a total addressing space for a map of 256 bytes.



However,
when the map is first loaded, its header is first read before passing
control onto the map data reading routines. When the header is read
in (two bytes in size), the object data address's low byte (0xE7)
gets incremented by two. However, there is not a carry check
preformed when this is done. What this means is, if a map's header
were to fall within two bytes short of an eight-byte addressing
boundary, (0xXXFE or 0xXXFF), the low byte address would roll over,
and the high byte address would be unaffected. This would result in
the map address being off by 255 to 256 bytes.



This is a
flaw in the game code, but because none of the object map data sets
happen to fall at such a memory location, this flaw was never
manifest as a bug in the original game. However, anyone reorganizing
the map data and address tables should be aware of this flaw, and
take appropriate action to make sure the bug is never manifest.



QBRADQ


(edited by QBRADQ on 02-02-06 05:07 PM)
insectduel

Lantern Ghost
Not welcome here anymore.








Since: 11-18-05
From: Bronx, New York

Last post: 6522 days
Last view: 6317 days
Posted on 02-03-06 02:43 PM Link | Quote
Damn it, thats a lot but can you put it in a HTML format so I can upload it from my webpage.

EDIT: It is on Insectduel's Domain. I think I rather collect all SMB and SMB2J data.


(edited by insectduel on 02-03-06 01:52 PM)
Add to favorites | Next newer thread | Next older thread
Acmlm's Board - I3 Archive - ROM Hacking - SMB1 Map Data and Addressing (Long) |


ABII

Acmlmboard 1.92.999, 9/17/2006
©2000-2006 Acmlm, Emuz, Blades, Xkeeper

Page rendered in 0.033 seconds; used 439.88 kB (max 791.31 kB)