Internal ROM Header

Internal ROM Header (or IRH) is a string of 64 bytes containing the game’s metadata. Because vanilla Super Mario World is LoROM, its IRH is located at byte £007FC0 and ends at £007FE0. This game uses IRH Ver. 1.

Contents of IRH

Location Data Length [bytes] Value in vanilla SMW (US)
£007FC0 Internal ROM Name 21 "SUPER MARIOWORLD     "
£007FD5 Map Mode 1 F016 (LoROM)
£007FD6 Cartridge Type 1 0216 (ROM + SRAM + Battery)
£007FD7 ROM Size 1 0916 (512 kB)
£007FD8 SRAM Size 1 0116 (2 kB)
£007FD9 Region/Destination Code 1 0116 (North America)
£007FDA Developer ID 1 0116 (Nintendo)
£007FDB Version Number 1 0016 (1.0)
£007FDC Checksum Complement 2 5F2516
£007FDE Checksum 2 A0DA16

The remaining 32 bytes contain the interrupt vectors which are outside the scope of this page.

Data format

This section explains what each piece of the IRH is and how it is interpreted.

Internal ROM name

Fixed size ASCII string: each of the 21 bytes is interpreted as a single ASCII character. Only values between 2016 and 7F16 are allowed in this string, meaning that the special ASCII characters are not supported.

Map mode

This byte can be represented as bits: 001F0HLh2

Where each letter corresponds to a flag:

Flag Value Description
F 0
1
Regular speed
High speed
H 0
1
Non-ExHiROM
ExHiROM
L 0
1
Non-ExLoROM
ExLoROM
h 0
1
LoROM
HiROM
Note: only one or none of the last 3 bits (H, L, and h) may be set at the same time. The F bit may be set or unset regardless of the values of other bits. This yields the following range of values:
  • 001000002 (LoROM)
  • 001000012 (HiROM)
  • 001000102 (ExLoROM)
  • 001001002 (ExHiROM)
  • 001100002 (Fast LoROM)
  • 001100012 (Fast HiROM)
  • 001100102 (Fast ExLoROM)
  • 001101002 (Fast ExHiROM)

Cartridge type

This byte can be represented as a pair nibbles: XP.

The P nibble states what memory chips are used by the game cartridge:

Values of P Memory chips
0 or 3 ROM
1 or 4 ROM + SRAM
2 or 5 ROM + SRAM + Battery
6 ROM + Battery

If P has a value greater than 2, it means that the cartridge uses the expansion chip specified by nibble X:

Values of X Expansion chip
016 DSP
116 SuperFX
216 OBC-1
316 SA1
416 S-DD1
516 S-RTC
E16 Other
F16 Custom

ROM size

The actual size of the ROM equals 2nKiB, where n is the value of this byte.

SRAM size

If this byte equals 0, the size of SRAM is also 0. Otherwise, the actual size of SRAM equals 2nKiB, where n is the value of this byte.

Region/destination code

Just an enumeration of numbers corresponding to certain regions.

Value Region
0016 Japan
0116 Most of North America
0216 Most of Europe
0316 Sweden
0416 Finland
0516 Denmark
0616 France
0716 The Netherlands
0816 Spain
0916 Germany
0A16 Italy
0B16 China
0C16 Indonesia
0D16 South Korea
0E16 Global
0F16 Canada
1016 Brazil
1116 Australia
1216 Other (1)
1316 Other (2)
1416 Other (3)

Developer ID

A number assigned to each developer.

Nintendo’s ID is 1.

Version number

This byte is the minor version number: the major version number is always assumed to be 1. For example, if this byte is 0, the full version number is 1.0.

Checksum & complement check

The checksum is calculated by adding the values of every single byte in the ROM and keeping the 2 least significant bytes of the result. Because the checksum itself is also used in this calculation, it comes together with a complement check equal to ¬checksum, ensuring that they always add up to the same value:

checksum + complement = 1FE₁₆

Checksum and complement check are used by SNES for validating the ROM. Bitwise XOR of the checksum and its complement check is always equal to FFFF16.

This can be used to find the location of the IRH and deduce the mapping mode from that:

  • If readw(£007FDC) ^ readw(£007FDE) = FFFF16, it means that the IRH is at £007FC0 and we’re in LoROM.
  • If readw(£00FFDC) ^ readw(£00FFDE) = FFFF16, it means that the IRH is at £00FFC0 and we’re in HiROM.

Acknowledgments

Information in the Data format section is based on this video by Retro Game Mechanics Explained. Thank you!