From 82facb387c5553bed6fbd6dba34f6cd46dbe0f45 Mon Sep 17 00:00:00 2001 From: gingerBill Date: Wed, 25 Aug 2021 12:46:18 +0100 Subject: [PATCH] Add `vendor:portmidi` --- vendor/portmidi/LICENSE.txt | 25 ++ vendor/portmidi/doc.odin | 89 ++++++ vendor/portmidi/portmidi.odin | 508 +++++++++++++++++++++++++++++++++ vendor/portmidi/portmidi_s.lib | Bin 0 -> 177524 bytes vendor/portmidi/util.odin | 121 ++++++++ 5 files changed, 743 insertions(+) create mode 100644 vendor/portmidi/LICENSE.txt create mode 100644 vendor/portmidi/doc.odin create mode 100644 vendor/portmidi/portmidi.odin create mode 100644 vendor/portmidi/portmidi_s.lib create mode 100644 vendor/portmidi/util.odin diff --git a/vendor/portmidi/LICENSE.txt b/vendor/portmidi/LICENSE.txt new file mode 100644 index 000000000..fea306333 --- /dev/null +++ b/vendor/portmidi/LICENSE.txt @@ -0,0 +1,25 @@ +PortMidi Portable Real-Time MIDI Library +PortMidi API Header File +Latest version available at: http://sourceforge.net/projects/portmedia + +Copyright (c) 1999-2000 Ross Bencina and Phil Burk +Copyright (c) 2001-2006 Roger B. Dannenberg + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files +(the "Software"), to deal in the Software without restriction, +including without limitation the rights to use, copy, modify, merge, +publish, distribute, sublicense, and/or sell copies of the Software, +and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR +ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF +CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/vendor/portmidi/doc.odin b/vendor/portmidi/doc.odin new file mode 100644 index 000000000..6a3d5331a --- /dev/null +++ b/vendor/portmidi/doc.odin @@ -0,0 +1,89 @@ +package portmidi + +/* + * PortMidi Portable Real-Time MIDI Library + * PortMidi API Header File + * Latest version available at: http://sourceforge.net/projects/portmedia + * + * Copyright (c) 1999-2000 Ross Bencina and Phil Burk + * Copyright (c) 2001-2006 Roger B. Dannenberg + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files + * (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, merge, + * publish, distribute, sublicense, and/or sell copies of the Software, + * and to permit persons to whom the Software is furnished to do so, + * subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR + * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF + * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +/* + * The text above constitutes the entire PortMidi license; however, + * the PortMusic community also makes the following non-binding requests: + * + * Any person wishing to distribute modifications to the Software is + * requested to send the modifications to the original developer so that + * they can be incorporated into the canonical version. It is also + * requested that these non-binding requests be included along with the + * license above. + */ + +/* CHANGELOG FOR PORTMIDI + * (see ../CHANGELOG.txt) + * + * NOTES ON HOST ERROR REPORTING: + * + * PortMidi errors (of type PmError) are generic, system-independent errors. + * When an error does not map to one of the more specific PmErrors, the + * catch-all code pmHostError is returned. This means that PortMidi has + * retained a more specific system-dependent error code. The caller can + * get more information by calling Pm_HasHostError() to test if there is + * a pending host error, and Pm_GetHostErrorText() to get a text string + * describing the error. Host errors are reported on a per-device basis + * because only after you open a device does PortMidi have a place to + * record the host error code. I.e. only + * those routines that receive a (PortMidiStream *) argument check and + * report errors. One exception to this is that Pm_OpenInput() and + * Pm_OpenOutput() can report errors even though when an error occurs, + * there is no PortMidiStream* to hold the error. Fortunately, both + * of these functions return any error immediately, so we do not really + * need per-device error memory. Instead, any host error code is stored + * in a global, pmHostError is returned, and the user can call + * Pm_GetHostErrorText() to get the error message (and the invalid stream + * parameter will be ignored.) The functions + * pm_init and pm_term do not fail or raise + * errors. The job of pm_init is to locate all available devices so that + * the caller can get information via PmDeviceInfo(). If an error occurs, + * the device is simply not listed as available. + * + * Host errors come in two flavors: + * a) host error + * b) host error during callback + * These can occur w/midi input or output devices. (b) can only happen + * asynchronously (during callback routines), whereas (a) only occurs while + * synchronously running PortMidi and any resulting system dependent calls. + * Both (a) and (b) are reported by the next read or write call. You can + * also query for asynchronous errors (b) at any time by calling + * Pm_HasHostError(). + * + * NOTES ON COMPILE-TIME SWITCHES + * + * DEBUG assumes stdio and a console. Use this if you want automatic, simple + * error reporting, e.g. for prototyping. If you are using MFC or some + * other graphical interface with no console, DEBUG probably should be + * undefined. + * PM_CHECK_ERRORS more-or-less takes over error checking for return values, + * stopping your program and printing error messages when an error + * occurs. This also uses stdio for console text I/O. + */ \ No newline at end of file diff --git a/vendor/portmidi/portmidi.odin b/vendor/portmidi/portmidi.odin new file mode 100644 index 000000000..8c52cc7eb --- /dev/null +++ b/vendor/portmidi/portmidi.odin @@ -0,0 +1,508 @@ +package portmidi + +import "core:c" +import "core:strings" + +when ODIN_OS == "windows" do foreign import lib "portmidi.lib" + +#assert(size_of(b32) == size_of(c.int)); + +DEFAULT_SYSEX_BUFFER_SIZE :: 1024; + +Error :: enum c.int { + NoError = 0, + NoData = 0, /**< A "no error" return that also indicates no data avail. */ + GotData = 1, /**< A "no error" return that also indicates data available */ + HostError = -10000, + InvalidDeviceId, /** out of range or + * output device when input is requested or + * input device when output is requested or + * device is already opened + */ + InsufficientMemory, + BufferTooSmall, + BufferOverflow, + BadPtr, /* Stream parameter is nil or + * stream is not opened or + * stream is output when input is required or + * stream is input when output is required */ + BadData, /** illegal midi data, e.g. missing EOX */ + InternalError, + BufferMaxSize, /** buffer is already as large as it can be */ +} + +/** A single Stream is a descriptor for an open MIDI device. +*/ +Stream :: distinct rawptr; + +@(default_calling_convention="c", link_prefix="Pm_") +foreign lib { + /** + Initialize() is the library initialisation function - call this before + using the library. + */ + Initialize :: proc() -> Error --- + + /** + Terminate() is the library termination function - call this after + using the library. + */ + Terminate :: proc() -> Error --- + + /** + Test whether stream has a pending host error. Normally, the client finds + out about errors through returned error codes, but some errors can occur + asynchronously where the client does not + explicitly call a function, and therefore cannot receive an error code. + The client can test for a pending error using HasHostError(). If true, + the error can be accessed and cleared by calling GetErrorText(). + Errors are also cleared by calling other functions that can return + errors, e.g. OpenInput(), OpenOutput(), Read(), Write(). The + client does not need to call HasHostError(). Any pending error will be + reported the next time the client performs an explicit function call on + the stream, e.g. an input or output operation. Until the error is cleared, + no new error codes will be obtained, even for a different stream. + */ + HasHostError :: proc(stream: Stream) -> b32 --- +} + +/** Translate portmidi error number into human readable message. + These strings are constants (set at compile time) so client has + no need to allocate storage +*/ +GetErrorText :: proc (errnum: Error) -> string { + @(default_calling_convention="c") + foreign lib { + Pm_GetErrorText :: proc(errnum: Error) -> cstring --- + } + return string(Pm_GetErrorText(errnum)); +} + +/** Translate portmidi host error into human readable message. + These strings are computed at run time, so client has to allocate storage. + After this routine executes, the host error is cleared. +*/ +GetHostErrorText :: proc (buf: []byte) -> string { + @(default_calling_convention="c") + foreign lib { + Pm_GetHostErrorText :: proc(msg: [^]u8, len: c.uint) --- + } + Pm_GetHostErrorText(raw_data(buf), u32(len(buf))); + str := string(buf[:]); + return strings.truncate_to_byte(str, 0); +} + + +HDRLENGTH :: 50; +HOST_ERROR_MSG_LEN :: 256; /* any host error msg will occupy less + than this number of characters */ + +DeviceID :: distinct c.int; +NoDevice :: DeviceID(-1); +DeviceInfo :: struct { + structVersion: c.int, /**< this internal structure version */ + interf: cstring, /**< underlying MIDI API, e.g. MMSystem or DirectX */ + name: cstring, /**< device name, e.g. USB MidiSport 1x1 */ + input: c.int, /**< true iff input is available */ + output: c.int, /**< true iff output is available */ + opened: b32, /**< used by generic PortMidi code to do error checking on arguments */ +} + +@(default_calling_convention="c", link_prefix="Pm_") +foreign lib { + /** Get devices count, ids range from 0 to CountDevices()-1. */ + CountDevices :: proc() -> c.int --- + + GetDefaultInputDeviceID :: proc() -> DeviceID --- + GetDefaultOutputDeviceID :: proc() -> DeviceID --- +} + + +/** + Timestamp is used to represent a millisecond clock with arbitrary + start time. The type is used for all MIDI timestampes and clocks. +*/ +Timestamp :: distinct i32; +TimeProc :: proc "c" (time_info: rawptr) -> Timestamp; + +Before :: #force_inline proc "c" (t1, t2: Timestamp) -> b32 { + return b32((t1-t2) < 0); +} + +@(default_calling_convention="c", link_prefix="Pm_") +foreign lib { + /** + GetDeviceInfo() returns a pointer to a DeviceInfo structure + referring to the device specified by id. + If id is out of range the function returns nil. + + The returned structure is owned by the PortMidi implementation and must + not be manipulated or freed. The pointer is guaranteed to be valid + between calls to Initialize() and Terminate(). + */ + GetDeviceInfo :: proc(id: DeviceID) -> DeviceInfo --- + + /** + OpenInput() and OpenOutput() open devices. + + stream is the address of a Stream pointer which will receive + a pointer to the newly opened stream. + + inputDevice is the id of the device used for input (see DeviceID above). + + inputDriverInfo is a pointer to an optional driver specific data structure + containing additional information for device setup or handle processing. + inputDriverInfo is never required for correct operation. If not used + inputDriverInfo should be nil. + + outputDevice is the id of the device used for output (see DeviceID above.) + + outputDriverInfo is a pointer to an optional driver specific data structure + containing additional information for device setup or handle processing. + outputDriverInfo is never required for correct operation. If not used + outputDriverInfo should be nil. + + For input, the buffersize specifies the number of input events to be + buffered waiting to be read using Read(). For output, buffersize + specifies the number of output events to be buffered waiting for output. + (In some cases -- see below -- PortMidi does not buffer output at all + and merely passes data to a lower-level API, in which case buffersize + is ignored.) + + latency is the delay in milliseconds applied to timestamps to determine + when the output should actually occur. (If latency is < 0, 0 is assumed.) + If latency is zero, timestamps are ignored and all output is delivered + immediately. If latency is greater than zero, output is delayed until the + message timestamp plus the latency. (NOTE: the time is measured relative + to the time source indicated by time_proc. Timestamps are absolute, + not relative delays or offsets.) In some cases, PortMidi can obtain + better timing than your application by passing timestamps along to the + device driver or hardware. Latency may also help you to synchronize midi + data to audio data by matching midi latency to the audio buffer latency. + + time_proc is a pointer to a procedure that returns time in milliseconds. It + may be nil, in which case a default millisecond timebase (PortTime) is + used. If the application wants to use PortTime, it should start the timer + (call Pt_Start) before calling OpenInput or OpenOutput. If the + application tries to start the timer *after* OpenInput or OpenOutput, + it may get a ptAlreadyStarted error from Pt_Start, and the application's + preferred time resolution and callback function will be ignored. + time_proc result values are appended to incoming MIDI data, and time_proc + times are used to schedule outgoing MIDI data (when latency is non-zero). + + time_info is a pointer passed to time_proc. + + Example: If I provide a timestamp of 5000, latency is 1, and time_proc + returns 4990, then the desired output time will be when time_proc returns + timestamp+latency = 5001. This will be 5001-4990 = 11ms from now. + + return value: + Upon success Open() returns NoError and places a pointer to a + valid Stream in the stream argument. + If a call to Open() fails a nonzero error code is returned (see + PMError above) and the value of port is invalid. + + Any stream that is successfully opened should eventually be closed + by calling Close(). + + */ + OpenInput :: proc(stream: ^Stream, + inputDevice: DeviceID, + inputDriverInfo: rawptr, + bufferSize: i32, + time_proc: TimeProc, + time_info: rawptr) -> Error --- + + OpenOutput :: proc(stream: ^Stream, + outputDevice: DeviceID, + outputDriverInfo: rawptr, + bufferSize: i32, + time_proc: TimeProc, + time_info: rawptr, + latency: i32) -> Error --- + +} + + +@(default_calling_convention="c", link_prefix="Pm_") +foreign lib { + /** + SetFilter() sets filters on an open input stream to drop selected + input types. By default, only active sensing messages are filtered. + To prohibit, say, active sensing and sysex messages, call + SetFilter(stream, FILT_ACTIVE | FILT_SYSEX); + + Filtering is useful when midi routing or midi thru functionality is being + provided by the user application. + For example, you may want to exclude timing messages (clock, MTC, start/stop/continue), + while allowing note-related messages to pass. + Or you may be using a sequencer or drum-machine for MIDI clock information but want to + exclude any notes it may play. + */ + SetFilter :: proc(stream: Stream, filters: i32) -> Error --- +} + + +/* Filter bit-mask definitions */ +/** filter active sensing messages (0xFE): */ +FILT_ACTIVE :: 1 << 0x0E; +/** filter system exclusive messages (0xF0): */ +FILT_SYSEX :: 1 << 0x00; +/** filter MIDI clock message (0xF8) */ +FILT_CLOCK :: 1 << 0x08; +/** filter play messages (start 0xFA, stop 0xFC, continue 0xFB) */ +FILT_PLAY :: (1 << 0x0A) | (1 << 0x0C) | (1 << 0x0B); +/** filter tick messages (0xF9) */ +FILT_TICK :: 1 << 0x09; +/** filter undefined FD messages */ +FILT_FD :: 1 << 0x0D; +/** filter undefined real-time messages */ +FILT_UNDEFINED :: FILT_FD; +/** filter reset messages (0xFF) */ +FILT_RESET :: 1 << 0x0F; +/** filter all real-time messages */ +FILT_REALTIME :: FILT_ACTIVE | FILT_SYSEX | FILT_CLOCK | FILT_PLAY | FILT_UNDEFINED | FILT_RESET | FILT_TICK; +/** filter note-on and note-off (0x90-0x9F and 0x80-0x8F */ +FILT_NOTE :: (1 << 0x19) | (1 << 0x18); +/** filter channel aftertouch (most midi controllers use this) (0xD0-0xDF)*/ +FILT_CHANNEL_AFTERTOUCH :: 1 << 0x1D; +/** per-note aftertouch (0xA0-0xAF) */ +FILT_POLY_AFTERTOUCH :: 1 << 0x1A; +/** filter both channel and poly aftertouch */ +FILT_AFTERTOUCH :: FILT_CHANNEL_AFTERTOUCH | FILT_POLY_AFTERTOUCH; +/** Program changes (0xC0-0xCF) */ +FILT_PROGRAM :: 1 << 0x1C; +/** Control Changes (CC's) (0xB0-0xBF)*/ +FILT_CONTROL :: 1 << 0x1B; +/** Pitch Bender (0xE0-0xEF*/ +FILT_PITCHBEND :: 1 << 0x1E; +/** MIDI Time Code (0xF1)*/ +FILT_MTC :: 1 << 0x01; +/** Song Position (0xF2) */ +FILT_SONG_POSITION :: 1 << 0x02; +/** Song Select (0xF3)*/ +FILT_SONG_SELECT :: 1 << 0x03; +/** Tuning request (0xF6)*/ +FILT_TUNE :: 1 << 0x06; +/** All System Common messages (mtc, song position, song select, tune request) */ +FILT_SYSTEMCOMMON :: FILT_MTC | FILT_SONG_POSITION | FILT_SONG_SELECT | FILT_TUNE; + +Channel :: #force_inline proc "c" (channel: c.int) -> c.int { + return 1< Error --- + + /** + Abort() terminates outgoing messages immediately + The caller should immediately close the output port; + this call may result in transmission of a partial midi message. + There is no abort for Midi input because the user can simply + ignore messages in the buffer and close an input device at + any time. + */ + Abort :: proc(stream: Stream) -> Error --- + + /** + Close() closes a midi stream, flushing any pending buffers. + (PortMidi attempts to close open streams when the application + exits -- this is particularly difficult under Windows.) + */ + Close :: proc(stream: Stream) -> Error --- + + /** + Synchronize() instructs PortMidi to (re)synchronize to the + time_proc passed when the stream was opened. Typically, this + is used when the stream must be opened before the time_proc + reference is actually advancing. In this case, message timing + may be erratic, but since timestamps of zero mean + "send immediately," initialization messages with zero timestamps + can be written without a functioning time reference and without + problems. Before the first MIDI message with a non-zero + timestamp is written to the stream, the time reference must + begin to advance (for example, if the time_proc computes time + based on audio samples, time might begin to advance when an + audio stream becomes active). After time_proc return values + become valid, and BEFORE writing the first non-zero timestamped + MIDI message, call Synchronize() so that PortMidi can observe + the difference between the current time_proc value and its + MIDI stream time. + + In the more normal case where time_proc + values advance continuously, there is no need to call + Synchronize. PortMidi will always synchronize at the + first output message and periodically thereafter. + */ + Synchronize :: proc(stream: Stream) -> Error --- +} + +/** + MessageMake() encodes a short Midi message into a 32-bit word. If data1 + and/or data2 are not present, use zero. + + MessageStatus(), MessageData1(), and + MessageData2() extract fields from a 32-bit midi message. +*/ +MessageMake :: #force_inline proc "c" (status: c.int, data1, data2: c.int) -> Message { + return Message(((data2 << 16) & 0xFF0000) | ((data1 << 8) & 0xFF00) | (status & 0xFF)); +} +MessageStatus :: #force_inline proc "c" (msg: Message) -> c.int { + return c.int(msg & 0xFF); +} +MessageData1 :: #force_inline proc "c" (msg: Message) -> c.int { + return c.int((msg >> 8) & 0xFF); +} +MessageData2 :: #force_inline proc "c" (msg: Message) -> c.int { + return c.int((msg >> 16) & 0xFF); +} + +Message :: distinct i32; +/** + All midi data comes in the form of Event structures. A sysex + message is encoded as a sequence of Event structures, with each + structure carrying 4 bytes of the message, i.e. only the first + Event carries the status byte. + + Note that MIDI allows nested messages: the so-called "real-time" MIDI + messages can be inserted into the MIDI byte stream at any location, + including within a sysex message. MIDI real-time messages are one-byte + messages used mainly for timing (see the MIDI spec). PortMidi retains + the order of non-real-time MIDI messages on both input and output, but + it does not specify exactly how real-time messages are processed. This + is particulary problematic for MIDI input, because the input parser + must either prepare to buffer an unlimited number of sysex message + bytes or to buffer an unlimited number of real-time messages that + arrive embedded in a long sysex message. To simplify things, the input + parser is allowed to pass real-time MIDI messages embedded within a + sysex message, and it is up to the client to detect, process, and + remove these messages as they arrive. + + When receiving sysex messages, the sysex message is terminated + by either an EOX status byte (anywhere in the 4 byte messages) or + by a non-real-time status byte in the low order byte of the message. + If you get a non-real-time status byte but there was no EOX byte, it + means the sysex message was somehow truncated. This is not + considered an error; e.g., a missing EOX can result from the user + disconnecting a MIDI cable during sysex transmission. + + A real-time message can occur within a sysex message. A real-time + message will always occupy a full Event with the status byte in + the low-order byte of the Event message field. (This implies that + the byte-order of sysex bytes and real-time message bytes may not + be preserved -- for example, if a real-time message arrives after + 3 bytes of a sysex message, the real-time message will be delivered + first. The first word of the sysex message will be delivered only + after the 4th byte arrives, filling the 4-byte Event message field. + + The timestamp field is observed when the output port is opened with + a non-zero latency. A timestamp of zero means "use the current time", + which in turn means to deliver the message with a delay of + latency (the latency parameter used when opening the output port.) + Do not expect PortMidi to sort data according to timestamps -- + messages should be sent in the correct order, and timestamps MUST + be non-decreasing. See also "Example" for OpenOutput() above. + + A sysex message will generally fill many Event structures. On + output to a Stream with non-zero latency, the first timestamp + on sysex message data will determine the time to begin sending the + message. PortMidi implementations may ignore timestamps for the + remainder of the sysex message. + + On input, the timestamp ideally denotes the arrival time of the + status byte of the message. The first timestamp on sysex message + data will be valid. Subsequent timestamps may denote + when message bytes were actually received, or they may be simply + copies of the first timestamp. + + Timestamps for nested messages: If a real-time message arrives in + the middle of some other message, it is enqueued immediately with + the timestamp corresponding to its arrival time. The interrupted + non-real-time message or 4-byte packet of sysex data will be enqueued + later. The timestamp of interrupted data will be equal to that of + the interrupting real-time message to insure that timestamps are + non-decreasing. + */ +Event :: struct { + message: Message, + timestamp: Timestamp, +} + + +@(default_calling_convention="c", link_prefix="Pm_") +foreign lib { + /** + Read() retrieves midi data into a buffer, and returns the number + of events read. Result is a non-negative number unless an error occurs, + in which case a Error value will be returned. + + Buffer Overflow + + The problem: if an input overflow occurs, data will be lost, ultimately + because there is no flow control all the way back to the data source. + When data is lost, the receiver should be notified and some sort of + graceful recovery should take place, e.g. you shouldn't resume receiving + in the middle of a long sysex message. + + With a lock-free fifo, which is pretty much what we're stuck with to + enable portability to the Mac, it's tricky for the producer and consumer + to synchronously reset the buffer and resume normal operation. + + Solution: the buffer managed by PortMidi will be flushed when an overflow + occurs. The consumer (Read()) gets an error message (.BufferOverflow) + and ordinary processing resumes as soon as a new message arrives. The + remainder of a partial sysex message is not considered to be a "new + message" and will be flushed as well. + + */ + Read :: proc(stream: Stream, buffer: [^]Event, length: i32) -> c.int --- + + /** + Poll() tests whether input is available. + */ + Poll :: proc(stream: Stream) -> Error --- + + /** + Write() writes midi data from a buffer. This may contain: + - short messages + or + - sysex messages that are converted into a sequence of Event + structures, e.g. sending data from a file or forwarding them + from midi input. + + Use WriteSysEx() to write a sysex message stored as a contiguous + array of bytes. + + Sysex data may contain embedded real-time messages. + */ + Write :: proc(stream: Stream, buffer: [^]Event, length: i32) -> Error --- + + /** + WriteShort() writes a timestamped non-system-exclusive midi message. + Messages are delivered in order as received, and timestamps must be + non-decreasing. (But timestamps are ignored if the stream was opened + with latency = 0.) + */ + WriteShort :: proc(stream: Stream, whence: Timestamp, msg: Message) -> Error --- + + /** + WriteSysEx() writes a timestamped system-exclusive midi message. + */ + WriteSysEx :: proc(stream: Stream, whence: Timestamp, msg: cstring) -> Error --- +} \ No newline at end of file diff --git a/vendor/portmidi/portmidi_s.lib b/vendor/portmidi/portmidi_s.lib new file mode 100644 index 0000000000000000000000000000000000000000..7dd7de4a9566b81710c76a2c6c3c1e6911b6b2af GIT binary patch literal 177524 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 Pf1?7rD>A&gH~;?t_}U@? literal 0 HcmV?d00001 diff --git a/vendor/portmidi/util.odin b/vendor/portmidi/util.odin new file mode 100644 index 000000000..242844faa --- /dev/null +++ b/vendor/portmidi/util.odin @@ -0,0 +1,121 @@ +package portmidi + +/* util.odin -- some helpful utilities for building midi + applications that use PortMidi + */ + + +import "core:c" + +when ODIN_OS == "windows" do foreign import lib "portmidi_s.lib" + + +Queue :: distinct rawptr; + + +/* + A single-reader, single-writer queue is created by + QueueCreate(), which takes the number of messages and + the message size as parameters. The queue only accepts + fixed sized messages. Returns nil if memory cannot be allocated. + This queue implementation uses the "light pipe" algorithm which + operates correctly even with multi-processors and out-of-order + memory writes. (see Alexander Dokumentov, "Lock-free Interprocess + Communication," Dr. Dobbs Portal, http://www.ddj.com/, + articleID=189401457, June 15, 2006. This algorithm requires + that messages be translated to a form where no words contain + zeros. Each word becomes its own "data valid" tag. Because of + this translation, we cannot return a pointer to data still in + the queue when the "peek" method is called. Instead, a buffer + is preallocated so that data can be copied there. QueuePeek() + dequeues a message into this buffer and returns a pointer to + it. A subsequent Dequeue() will copy from this buffer. + This implementation does not try to keep reader/writer data in + separate cache lines or prevent thrashing on cache lines. + However, this algorithm differs by doing inserts/removals in + units of messages rather than units of machine words. Some + performance improvement might be obtained by not clearing data + immediately after a read, but instead by waiting for the end + of the cache line, especially if messages are smaller than + cache lines. See the Dokumentov article for explanation. + The algorithm is extended to handle "overflow" reporting. To report + an overflow, the sender writes the current tail position to a field. + The receiver must acknowlege receipt by zeroing the field. The sender + will not send more until the field is zeroed. + + QueueDestroy() destroys the queue and frees its storage. + */ + +@(default_calling_convention="c", link_prefix="Pm_") +foreign lib { + QueueCreate :: proc(num_msgs: c.long, bytes_per_msg: i32) -> Queue --- + QueueDestroy :: proc(queue: Queue) -> Error --- + + /* + Dequeue() removes one item from the queue, copying it into msg. + Returns 1 if successful, and 0 if the queue is empty. + Returns .BufferOverflow if what would have been the next thing + in the queue was dropped due to overflow. (So when overflow occurs, + the receiver can receive a queue full of messages before getting the + overflow report. This protocol ensures that the reader will be + notified when data is lost due to overflow. + */ + Dequeue :: proc(queue: Queue, msg: rawptr) -> Error --- + + /* + Enqueue() inserts one item into the queue, copying it from msg. + Returns .NoError if successful and .BufferOverflow if the queue was + already full. If .BufferOverflow is returned, the overflow flag is set. + */ + Enqueue :: proc(queue: Queue, msg: rawptr) -> Error --- + + /* + QueueFull() returns non-zero if the queue is full + QueueEmpty() returns non-zero if the queue is empty + Either condition may change immediately because a parallel + enqueue or dequeue operation could be in progress. Furthermore, + QueueEmpty() is optimistic: it may say false, when due to + out-of-order writes, the full message has not arrived. Therefore, + Dequeue() could still return 0 after QueueEmpty() returns + false. On the other hand, QueueFull() is pessimistic: if it + returns false, then Enqueue() is guaranteed to succeed. + Error conditions: QueueFull() returns .BadPtr if queue is nil. + QueueEmpty() returns false if queue is nil. + */ + QueueFull :: proc(queue: Queue) -> b32 --- + QueueEmpty :: proc(queue: Queue) -> b32 --- + + /* + QueuePeek() returns a pointer to the item at the head of the queue, + or NULL if the queue is empty. The item is not removed from the queue. + QueuePeek() will not indicate when an overflow occurs. If you want + to get and check .BufferOverflow messages, use the return value of + QueuePeek() *only* as an indication that you should call + Dequeue(). At the point where a direct call to Dequeue() would + return .BufferOverflow, QueuePeek() will return NULL but internally + clear the .BufferOverflow flag, enabling Enqueue() to resume + enqueuing messages. A subsequent call to QueuePeek() + will return a pointer to the first message *after* the overflow. + Using this as an indication to call Dequeue(), the first call + to Dequeue() will return .BufferOverflow. The second call will + return success, copying the same message pointed to by the previous + QueuePeek(). + When to use QueuePeek(): (1) when you need to look at the message + data to decide who should be called to receive it. (2) when you need + to know a message is ready but cannot accept the message. + Note that QueuePeek() is not a fast check, so if possible, you + might as well just call Dequeue() and accept the data if it is there. + */ + QueuePeek :: proc(queue: Queue) -> rawptr --- + + /* + SetOverflow() allows the writer (enqueuer) to signal an overflow + condition to the reader (dequeuer). E.g. when transfering data from + the OS to an application, if the OS indicates a buffer overrun, + SetOverflow() can be used to insure that the reader receives a + .BufferOverflow result from Dequeue(). Returns .BadPtr if queue + is NULL, returns .BufferOverflow if buffer is already in an overflow + state, returns .NoError if successfully set overflow state. + */ + SetOverflow :: proc(queue: Queue) -> Error --- +} \ No newline at end of file