Name AL_SOFT_source_latency Contributors Chris Robinson Jason Daly Dee Sharpe Contact Chris Robinson (chris.kcat 'at' gmail.com) Status Complete. Dependencies This extension is for OpenAL 1.1. Overview This extension provides a method for applications to more accurately measure the playback latency of sources. Unextended OpenAL allows apps to retrieve a source's playback offset in bytes, samples, or seconds, but this is (typically) where the AL is processing the audio data. Often, more processing is done outside of the AL. Audio servers are common and they can introduce a bit of latency, increasing the time between when the AL is done with a piece of audio data until it gets heard by the user. If the OpenAL implementation uses its own mixer, that can also add to the latency. This can ultimately cause a not-insignificant delay between where the AL is processing and what is actually being heard. Although this delay may not be very noticeable for general gaming, if the app is trying to keep a video or animation syncronized with the playback of an OpenAL source this extra delay can cause the audio and video to appear of out sync. Luckily, most audio systems have a way of measuring the latency it takes for sound to actually get to the physical output device (the DAC or speakers). By providing this information through the AL, an application can more accurately tell what a user is hearing and thus synchronize better with the audio output. Issues Q: How should an application get the latency information from a source? A: A few options were considered: 1) Simply forcing the source's playback offset back, based on the amount of detected latency. 2) Adding a new read-only property that takes the source's playback offset and adjusts it back, based on the amount of detected latency. 3) Adding a new read-only property that returns a precise measurement of the playback offset along with the measured latency it'll take for that offset to be heard. Ultimately option 3 was decided, as it will have the least impact on compatibility and little difficulty with handling "special" cases (such as looping, when the offset was recently changed, or where it would go negative). Q: What unit of measurement should this information be provided as? A: 32.32 fixed-point sample offsets+nanoseconds, and seconds. This necessitates functions to retrieve 64-bit integer and double-precision floating point values from a source. Q: Why fixed-point sample offsets, and why 32 bits of precision? A: OpenAL knows more precisely where a sample offset is when it has to resample, and this extra precision can be useful for applications that want precise timing information. In actuality, 16 bits of precision would be more than enough, however 32 bits neatly packs the value to put the whole number offset in the upper 32 bits. Such a configuration can make it easier for a 32-bit applications to deal with. New Primitive Types AL Type Description GL Type ============ ==================================== ======== ALint64SOFT Signed 64-bit 2's-compliment integer GLint64 ------------ ------------------------------------ -------- ALuint64SOFT Unsigned 64-bit integer GLuint64 New Procedures and Functions void alSourcedSOFT(ALuint source, ALenum param, ALdouble value); void alSource3dSOFT(ALuint source, ALenum param, ALdouble value1, ALdouble value2, ALdouble value3); void alSourcedvSOFT(ALuint source, ALenum param, const ALdouble *values); void alGetSourcedSOFT(ALuint source, ALenum param, ALdouble *value); void alGetSource3dSOFT(ALuint source, ALenum param, ALdouble *value1, ALdouble *value2, ALdouble *value3); void alGetSourcedvSOFT(ALuint source, ALenum param, ALdouble *values); void alSourcei64SOFT(ALuint source, ALenum param, ALint64SOFT value); void alSource3i64SOFT(ALuint source, ALenum param, ALint64SOFT value1, ALint64SOFT value2, ALint64SOFT value3); void alSourcei64vSOFT(ALuint source, ALenum param, const ALint64SOFT *values); void alGetSourcei64SOFT(ALuint source, ALenum param, ALint64SOFT *value); void alGetSource3i64SOFT(ALuint source, ALenum param, ALint64SOFT *value1, ALint64SOFT *value2, ALint64SOFT *value3); void alGetSourcei64vSOFT(ALuint source, ALenum param, ALint64SOFT *values); New Tokens AL_SAMPLE_OFFSET_LATENCY_SOFT 0x1200 AL_SEC_OFFSET_LATENCY_SOFT 0x1201 Additions to Specification New 64-bit Integer and Double-Precision Floating Point Functions: In addition to the standard 32-bit integer (i) and single-precision floating point (f) types, source attributes may be changed or queried using 64-bit integer (i64) and double-precision floating point (d) types. Any valid attribute for 32-bit integers will be valid for 64-bit integers, and any attribute for single-precision floating point will be valid for double-precision floating point. Note that the reverse is not necessarily true. Specific 64-bit integer attributes may not work through the 32-bit integer functions, and specific double-precision floating point attributes may not work with the single-precision floating point functions, unless otherwise specified. Also note that range restrictions still apply, so for example, attributes that only allow up to INT_MAX will still only allow up to INT_MAX even when set through 64-bit integer functions. New Source Attributes: Two new attributes are added to sources, which can be used to retrieve a high-precision source offset and playback latency. Source AL_SAMPLE_OFFSET_LATENCY_SOFT Attribute Name Signature Values Default ----------------------------- --------- -------------------- ------- AL_SAMPLE_OFFSET_LATENCY_SOFT i64v {[0, Any], [0, Any]} N/A Description: the playback position, expressed in fixed-point samples, along with the playback latency, expressed in nanoseconds (1/1000000000ths of a second). This attribute is read-only. The first value in the returned vector is the sample offset, which is a 32.32 fixed-point value. The whole number is stored in the upper 32 bits and the fractional component is in the lower 32 bits. The value is similar to that returned by AL_SAMPLE_OFFSET, just with more precision. The second value is the latency, in nanoseconds. It represents the length of time it will take for the audio at the current offset to actually reach the speakers or DAC. This value should be considered volatile, as it may change very often during playback (it can depend on a number of factors, including how full the mixing buffer OpenAL may be using is timer jitter, or other changes deeper in the audio pipeline). The retrieved offset and latency should be considered atomic, with respect to one another. This means the returned latency was measured exactly when the source was at the returned offset. Source AL_SEC_OFFSET_LATENCY_SOFT Attribute Name Signature Values Default -------------------------- --------- ------------------------ ------- AL_SEC_OFFSET_LATENCY_SOFT dv {[0.0, Any], [0.0, Any]} N/A Description: the playback position, along with the playback latency, both expressed in seconds. This attribute is read-only. The first value in the returned vector is the offset in seconds. The value is similar to that returned by AL_SEC_OFFSET, just with more precision. The second value is the latency, in seconds. It represents the length of time it will take for the audio at the current offset to actually reach the speakers or DAC. This value should be considered volatile, as it may change very often during playback (it can depend on a number of factors, including how full the mixing buffer OpenAL may be using is, timer jitter, or other changes deeper in the audio pipeline). The retrieved offset and latency should be considered atomic with respect to one another. This means the returned latency was measured exactly when the source was at the returned offset. Errors An AL_INVALID_OPERATION error is generated when trying to set the AL_SAMPLE_OFFSET_LATENCY_SOFT or AL_SEC_OFFSET_LATENCY_SOFT attributes.