diff options
author | Chris Robinson <[email protected]> | 2013-11-27 03:24:35 -0800 |
---|---|---|
committer | Chris Robinson <[email protected]> | 2013-11-27 03:49:26 -0800 |
commit | d315feae404a810177d27f86d8e4b58c1531cd60 (patch) | |
tree | a74ab4950d411f995b3eebc74446d55f546f0db9 | |
parent | 08dfbcfd5c61bc07db428e001a7a9e880d618335 (diff) |
Add a MIDI event queue
In preparation for a MIDI extension.
-rw-r--r-- | Alc/evtqueue.h | 23 | ||||
-rw-r--r-- | CMakeLists.txt | 1 | ||||
-rw-r--r-- | OpenAL32/alMidi.c | 84 |
3 files changed, 108 insertions, 0 deletions
diff --git a/Alc/evtqueue.h b/Alc/evtqueue.h new file mode 100644 index 00000000..9208df6e --- /dev/null +++ b/Alc/evtqueue.h @@ -0,0 +1,23 @@ +#ifndef AL_EVTQUEUE_H +#define AL_EVTQUEUE_H + +#include "AL/al.h" + +typedef struct MidiEvent { + ALuint time; + ALuint event; + ALuint param[2]; +} MidiEvent; + +typedef struct EvtQueue { + MidiEvent *events; + ALsizei pos; + ALsizei size; + ALsizei maxsize; +} EvtQueue; + +void InitEvtQueue(EvtQueue *queue); +void ResetEvtQueue(EvtQueue *queue); +ALenum InsertEvtQueue(EvtQueue *queue, const MidiEvent *evt); + +#endif /* AL_EXTQUEUE_H */ diff --git a/CMakeLists.txt b/CMakeLists.txt index 36efb741..1d5b6960 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -488,6 +488,7 @@ SET(OPENAL_OBJS OpenAL32/alAuxEffectSlot.c OpenAL32/alExtension.c OpenAL32/alFilter.c OpenAL32/alListener.c + OpenAL32/alMidi.c OpenAL32/alSource.c OpenAL32/alState.c OpenAL32/alThunk.c diff --git a/OpenAL32/alMidi.c b/OpenAL32/alMidi.c new file mode 100644 index 00000000..773f4cac --- /dev/null +++ b/OpenAL32/alMidi.c @@ -0,0 +1,84 @@ + +#include "config.h" + +#include <stdlib.h> +#include <string.h> +#include <limits.h> + +#include "evtqueue.h" + + +void InitEvtQueue(EvtQueue *queue) +{ + queue->events = NULL; + queue->maxsize = 0; + queue->size = 0; + queue->pos = 0; +} + +void ResetEvtQueue(EvtQueue *queue) +{ + free(queue->events); + queue->events = NULL; + queue->maxsize = 0; + queue->size = 0; + queue->pos = 0; +} + +ALenum InsertEvtQueue(EvtQueue *queue, const MidiEvent *evt) +{ + ALsizei pos; + + if(queue->maxsize == queue->size) + { + if(queue->pos > 0) + { + /* Queue has some stale entries, remove them to make space for more + * events. */ + memmove(&queue->events[0], &queue->events[queue->pos], + (queue->size-queue->pos)*sizeof(queue->events[0])); + queue->size -= queue->pos; + queue->pos = 0; + } + else + { + /* Queue is full, double the allocated space. */ + void *temp = NULL; + ALsizei newsize; + + newsize = (queue->maxsize ? (queue->maxsize<<1) : 16); + if(newsize > queue->maxsize) + temp = realloc(queue->events, newsize * sizeof(queue->events[0])); + if(!temp) + return AL_OUT_OF_MEMORY; + + queue->events = temp; + queue->maxsize = newsize; + } + } + + pos = queue->pos; + if(queue->size > 0) + { + ALsizei high = queue->size - 1; + while(pos < high) + { + ALsizei mid = pos + (high-pos)/2; + if(queue->events[mid].time < evt->time) + pos = mid + 1; + else + high = mid; + } + while(pos < queue->size && queue->events[pos].time <= evt->time) + pos++; + + if(pos < queue->size) + memmove(&queue->events[pos+1], &queue->events[pos], + (queue->size-pos)*sizeof(queue->events[0])); + } + + queue->events[pos] = *evt; + queue->size++; + + return AL_NO_ERROR; +} |