The Musical Instrument Digital Interface (MIDI) file format is used for storing the notes required to accurately reproduce a song. Commercial instruments are available that "speak" the MIDI protocol, and a MIDI file (.mid) simply stores the data sent over the wire, with a few headers on the front.

File format

A MIDI file starts with an overall MThd header, followed by one or more MTrk headers for each "track" (a track is normally created for each instrument, for simplicity when the song is being composed.)

MThd Header

The file begins with a header:

Data type

Name

Description

BYTE[4]

cSignature

"MThd" (not NULL-terminated)

UINT32BE

iLength

Length of MThd block (usually 6)

UINT16BE

iType

0, 1 or 2 (for format-0, 1 or 2)

UINT16BE

iNumTracks

Number of tracks (will be 1 for format-0)

UINT16BE

iTicksPerQuarterNote

Number of MIDI delay ticks in a quarter-note

If the high bit in iTicksPerQuarterNote is set (0x8000) then the file uses SMPTE timing instead, which is rare and not covered here.

MTrk block

The MTrk block is repeated once for each track in the song (the iNumTracks field in the MThd header.)

Data type

Name

Description

BYTE[4]

cSignature

"MTrk" (not NULL-terminated)

UINT32BE

iLength

Length of block

BYTE[iLength]

cData

MIDI data

MIDI data

