00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #ifndef __jack_midi_unpack_h__
00020 #define __jack_midi_unpack_h__
00021
00022 enum {
00023 MIDI_UNPACK_MAX_MSG = 1024
00024 };
00025
00026 typedef struct
00027 {
00028 int pos, need, size;
00029 unsigned char data[MIDI_UNPACK_MAX_MSG];
00030 }
00031 midi_unpack_t;
00032
00033 static inline
00034 void midi_unpack_init(midi_unpack_t *u)
00035 {
00036 u->pos = 0;
00037 u->size = sizeof(u->data);
00038 u->need = u->size;
00039 }
00040
00041 static inline
00042 void midi_unpack_reset(midi_unpack_t *u)
00043 {
00044 u->pos = 0;
00045 u->need = u->size;
00046 }
00047
00048 static const unsigned char midi_voice_len[] =
00049 {
00050 3,
00051 3,
00052 3,
00053 3,
00054 2,
00055 2,
00056 3,
00057 1
00058 };
00059
00060 static const unsigned char midi_system_len[] =
00061 {
00062 0,
00063 2,
00064 3,
00065 2,
00066 0,
00067 0,
00068 1,
00069 1
00070 };
00071
00072 static
00073 int midi_unpack_buf(midi_unpack_t *buf, const unsigned char *data, int len, void *jack_port_buf, jack_nframes_t time)
00074 {
00075 int i;
00076 for (i = 0; i < len; ++i) {
00077 const unsigned char byte = data[i];
00078 if (byte >= 0xF8)
00079 {
00080 jack_midi_event_write(jack_port_buf, time, &data[i], 1);
00081
00082
00083 } else if (byte < 0x80)
00084 {
00085 assert (buf->pos < buf->size);
00086 buf->data[buf->pos++] = byte;
00087 } else if (byte < 0xF0)
00088 {
00089 assert (byte >= 0x80 && byte < 0xF0);
00090
00091 buf->need = midi_voice_len[(byte-0x80)>>4];
00092 buf->data[0] = byte;
00093 buf->pos = 1;
00094 } else if (byte == 0xF7)
00095 {
00096 assert (buf->pos < buf->size);
00097 buf->data[buf->pos++] = byte;
00098 buf->need = buf->pos;
00099 } else {
00100 assert (byte >= 0xF0 && byte < 0xF8);
00101 buf->pos = 1;
00102 buf->data[0] = byte;
00103 buf->need = midi_system_len[byte - 0xF0];
00104 if (!buf->need)
00105 buf->need = buf->size;
00106 }
00107 if (buf->pos == buf->need) {
00108
00109 if (buf->data[0] >= 0x80 || (buf->data[0] == 0xF0 && buf->data[buf->pos-1] == 0xF7)) {
00110
00111 if ((buf->data[0] & 0xF0) == 0x90 && buf->data[2] == 0) {
00112
00113 jack_midi_data_t temp[3] = { 0x80, 0, 0x40 };
00114 temp[0] |= buf->data[0] & 0x0F;
00115 temp[1] = buf->data[1];
00116 jack_midi_event_write(jack_port_buf, time, temp, 3);
00117 } else
00118 jack_midi_event_write(jack_port_buf, time, &buf->data[0], buf->pos);
00119
00120
00121 }
00122
00123 if (buf->data[0] >= 0x80 && buf->data[0] < 0xF0)
00124 buf->pos = 1;
00125 else {
00126 buf->pos = 0;
00127 buf->need = buf->size;
00128 }
00129 }
00130 }
00131 assert (i == len);
00132 return i;
00133 }
00134
00135 #endif