NSF
NSF is the NES Sound Format used for storing and playing music from the NES and related systems. It is similar to the PSID file format for C64 music/sound, in that the basic idea is one rips the music/sound code from an NES game and prepends a small header to the data.
An NSF player takes this data and loads it into the prepares it properly on real hardware or an emulator, then uses it to play the tune.
Header Overview
offset # of bytes Function ---------------------------- $000 5 STRING 'N','E','S','M',$1A (denotes an NES sound format file) $005 1 BYTE Version number (currently $01) $006 1 BYTE Total songs (1=1 song, 2=2 songs, etc) $007 1 BYTE Starting song (1=1st song, 2=2nd song, etc) $008 2 WORD (lo, hi) load address of data ($8000-FFFF) $00A 2 WORD (lo, hi) init address of data ($8000-FFFF) $00C 2 WORD (lo, hi) play address of data ($8000-FFFF) $00E 32 STRING The name of the song, null terminated $02E 32 STRING The artist, if known, null terminated $04E 32 STRING The copyright holder, null terminated $06E 2 WORD (lo, hi) Play speed, in 1/1000000th sec ticks, NTSC (see text) $070 8 BYTE Bankswitch Init Values (see text, and FDS section) $078 2 WORD (lo, hi) Play speed, in 1/1000000th sec ticks, PAL (see text) $07A 1 BYTE PAL/NTSC bits, like NES 2.0 byte 12 bit 0: if clear, this is an NTSC tune bit 0: if set, this is a PAL tune bit 1: if set, this is a dual PAL/NTSC tune bits 2-7: not used. they *must* be 0 $07B 1 BYTE Extra Sound Chip Support bit 0: if set, this song uses VRC6 audio bit 1: if set, this song uses VRC7 audio bit 2: if set, this song uses FDS audio bit 3: if set, this song uses MMC5 audio bit 4: if set, this song uses Namco 163 audio bit 5: if set, this song uses Sunsoft 5B audio bits 6,7: future expansion: they *must* be 0 $07C 4 ---- 4 extra bytes for expansion (must be $00) $080 nnn ---- The music program/data follows until end of file
Loading a tune into RAM
If file offsets $070 to $077 have $00 in them, then bank switching is not used. Data should be read from the file beginning at $080 and loaded contiguously into the 6502 address space beginning at the load address until the end of file is reached.
Bank Switching
If any of the bytes from $070 to $077 in the file header are nonzero then bank switching is used. In this case, take the logical AND of the load address with $0FFF, and the result specifies the number of bytes of padding at the start of the ROM image. The ROM image should consist of a contiguous set of 4k banks, read directly from the NSF file beginning at $080 after inserting the requested number of pad bytes. If the file does not have enough data to fill the last bank completely, it may be padded out.
The 6502's address space is divided into 8 4k bank switchable blocks. For each block the current bank is controlled by writing the bank number to at corresponding register at $5FF8 through $5FFF. The initial bank assignment is determined by bytes $070 through $077 in the file.
NSF Address Register ==== ========== ======== $070 $8000-8FFF $5FF8 $071 $9000-9FFF $5FF9 $072 $A000-AFFF $5FFA $073 $B000-BFFF $5FFB $074 $C000-CFFF $5FFC $075 $D000-DFFF $5FFD $076 $E000-EFFF $5FFE $077 $F000-FFFF $5FFF
The initial bank assignment should be done before any call to the init routine. Once the ROM image has been built from the NSF file, this can be set up simply by writing the 8 values from the file header $070-077 to the corresponding registers $5FF8-$5FFF.
If the init routine needs to change the bank assignments based on the selected song, it may do so by writing the bank control registers.
FDS Bankswitching
If the FDS expansion is enabled, bank switching operates slightly differently. Two additional registers at $5FF6 and $5FF7 control the banks $6000-6FFF and $7000-7FFF respectively, and the initial load values at $076 and $077 now specify the banks used for $6000-7FFF as well as $E000-FFFF (these regions will both be set up to use the same banks before init is called).
Because the FDS has a RAM area at $8000-DFFF for the disk image to be loaded to, that means this area is writable when the FDS expansion is enabled. Most NSF player implementations will treat this like bankswitched RAM, meaning writes to this area will persist in the bank written to if it is switched out then switched back in. This does not affect FDS game rips, which do not bankswitch mid-song, but will affect modern NSFs which use bankswitching with the FDS expansion sound. Writes may or may not persist between songs, depending on whether the NSF player will reload the NSF image when the song is changed, so the NSF code should be careful not to rely on this.
See also the notes on multi-chip tunes below.
Example
METROID.NSF will be used for the following explanation.
The file is set up like so: (starting at $070 in the file) $070: 05 05 05 05 05 05 05 05 $078: 00 00 00 00 00 00 00 00 $080: ... music data goes here...
Since $070-$077 are something other than $00, this NSF is using bank switching. The load address given is $8000. The load address AND $0FFF specifies 0 bytes of padding, so we set up our ROM image with contiguous data starting from $080 in the file.
This NSF has 6 4k banks in it, numbered 0 through 5. It specifies that each of the 8 memory regions should be switched to bank 5, which begins at $05 * $1000 bytes in the ROM image.
Initializing a tune
The desired song number is loaded into the accumulator register A, and the X register is set to specify specify PAL (X=1) or NTSC (X=0).
Valid song numbers are 0 to one less than the number of songs (specified at $006 in the header). The first selected song is in the header at $007. The NSF player should display to the user song numbers from 1 up to and including the number of songs, and these should correspond to the same number - 1 loaded into register A. Note that when choosing the first song from the value in $007, subtract 1 from it before loading that value into register A.
- Write $00 to all RAM at $0000-$07FF and $6000-$7FFF.
- Initialize the sound registers by writing $00 to $4000-$4013, $0F to $4015.
- Initialize the frame counter to 4-step mode ($40 to $4017).
- If the tune is bank switched, load the bank values from $070-$077 into $5FF8-$5FFF.
- Set the A register for the desired song.
- Set the X register for PAL or NTSC.
- Call the music init routine.
The init routine MUST finish with an RTS instruction before music playback will begin. At this point, the NSF player will begin executing the play routine at the specified interval.
If this is a single standard tune (PAL or NTSC but not both) the init routine MAY ignore the X register. Otherwise, it SHOULD use this value to determine how to set pitches and tempo for the appropriate platform.
The use of the $4017 register is not well supported by existing NSF players. The NSF should never clear bit 6 (the IRQ disable bit), as the specification does not allow IRQ handling by the NSF. Writing to $4017 may cause problems for some hardware NSF players.
Playing a tune
Once the tune has been initialized, it can now be played. To do this, simply call the routine at the play address at the rate determined by the file header at $06E-06F (NTSC) or $078-079 (PAL).
The playback rate is determined by this formula:
1000000 1000000 rate = --------- period = --------- period speed
Where period is the value you place at $06E-$06F in the file, and rate is how often the play routine should be called in Hz.
The following playback rates are common:
- 60.002 Hz (recommended by the original NSF specification, close to APU timer IRQ rate): 16666 ($411A)
- 60.099 Hz (actual NTSC NES frame rate): 16640 ($4100)
- 50.007 Hz (suggested PAL NES frame rate): 19997 ($4E1D)
Nonstandard rates may be difficult for hardware players. If the rate is much faster the play routine may not be short enough to execute in the specified amount of time. Additionally, an NES player will usually require mapper hardware to create an IRQ to execute the play routine at the required rate.
The play routine will be called at the specified interval. If the X register passed to init was 1 (PAL), it will be called at the rate specified by $078-079, and if 0 (NTSC), it will use the rate at $06E-06F.
A play routine should normally finish with an RTS instruction, but is not required to do so. A non-returning play may cause problems for some NSF players (especially NES players, which will not be able to use the CPU to control a user interface). If play takes longer to finish than the specified interval, that interval may be skipped and play may not be called again until the next one.
Sound Chip Support
Byte $07B of the file stores the sound chip flags. If a particular flag is set, those sound registers should be enabled. If the flag is clear, then those registers should be disabled. All I/O registers within $8000-FFFF are write only and must not disrupt music code that happens to be stored there. Some audio register addresses have mirrors in their original hardware mappers, but NSF code should use only the lowest address for each register, listed here.
APU
- Uses registers $4000-4013, and $4015. See APU for more information.
- $4015 is set to 0F on reset by most players. It is better if the NSF does not assume this and initializes this register itself, but there are several existing NSF files that require it (Battletoads, Castlevania and Gremlins 2 are examples).
- The interrupts that can be enabled via $4015 and $4017 are not supported by the NSF format.
- $4017 is not consistently supported across NSF players.
VRCVI
- Uses registers $9000-9002, $A000-A002, and $B000-B002, write only. See VRC6 Audio for more information.
- The A0 and A1 lines are flipped on a few games. If you rip the music and it sounds all funny, flip around the xxx1 and xxx2 register pairs. (i.e. 9001 and 9002) 9000 and 9003 can be left untouched. I decided to do this since it would make things easier all around, and this means you only will have to change the music code in a very few places (6). Esper2 and Madara will need this change, while Castlevania 3j will not, for instance.
VRCVII
- Uses registers $9010 and $9030, write only. See VRC7 Audio for more information.
FDS Sound
- Uses registers from $4040 through $4092. See FDS Audio for more information.
Notes:
- $6000-DFFF is assumed to be RAM, since $6000-DFFF is RAM on the FDS. $E000-FFFF is usually not included in FDS games because it is the BIOS ROM. However, it can be used on FDS rips to help the ripper (for modified play/init addresses).
- Bank switching is different if FDS is enabled. $5FF6 and $5FF7 control banks at $6000-6FFF and $7000-7FFF, and the NSF header $076-$077 initialized both $6000-7FFF and $E000-FFFF. See above.
MMC5 Sound
- Uses registers $5000-5015, write only as well as $5205 and $5206, and $5C00-5FF5. see MMC5 Audio for more information.
Notes:
- $5205 and $5206 are a hardware 8 * 8 multiplier. The idea being you write your two bytes to be multiplied into 5205 and 5206 and after doing so, you read the result back out.
- $5C00-5FF5 should be RAM to emulate EXRAM while in MMC5 mode.
Namco 163 Sound
- Uses registers $4800 and $F800. See Namco 163 audio for more information.
Sunsoft 5B Sound
- Audio in the Sunsoft 5B mapper, a variant of the FME-7, uses registers $C000 and $E000. See Sunsoft audio.
- Many players do not implement the noise or envelope capabilities of the 5B, as they were not used in the only 5B game, Gimmick.
Multi-chip tunes
Multiple expansion chips can be used at the same time, but because this was not something that was ever supported by an original Famicom games, actual practice with multi-expansion NSF varies.
Some mappers mirror their audio registers at addresses that would conflict. Many NSF players only support the lowest address, which avoids these conflicts, but the following conflicts may need resolution in an attempted hardware multi-chip implementation:
- N163's address port $F800 overlaps a mirror of Sunsoft 5B's data port $E000. This can be avoided by setting Sunsoft 5B's address port $C000 to $0E or $0F (unused internal registers) before writing to the N163.
- VRC6 and VRC7 have a conflict at ports $9010 and $9030, where the VRC6's pulse 1 control port is mirrored.
Additionally, NSFs using FDS sound make the normally read-only area from $8000-$DFFF writable. This may cause corruption of these areas when writing to VRC6, VRC7, or 5B audio registers. The safest way to avoid this is to make sure your code and data do not fall within these addresses, so that you may safely write to them. NSF player implementations may wish to disable memory writes at these addresses to avoid the conflict.
Caveats
- The starting song number and maximum song numbers start counting at 1, while the init address of the tune starts counting at 0. Remember to pass the desired song number minus 1 to the init routine.
- The NTSC speed word is used only for NTSC tunes and dual PAL/NTSC tunes. The PAL speed word is used only for PAL tunes and dual PAL/NTSC tunes.
- The length of the text in the name, artist, and copyright fields must be 31 characters or less. There has to be at least a single NULL byte ($00) after the text, between fields.
- If a field is not known (name, artist, copyright) then the field must contain the string "<?>" (without quotes).
- There should be 8K of RAM present at $6000-7FFF. MMC5 tunes need RAM at $5C00-5FF7 to emulate its $EXRAM. $8000-FFFF should be read-only (not writable) after a tune has loaded. The only time this area should be writable is if an FDS tune is being played.
- Do not assume the state of anything on entry to the init routine except A and X. Y can be anything, as can the flags.
- Do not assume the state of anything on entry to the play routine. Flags, X, A, and Y could be at any state. I've fixed about 10 tunes because of this problem and the problem, above.
- The stack sits at $01FF and grows down. Make sure the tune does not attempt to use $01F0-01FF for variables. (Armed Dragon Villigust did, and was relocated to 2xx for its NSF.)
- RAM should be addressed from $0000-07FF, and should not expect mirror addresses to work. If the tune writes outside this range, e.g. $1400 it should be relocated. (Terminator 3 did this and was relocated to 04xx for NSF.)