]> scripts.mit.edu Git - autoinstallsdev/mediawiki.git/blob - vendor/james-heinrich/getid3/getid3/module.audio.midi.php
MediaWiki 1.30.2
[autoinstallsdev/mediawiki.git] / vendor / james-heinrich / getid3 / getid3 / module.audio.midi.php
1 <?php
2 /////////////////////////////////////////////////////////////////
3 /// getID3() by James Heinrich <info@getid3.org>               //
4 //  available at http://getid3.sourceforge.net                 //
5 //            or http://www.getid3.org                         //
6 //          also https://github.com/JamesHeinrich/getID3       //
7 /////////////////////////////////////////////////////////////////
8 // See readme.txt for more details                             //
9 /////////////////////////////////////////////////////////////////
10 //                                                             //
11 // module.audio.midi.php                                       //
12 // module for Midi Audio files                                 //
13 // dependencies: NONE                                          //
14 //                                                            ///
15 /////////////////////////////////////////////////////////////////
16
17 define('GETID3_MIDI_MAGIC_MTHD', 'MThd'); // MIDI file header magic
18 define('GETID3_MIDI_MAGIC_MTRK', 'MTrk'); // MIDI track header magic
19
20 class getid3_midi extends getid3_handler
21 {
22         public $scanwholefile = true;
23
24         public function Analyze() {
25                 $info = &$this->getid3->info;
26
27                 // shortcut
28                 $info['midi']['raw'] = array();
29                 $thisfile_midi               = &$info['midi'];
30                 $thisfile_midi_raw           = &$thisfile_midi['raw'];
31
32                 $info['fileformat']          = 'midi';
33                 $info['audio']['dataformat'] = 'midi';
34
35                 $this->fseek($info['avdataoffset']);
36                 $MIDIdata = $this->fread($this->getid3->fread_buffer_size());
37                 $offset = 0;
38                 $MIDIheaderID = substr($MIDIdata, $offset, 4); // 'MThd'
39                 if ($MIDIheaderID != GETID3_MIDI_MAGIC_MTHD) {
40                         $this->error('Expecting "'.getid3_lib::PrintHexBytes(GETID3_MIDI_MAGIC_MTHD).'" at offset '.$info['avdataoffset'].', found "'.getid3_lib::PrintHexBytes($MIDIheaderID).'"');
41                         unset($info['fileformat']);
42                         return false;
43                 }
44                 $offset += 4;
45                 $thisfile_midi_raw['headersize']    = getid3_lib::BigEndian2Int(substr($MIDIdata, $offset, 4));
46                 $offset += 4;
47                 $thisfile_midi_raw['fileformat']    = getid3_lib::BigEndian2Int(substr($MIDIdata, $offset, 2));
48                 $offset += 2;
49                 $thisfile_midi_raw['tracks']        = getid3_lib::BigEndian2Int(substr($MIDIdata, $offset, 2));
50                 $offset += 2;
51                 $thisfile_midi_raw['ticksperqnote'] = getid3_lib::BigEndian2Int(substr($MIDIdata, $offset, 2));
52                 $offset += 2;
53
54                 for ($i = 0; $i < $thisfile_midi_raw['tracks']; $i++) {
55                         while ((strlen($MIDIdata) - $offset) < 8) {
56                                 if ($buffer = $this->fread($this->getid3->fread_buffer_size())) {
57                                         $MIDIdata .= $buffer;
58                                 } else {
59                                         $this->warning('only processed '.($i - 1).' of '.$thisfile_midi_raw['tracks'].' tracks');
60                                         $this->error('Unabled to read more file data at '.$this->ftell().' (trying to seek to : '.$offset.'), was expecting at least 8 more bytes');
61                                         return false;
62                                 }
63                         }
64                         $trackID = substr($MIDIdata, $offset, 4);
65                         $offset += 4;
66                         if ($trackID == GETID3_MIDI_MAGIC_MTRK) {
67                                 $tracksize = getid3_lib::BigEndian2Int(substr($MIDIdata, $offset, 4));
68                                 $offset += 4;
69                                 //$thisfile_midi['tracks'][$i]['size'] = $tracksize;
70                                 $trackdataarray[$i] = substr($MIDIdata, $offset, $tracksize);
71                                 $offset += $tracksize;
72                         } else {
73                                 $this->error('Expecting "'.getid3_lib::PrintHexBytes(GETID3_MIDI_MAGIC_MTRK).'" at '.($offset - 4).', found "'.getid3_lib::PrintHexBytes($trackID).'" instead');
74                                 return false;
75                         }
76                 }
77
78                 if (!isset($trackdataarray) || !is_array($trackdataarray)) {
79                         $this->error('Cannot find MIDI track information');
80                         unset($thisfile_midi);
81                         unset($info['fileformat']);
82                         return false;
83                 }
84
85                 if ($this->scanwholefile) { // this can take quite a long time, so have the option to bypass it if speed is very important
86                         $thisfile_midi['totalticks']      = 0;
87                         $info['playtime_seconds'] = 0;
88                         $CurrentMicroSecondsPerBeat       = 500000; // 120 beats per minute;  60,000,000 microseconds per minute -> 500,000 microseconds per beat
89                         $CurrentBeatsPerMinute            = 120;    // 120 beats per minute;  60,000,000 microseconds per minute -> 500,000 microseconds per beat
90                         $MicroSecondsPerQuarterNoteAfter  = array ();
91
92                         foreach ($trackdataarray as $tracknumber => $trackdata) {
93
94                                 $eventsoffset               = 0;
95                                 $LastIssuedMIDIcommand      = 0;
96                                 $LastIssuedMIDIchannel      = 0;
97                                 $CumulativeDeltaTime        = 0;
98                                 $TicksAtCurrentBPM = 0;
99                                 while ($eventsoffset < strlen($trackdata)) {
100                                         $eventid = 0;
101                                         if (isset($MIDIevents[$tracknumber]) && is_array($MIDIevents[$tracknumber])) {
102                                                 $eventid = count($MIDIevents[$tracknumber]);
103                                         }
104                                         $deltatime = 0;
105                                         for ($i = 0; $i < 4; $i++) {
106                                                 $deltatimebyte = ord(substr($trackdata, $eventsoffset++, 1));
107                                                 $deltatime = ($deltatime << 7) + ($deltatimebyte & 0x7F);
108                                                 if ($deltatimebyte & 0x80) {
109                                                         // another byte follows
110                                                 } else {
111                                                         break;
112                                                 }
113                                         }
114                                         $CumulativeDeltaTime += $deltatime;
115                                         $TicksAtCurrentBPM   += $deltatime;
116                                         $MIDIevents[$tracknumber][$eventid]['deltatime'] = $deltatime;
117                                         $MIDI_event_channel                                  = ord(substr($trackdata, $eventsoffset++, 1));
118                                         if ($MIDI_event_channel & 0x80) {
119                                                 // OK, normal event - MIDI command has MSB set
120                                                 $LastIssuedMIDIcommand = $MIDI_event_channel >> 4;
121                                                 $LastIssuedMIDIchannel = $MIDI_event_channel & 0x0F;
122                                         } else {
123                                                 // running event - assume last command
124                                                 $eventsoffset--;
125                                         }
126                                         $MIDIevents[$tracknumber][$eventid]['eventid']   = $LastIssuedMIDIcommand;
127                                         $MIDIevents[$tracknumber][$eventid]['channel']   = $LastIssuedMIDIchannel;
128                                         if ($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x08) { // Note off (key is released)
129
130                                                 $notenumber = ord(substr($trackdata, $eventsoffset++, 1));
131                                                 $velocity   = ord(substr($trackdata, $eventsoffset++, 1));
132
133                                         } elseif ($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x09) { // Note on (key is pressed)
134
135                                                 $notenumber = ord(substr($trackdata, $eventsoffset++, 1));
136                                                 $velocity   = ord(substr($trackdata, $eventsoffset++, 1));
137
138                                         } elseif ($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x0A) { // Key after-touch
139
140                                                 $notenumber = ord(substr($trackdata, $eventsoffset++, 1));
141                                                 $velocity   = ord(substr($trackdata, $eventsoffset++, 1));
142
143                                         } elseif ($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x0B) { // Control Change
144
145                                                 $controllernum = ord(substr($trackdata, $eventsoffset++, 1));
146                                                 $newvalue      = ord(substr($trackdata, $eventsoffset++, 1));
147
148                                         } elseif ($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x0C) { // Program (patch) change
149
150                                                 $newprogramnum = ord(substr($trackdata, $eventsoffset++, 1));
151
152                                                 $thisfile_midi_raw['track'][$tracknumber]['instrumentid'] = $newprogramnum;
153                                                 if ($tracknumber == 10) {
154                                                         $thisfile_midi_raw['track'][$tracknumber]['instrument'] = $this->GeneralMIDIpercussionLookup($newprogramnum);
155                                                 } else {
156                                                         $thisfile_midi_raw['track'][$tracknumber]['instrument'] = $this->GeneralMIDIinstrumentLookup($newprogramnum);
157                                                 }
158
159                                         } elseif ($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x0D) { // Channel after-touch
160
161                                                 $channelnumber = ord(substr($trackdata, $eventsoffset++, 1));
162
163                                         } elseif ($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x0E) { // Pitch wheel change (2000H is normal or no change)
164
165                                                 $changeLSB = ord(substr($trackdata, $eventsoffset++, 1));
166                                                 $changeMSB = ord(substr($trackdata, $eventsoffset++, 1));
167                                                 $pitchwheelchange = (($changeMSB & 0x7F) << 7) & ($changeLSB & 0x7F);
168
169                                         } elseif (($MIDIevents[$tracknumber][$eventid]['eventid'] == 0x0F) && ($MIDIevents[$tracknumber][$eventid]['channel'] == 0x0F)) {
170
171                                                 $METAeventCommand = ord(substr($trackdata, $eventsoffset++, 1));
172                                                 $METAeventLength  = ord(substr($trackdata, $eventsoffset++, 1));
173                                                 $METAeventData    = substr($trackdata, $eventsoffset, $METAeventLength);
174                                                 $eventsoffset += $METAeventLength;
175                                                 switch ($METAeventCommand) {
176                                                         case 0x00: // Set track sequence number
177                                                                 $track_sequence_number = getid3_lib::BigEndian2Int(substr($METAeventData, 0, $METAeventLength));
178                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['seqno'] = $track_sequence_number;
179                                                                 break;
180
181                                                         case 0x01: // Text: generic
182                                                                 $text_generic = substr($METAeventData, 0, $METAeventLength);
183                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['text'] = $text_generic;
184                                                                 $thisfile_midi['comments']['comment'][] = $text_generic;
185                                                                 break;
186
187                                                         case 0x02: // Text: copyright
188                                                                 $text_copyright = substr($METAeventData, 0, $METAeventLength);
189                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['copyright'] = $text_copyright;
190                                                                 $thisfile_midi['comments']['copyright'][] = $text_copyright;
191                                                                 break;
192
193                                                         case 0x03: // Text: track name
194                                                                 $text_trackname = substr($METAeventData, 0, $METAeventLength);
195                                                                 $thisfile_midi_raw['track'][$tracknumber]['name'] = $text_trackname;
196                                                                 break;
197
198                                                         case 0x04: // Text: track instrument name
199                                                                 $text_instrument = substr($METAeventData, 0, $METAeventLength);
200                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['instrument'] = $text_instrument;
201                                                                 break;
202
203                                                         case 0x05: // Text: lyrics
204                                                                 $text_lyrics  = substr($METAeventData, 0, $METAeventLength);
205                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['lyrics'] = $text_lyrics;
206                                                                 if (!isset($thisfile_midi['lyrics'])) {
207                                                                         $thisfile_midi['lyrics'] = '';
208                                                                 }
209                                                                 $thisfile_midi['lyrics'] .= $text_lyrics."\n";
210                                                                 break;
211
212                                                         case 0x06: // Text: marker
213                                                                 $text_marker = substr($METAeventData, 0, $METAeventLength);
214                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['marker'] = $text_marker;
215                                                                 break;
216
217                                                         case 0x07: // Text: cue point
218                                                                 $text_cuepoint = substr($METAeventData, 0, $METAeventLength);
219                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['cuepoint'] = $text_cuepoint;
220                                                                 break;
221
222                                                         case 0x2F: // End Of Track
223                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['EOT'] = $CumulativeDeltaTime;
224                                                                 break;
225
226                                                         case 0x51: // Tempo: microseconds / quarter note
227                                                                 $CurrentMicroSecondsPerBeat = getid3_lib::BigEndian2Int(substr($METAeventData, 0, $METAeventLength));
228                                                                 if ($CurrentMicroSecondsPerBeat == 0) {
229                                                                         $this->error('Corrupt MIDI file: CurrentMicroSecondsPerBeat == zero');
230                                                                         return false;
231                                                                 }
232                                                                 $thisfile_midi_raw['events'][$tracknumber][$CumulativeDeltaTime]['us_qnote'] = $CurrentMicroSecondsPerBeat;
233                                                                 $CurrentBeatsPerMinute = (1000000 / $CurrentMicroSecondsPerBeat) * 60;
234                                                                 $MicroSecondsPerQuarterNoteAfter[$CumulativeDeltaTime] = $CurrentMicroSecondsPerBeat;
235                                                                 $TicksAtCurrentBPM = 0;
236                                                                 break;
237
238                                                         case 0x58: // Time signature
239                                                                 $timesig_numerator   = getid3_lib::BigEndian2Int($METAeventData{0});
240                                                                 $timesig_denominator = pow(2, getid3_lib::BigEndian2Int($METAeventData{1})); // $02 -> x/4, $03 -> x/8, etc
241                                                                 $timesig_32inqnote   = getid3_lib::BigEndian2Int($METAeventData{2});         // number of 32nd notes to the quarter note
242                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['timesig_32inqnote']   = $timesig_32inqnote;
243                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['timesig_numerator']   = $timesig_numerator;
244                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['timesig_denominator'] = $timesig_denominator;
245                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['timesig_text']        = $timesig_numerator.'/'.$timesig_denominator;
246                                                                 $thisfile_midi['timesignature'][] = $timesig_numerator.'/'.$timesig_denominator;
247                                                                 break;
248
249                                                         case 0x59: // Keysignature
250                                                                 $keysig_sharpsflats = getid3_lib::BigEndian2Int($METAeventData{0});
251                                                                 if ($keysig_sharpsflats & 0x80) {
252                                                                         // (-7 -> 7 flats, 0 ->key of C, 7 -> 7 sharps)
253                                                                         $keysig_sharpsflats -= 256;
254                                                                 }
255
256                                                                 $keysig_majorminor  = getid3_lib::BigEndian2Int($METAeventData{1}); // 0 -> major, 1 -> minor
257                                                                 $keysigs = array(-7=>'Cb', -6=>'Gb', -5=>'Db', -4=>'Ab', -3=>'Eb', -2=>'Bb', -1=>'F', 0=>'C', 1=>'G', 2=>'D', 3=>'A', 4=>'E', 5=>'B', 6=>'F#', 7=>'C#');
258                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['keysig_sharps'] = (($keysig_sharpsflats > 0) ? abs($keysig_sharpsflats) : 0);
259                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['keysig_flats']  = (($keysig_sharpsflats < 0) ? abs($keysig_sharpsflats) : 0);
260                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['keysig_minor']  = (bool) $keysig_majorminor;
261                                                                 //$thisfile_midi_raw['events'][$tracknumber][$eventid]['keysig_text']   = $keysigs[$keysig_sharpsflats].' '.($thisfile_midi_raw['events'][$tracknumber][$eventid]['keysig_minor'] ? 'minor' : 'major');
262
263                                                                 // $keysigs[$keysig_sharpsflats] gets an int key (correct) - $keysigs["$keysig_sharpsflats"] gets a string key (incorrect)
264                                                                 $thisfile_midi['keysignature'][] = $keysigs[$keysig_sharpsflats].' '.((bool) $keysig_majorminor ? 'minor' : 'major');
265                                                                 break;
266
267                                                         case 0x7F: // Sequencer specific information
268                                                                 $custom_data = substr($METAeventData, 0, $METAeventLength);
269                                                                 break;
270
271                                                         default:
272                                                                 $this->warning('Unhandled META Event Command: '.$METAeventCommand);
273                                                                 break;
274                                                 }
275
276                                         } else {
277
278                                                 $this->warning('Unhandled MIDI Event ID: '.$MIDIevents[$tracknumber][$eventid]['eventid'].' + Channel ID: '.$MIDIevents[$tracknumber][$eventid]['channel']);
279
280                                         }
281                                 }
282                                 if (($tracknumber > 0) || (count($trackdataarray) == 1)) {
283                                         $thisfile_midi['totalticks'] = max($thisfile_midi['totalticks'], $CumulativeDeltaTime);
284                                 }
285                         }
286                         $previoustickoffset = null;
287
288                         ksort($MicroSecondsPerQuarterNoteAfter);
289                         foreach ($MicroSecondsPerQuarterNoteAfter as $tickoffset => $microsecondsperbeat) {
290                                 if (is_null($previoustickoffset)) {
291                                         $prevmicrosecondsperbeat = $microsecondsperbeat;
292                                         $previoustickoffset = $tickoffset;
293                                         continue;
294                                 }
295                                 if ($thisfile_midi['totalticks'] > $tickoffset) {
296
297                                         if ($thisfile_midi_raw['ticksperqnote'] == 0) {
298                                                 $this->error('Corrupt MIDI file: ticksperqnote == zero');
299                                                 return false;
300                                         }
301
302                                         $info['playtime_seconds'] += (($tickoffset - $previoustickoffset) / $thisfile_midi_raw['ticksperqnote']) * ($prevmicrosecondsperbeat / 1000000);
303
304                                         $prevmicrosecondsperbeat = $microsecondsperbeat;
305                                         $previoustickoffset = $tickoffset;
306                                 }
307                         }
308                         if ($thisfile_midi['totalticks'] > $previoustickoffset) {
309
310                                 if ($thisfile_midi_raw['ticksperqnote'] == 0) {
311                                         $this->error('Corrupt MIDI file: ticksperqnote == zero');
312                                         return false;
313                                 }
314
315                                 $info['playtime_seconds'] += (($thisfile_midi['totalticks'] - $previoustickoffset) / $thisfile_midi_raw['ticksperqnote']) * ($microsecondsperbeat / 1000000);
316
317                         }
318                 }
319
320
321                 if (!empty($info['playtime_seconds'])) {
322                         $info['bitrate'] = (($info['avdataend'] - $info['avdataoffset']) * 8) / $info['playtime_seconds'];
323                 }
324
325                 if (!empty($thisfile_midi['lyrics'])) {
326                         $thisfile_midi['comments']['lyrics'][] = $thisfile_midi['lyrics'];
327                 }
328
329                 return true;
330         }
331
332         public function GeneralMIDIinstrumentLookup($instrumentid) {
333
334                 $begin = __LINE__;
335
336                 /** This is not a comment!
337
338                         0       Acoustic Grand
339                         1       Bright Acoustic
340                         2       Electric Grand
341                         3       Honky-Tonk
342                         4       Electric Piano 1
343                         5       Electric Piano 2
344                         6       Harpsichord
345                         7       Clavier
346                         8       Celesta
347                         9       Glockenspiel
348                         10      Music Box
349                         11      Vibraphone
350                         12      Marimba
351                         13      Xylophone
352                         14      Tubular Bells
353                         15      Dulcimer
354                         16      Drawbar Organ
355                         17      Percussive Organ
356                         18      Rock Organ
357                         19      Church Organ
358                         20      Reed Organ
359                         21      Accordian
360                         22      Harmonica
361                         23      Tango Accordian
362                         24      Acoustic Guitar (nylon)
363                         25      Acoustic Guitar (steel)
364                         26      Electric Guitar (jazz)
365                         27      Electric Guitar (clean)
366                         28      Electric Guitar (muted)
367                         29      Overdriven Guitar
368                         30      Distortion Guitar
369                         31      Guitar Harmonics
370                         32      Acoustic Bass
371                         33      Electric Bass (finger)
372                         34      Electric Bass (pick)
373                         35      Fretless Bass
374                         36      Slap Bass 1
375                         37      Slap Bass 2
376                         38      Synth Bass 1
377                         39      Synth Bass 2
378                         40      Violin
379                         41      Viola
380                         42      Cello
381                         43      Contrabass
382                         44      Tremolo Strings
383                         45      Pizzicato Strings
384                         46      Orchestral Strings
385                         47      Timpani
386                         48      String Ensemble 1
387                         49      String Ensemble 2
388                         50      SynthStrings 1
389                         51      SynthStrings 2
390                         52      Choir Aahs
391                         53      Voice Oohs
392                         54      Synth Voice
393                         55      Orchestra Hit
394                         56      Trumpet
395                         57      Trombone
396                         58      Tuba
397                         59      Muted Trumpet
398                         60      French Horn
399                         61      Brass Section
400                         62      SynthBrass 1
401                         63      SynthBrass 2
402                         64      Soprano Sax
403                         65      Alto Sax
404                         66      Tenor Sax
405                         67      Baritone Sax
406                         68      Oboe
407                         69      English Horn
408                         70      Bassoon
409                         71      Clarinet
410                         72      Piccolo
411                         73      Flute
412                         74      Recorder
413                         75      Pan Flute
414                         76      Blown Bottle
415                         77      Shakuhachi
416                         78      Whistle
417                         79      Ocarina
418                         80      Lead 1 (square)
419                         81      Lead 2 (sawtooth)
420                         82      Lead 3 (calliope)
421                         83      Lead 4 (chiff)
422                         84      Lead 5 (charang)
423                         85      Lead 6 (voice)
424                         86      Lead 7 (fifths)
425                         87      Lead 8 (bass + lead)
426                         88      Pad 1 (new age)
427                         89      Pad 2 (warm)
428                         90      Pad 3 (polysynth)
429                         91      Pad 4 (choir)
430                         92      Pad 5 (bowed)
431                         93      Pad 6 (metallic)
432                         94      Pad 7 (halo)
433                         95      Pad 8 (sweep)
434                         96      FX 1 (rain)
435                         97      FX 2 (soundtrack)
436                         98      FX 3 (crystal)
437                         99      FX 4 (atmosphere)
438                         100     FX 5 (brightness)
439                         101     FX 6 (goblins)
440                         102     FX 7 (echoes)
441                         103     FX 8 (sci-fi)
442                         104     Sitar
443                         105     Banjo
444                         106     Shamisen
445                         107     Koto
446                         108     Kalimba
447                         109     Bagpipe
448                         110     Fiddle
449                         111     Shanai
450                         112     Tinkle Bell
451                         113     Agogo
452                         114     Steel Drums
453                         115     Woodblock
454                         116     Taiko Drum
455                         117     Melodic Tom
456                         118     Synth Drum
457                         119     Reverse Cymbal
458                         120     Guitar Fret Noise
459                         121     Breath Noise
460                         122     Seashore
461                         123     Bird Tweet
462                         124     Telephone Ring
463                         125     Helicopter
464                         126     Applause
465                         127     Gunshot
466
467                 */
468
469                 return getid3_lib::EmbeddedLookup($instrumentid, $begin, __LINE__, __FILE__, 'GeneralMIDIinstrument');
470         }
471
472         public function GeneralMIDIpercussionLookup($instrumentid) {
473
474                 $begin = __LINE__;
475
476                 /** This is not a comment!
477
478                         35      Acoustic Bass Drum
479                         36      Bass Drum 1
480                         37      Side Stick
481                         38      Acoustic Snare
482                         39      Hand Clap
483                         40      Electric Snare
484                         41      Low Floor Tom
485                         42      Closed Hi-Hat
486                         43      High Floor Tom
487                         44      Pedal Hi-Hat
488                         45      Low Tom
489                         46      Open Hi-Hat
490                         47      Low-Mid Tom
491                         48      Hi-Mid Tom
492                         49      Crash Cymbal 1
493                         50      High Tom
494                         51      Ride Cymbal 1
495                         52      Chinese Cymbal
496                         53      Ride Bell
497                         54      Tambourine
498                         55      Splash Cymbal
499                         56      Cowbell
500                         57      Crash Cymbal 2
501                         59      Ride Cymbal 2
502                         60      Hi Bongo
503                         61      Low Bongo
504                         62      Mute Hi Conga
505                         63      Open Hi Conga
506                         64      Low Conga
507                         65      High Timbale
508                         66      Low Timbale
509                         67      High Agogo
510                         68      Low Agogo
511                         69      Cabasa
512                         70      Maracas
513                         71      Short Whistle
514                         72      Long Whistle
515                         73      Short Guiro
516                         74      Long Guiro
517                         75      Claves
518                         76      Hi Wood Block
519                         77      Low Wood Block
520                         78      Mute Cuica
521                         79      Open Cuica
522                         80      Mute Triangle
523                         81      Open Triangle
524
525                 */
526
527                 return getid3_lib::EmbeddedLookup($instrumentid, $begin, __LINE__, __FILE__, 'GeneralMIDIpercussion');
528         }
529
530 }