These messages are addressed to a specific MIDI channel.
In the following table, an "x" specifies any MIDI channel (0 - 15). Thus "status byte 8x" means any value from 80 to 8F.
Note that some message types have two data bytes; others have only one.
Type | Status (Hex) | Data (value = 0-127) |
Note off | 8x | note, velocity |
Note on | 9x | note, velocity (velocity 0 = note off) |
Polyphonic pressure | Ax | note, value |
Controller change | Bx | controller, value |
Program change | Cx | program |
Channel pressure | Dx | value |
Pitch bend | Ex | value, value (two bytes). However, many devices accept a single data byte (the MSB byte) |
System messages are intended for the whole MIDI system - not channel specific.
Note that any non-realtime status byte ends a System Exclusive message; F7 (EOX) is not required at the end of a SysEx message.
Realtime status bytes may appear any time in the MIDI data stream, including in the middle of a SysEx message.
Type | Status (Hex) | Data (value = 0-127) |
System Exclusive | F0 | data |
Time Code | F1 | one byte |
Song Position Pointer | F2 | two bytes: lsb msb |
Song Select | F3 | one byte: song number 0 - 127 |
(undefined) | F4 | |
(undefined) | F5 | |
Tune Request | F6 | no data |
EOX (End of System Exclusive) | F7 |
System Exclusive message examples:
• GM System On = F0 7E 7F 09 01 F7
• XG System On = F0 43 10 4C 00 00 7E 00 F7
• XG Works On = F0 43 76 1A 10 01 01 01 01 01 01 01 01 F7
• Yamaha = F0 43 73 39 F1 00 46 00 F7
• XG Reset = F0 43 10 4C 00 00 7F 00 F7
Realtime messages are not associated with any one MIDI channel.
They can appear in the MIDI data stream at any time.
These messages consist of a single status byte; they have no data bytes.
Type | Status (Hex) |
Clock | F8 |
(undefined) | F9 |
Start | FA |
Continue | FB |
Stop | FC |
(undefined) | FD |
Active Sensing | FE |
System Reset | FF |
Meta messages are not associated with any one MIDI channel.
They can appear in the MIDI data stream at any time (except for Time Signature and End of Track).
However it is recommended to insert most of the messages in the beginning of the stream/file.
Note that Meta messages are not for realtime use; but for use in MIDI files.
• 1. byte: FF = status byte (always FF)
• 2. byte: Message (event) type
• 3. byte: Length of the remaining data bytes
• 4. and following bytes: The data itself.
Type | Status (FF) Data (Hex) | Comments |
Sequence Number | FF 00 02 ss ss | Specifies the number of a sequence.
The two data bytes ss ss, are that number which corresponds to the MIDI Cue message. |
Text | FF 01 len text | Any amount of text (amount of bytes = len) for any purpose.
This event is primarily used to add "comments" to a MIDI file which a program would be expected to ignore when loading that file. |
Copyright | FF 02 len text | A copyright message (ie, text). |
Sequence/Track Name | FF 03 len text | The name of the sequence or track (ie, text). |
Instrument | FF 04 len text | The name of the instrument that the track plays (ie, text). |
Lyric | FF 05 len text | A song lyric (ie, text) which occurs on a given beat.
A single Lyric MetaEvent should contain only one syllable. |
Marker | FF 06 len text | A marker (ie, text) which occurs on a given beat.
Marker events might be used to denote a loop start and loop end (ie, where the sequence loops back to a previous event). |
Cue Point | FF 07 len text | A cue point (ie, text) which occurs on a given beat.
A Cue Point might be used to denote where a WAVE (ie, sampled sound) file starts playing, where the text would be the WAVE's filename. |
MIDI Channel | FF 20 01 cc | Specifies to which MIDI Channel any subsequent MetaEvent or System Exclusive events are associated.
The data byte cc, is the MIDI channel, where 0 would be the first channel. |
MIDI Port | FF 21 01 pp | Specifies out of which MIDI Port (ie, buss) the MIDI events in the MIDI track go.
The data byte pp, is the port number, where 0 would be the first MIDI buss in the system. |
End of Track | FF 2F 00 | This message is NOT optional. It must be the last event in every MIDI track. It's used as a definitive marking of the end of a MIDI track. Only 1 per MIDI track. |
Tempo | FF 51 03 tt tt tt | Indicates a tempo change.
The 3 data bytes of tt tt tt are the tempo in microseconds per quarter note. In other words, the microsecond tempo value tells you how long each one of your sequencer's "quarter notes" should be. If tt tt tt = 07 A1 20, then each quarter note should be 07 A1 20 (or 500,000) microseconds long. (Check with your Windows Calculator in Scientific Mode). Normally, musicians express tempo as "the amount of quarter notes in every minute (ie, time period)". This is the opposite of the way that the MIDI file format expresses it. To convert the MIDI file format's tempo to BPM (beats per minute): BPM = 60,000,000/(tt tt tt) For example, a tempo of 120 BPM = 07 A1 20 microseconds per quarter note. NOTE: • If no Tempo is defined at all, the default value 120 BPM is assumed. |
SMPTE Offset | FF 54 05 hr mn se fr ff | Designates the SMPTE start time (hours, minutes, secs, frames, subframes) of the MIDI track. |
Time Signature | FF 58 04 nn dd cc bb | Time signature is expressed as 4 numbers.
• nn and dd represent the "numerator" and "denominator" of the signature as notated on sheet music. The denominator is a negative power of 2: 2 = quarter note, 3 = eighth, etc. • cc expresses the number of MIDI clocks in a metronome click. • bb expresses the number of notated 32nd notes in a MIDI quarter note (24 MIDI clocks). This event allows a program to relate what MIDI thinks of as a quarter, to something entirely different. For example, 6/8 time with a metronome click every 3 eighth notes and 24 clocks per quarter note would be the following event: FF 58 04 06 03 18 08 NOTE: • If no Time Signature is defined, the default value 4/4 is assumed. • Time Signature can only be redefined at measure beginnings. |
Key Signature | FF 59 02 sf mi | • sf = -7 for 7 flats, -1 for 1 flat, etc, 0 for key of c, 1 for 1 sharp, etc.
• mi = 0 for major, 1 for minor |
Proprietary Event | FF 7F len data | This can be used by a program to store proprietary data. The first byte(s) should be a unique ID of some sort so that a program can identify whether the event belongs to it, or to some other program. A 4 character (ie, ascii) ID is recommended for such. |