The MIDI data consists of a delay value (in MIDI variable-length integer notation), followed by a MIDI event byte (see #MIDI events below.) The event data follows, and will be different depending on the event. It then starts again with the delay value for the next event.

MIDI lengths

MIDI lengths are stored as variable length integers, between one and four bytes long. Each byte only uses the lower 7-bits, with the MSB set if there is another length byte following. The bytes are in big endian order. Some examples of these length bytes are:

constchar*midi_data ="\x81\x50";unsignedlong val =0;for(int i =0; i <4; i++){// Include the lower 7-bits of this byte into the value
val |= midi_data[i]&0x7F;// If the high bit is set, shift the value up// seven bits to make room for the next valueif(midi_data[i]&0x80) val <<=7;elsebreak;// High bit unset means end of value}printf("Value is %lu\n", val);

Generally speaking, MIDI data that can be sent over the wire uses these values (e.g. delays), whereas data only used to write .mid files on disk (e.g. MTrk lengths in bytes) use normal big-endian fixed-length values.

MIDI events

This table lists the different MIDI events that can occur in a song. The events are listed as channel zero (e.g. 0x80, which would become 0x85 for channel five.) Removing the high bit ((byte & 0x7F) >> 4) will give the 'event number'.

Register value

Event number

Data size

Purpose

0x80

0

2

Note off

0x90

1

2

Note on

0xA0

2

2

Polyphonic key pressure

0xB0

3

2

Controller

0xC0

4

1

Instrument change

0xD0

5

1

Channel pressure

0xE0

6

2

Pitch bend

0xF0

7

Any

Sysex

0xFF

N/A

Any

Meta-event

The data bytes for each event are described in the sections below.

Each event is preceded by a delay (as a MIDILEN variable-length integer, see #MIDI lengths above) which specifies the number of MIDI ticks until the event should be actioned.

To convert the number of MIDI ticks into a usable time value, the iTicksPerQuarterNote field from the header will allow the tick count to be converted into a fractional number of quarter notes, then the song's tempo (in microseconds per quarter note) will allow this fractional number of quarter notes to be converted into microseconds.

The default tempo of 500,000 microseconds per quarter note applies until overridden by a set-tempo event.

Running-status

Any event values without the high-bit set (i.e. less than 0x80) are so-called "running status" values. If one of these bytes is encountered as a MIDI event, it is actually the first data byte of the event instead. The actual event is the same as the previous one. For example, these two lines are equivalent: (delay bytes omitted for clarity)

44 00: Turn note 0x44 off on the same channel (running status uses event 0x91 again, and takes advantage of note-on at zero velocity being the same as note-off)

Meta-events do not affect running status, so any event from 0xF0 to 0xFF can appear in the middle of data without affecting the running status. For example the following line is equivalent to the two lines above:

90 40 7F 91 44 7F FF 01 02 AA BB 47 7F F0 02 AA F7 44 00

0x80: Note off

Stops the specified note from sounding on this channel. Does not affect any other notes currently being played on the same channel. A note-on event with a velocity of zero is the same as a note-off event.

Data bytes

Purpose

UINT8 iNote

MIDI note number to key-off (0-127)

UINT8 iVelocity

How hard to release the note (0-127)

0x90: Note on

Plays the specified note on the given channel. Multiple notes can be sounding at the same time on the same channel. A velocity of zero is the same as a note-off event (this is often used with running status to minimise the amount of data used.)

Data bytes

Purpose

UINT8 iNote

MIDI note number to key-on (0-127)

UINT8 iVelocity

How hard to press the note (0-127)

0xA0: Polyphonic key pressure

Data bytes

Purpose

UINT8 iPressure

Pressure value (0-127)

UINT8 iNote

MIDI note number to affect (0-127)

0xB0: Controller

Set a MIDI controller to the specified value. TODO: List of standard controllers

Data bytes

Purpose

UINT8 iController

Controller index (0-127)

UINT8 iValue

Value to set (0-127)

0xC0: Instrument change

Set the channel to the specified instrument.

Data bytes

Purpose

UINT8 iInstrument

Instrument number (0-127)

0xD0: Channel pressure

Data bytes

Purpose

UINT8 iPressure

Pressure value (0-127)

0xE0: Pitch bend

Bend all notes on the channel up or down by the specified amount. The value is between 0 and 16384. The value 8192 is in the middle and means no bend, thus 8192 can be subtracted from this the value to create a signed integer between -8192 and +8191, with zero meaning "no bend." The actual pitch resulting from the bend depends on the range, which is set (usually at the start of the song) by a MIDI controller message.

Data bytes

Purpose

UINT8 iLSB

Least significant byte (0-127)

UINT8 iMSB

Most significant byte (0-127)

The value is calculated by combining the lower seven bits from each of the two bytes into a single 14-bit value: value = (iMSB << 7) | iLSB

0xF0: System exclusive

These messages are used to send proprietary commands to various MIDI devices. They are essentially a list of raw bytes to send. The channel is not used, so 0xF0 through 0xFF are different "sysex" messages. Since 0xFF is used as a reset it would have no use in a .mid file on disk, so this event is used for meta-events described below.

The event type (0xF0 to 0xFE) is followed by this structure:

Data bytes

Purpose

MIDILEN iLength

Length of data

UINT8 cData[iLength]

Block of data, iLength bytes long

Event 0xFF has a different structure and is covered below. The event types are defined as follows:

Event type

Purpose

0xF0

Start system exclusive event

0xF1

MIDI time code

0xF2

Song position pointer

0xF3

Song select

0xF4

(Unused)

0xF5

(Unused)

0xF6

Tune request

0xF7

End system exclusive event (EOX)

0xF8

Timing clock

0xF9

(Unused)

0xFA

Start playback

0xFB

Continue playback

0xFC

Stop playback

0xFD

(Unused)

0xFE

Active sensing

0xFF

System reset (used for meta-event in a MIDI file)

Meta events

Meta events are events specific to MIDI files themselves. They are not transmitted to MIDI devices. A meta event is signalled by the 0xFF system exclusive event. The following table lists the format of the bytes following the 0xFF.

Data bytes

Purpose

UINT8 iType

Meta-event type

MIDILEN iLength

Length of event data

UINT8 cData[iLength]

Event data

The following section lists the meaning of various values of iType.

0x01 - 0x0F: Text

These events set various types of text. The event data is the text to set.

Event type

Text use

0x01

Generic text event. Often the first text event in a song is used as its title.

0x02

Copyright notice

0x03

Track name. Often the first event (format-0) or the first track (format-1) is the song title.

0x04

Instrument name

0x05

Lyric

0x06

Marker

0x07

Cue point (e.g. stage instructions)

0x2F: End of track

Mandatory event at the end of each MTrk track. The length field is always zero, so there are no bytes of event data.

0x51: Set tempo

This event should always have a length of three. The event data is a big-endian integer (not in MIDI variable-length notation) indicating the number of microseconds in a quarter note. Together with the iTicksPerQuarterNote value from the header, this allows MIDI ticks to be converted into microseconds for correct playback speed of the MIDI file.

Unless overridden by this event, the number of microseconds in a quarter note defaults to 500,000.

0x7F: Manufacturer-specific

The first data byte of this event is a manufacturer ID. If it is 0x00, then the following UINT16BE is the actual manufacturer ID. This means either one or three bytes total will be read to obtain the manufacturer ID.

If the manufacturer ID is 0x3F then it is an Ad Lib, Inc. event, and the file format is technically .mdi (an Ad Lib MIDI file with embedded OPL instruments), see MDI Format for details.

Additional meta-events

Other meta-events (not so important for playing back game music) are listed on various web sites: