16 #include "alListener.h"
21 struct ALcontextProps
;
22 struct ALlistenerProps
;
24 struct ALeffectslotProps
;
26 struct ALeffectslotArray
;
29 enum class DistanceModel
{
30 InverseClamped
= AL_INVERSE_DISTANCE_CLAMPED
,
31 LinearClamped
= AL_LINEAR_DISTANCE_CLAMPED
,
32 ExponentClamped
= AL_EXPONENT_DISTANCE_CLAMPED
,
33 Inverse
= AL_INVERSE_DISTANCE
,
34 Linear
= AL_LINEAR_DISTANCE
,
35 Exponent
= AL_EXPONENT_DISTANCE
,
38 Default
= InverseClamped
41 struct SourceSubList
{
42 uint64_t FreeMask
{0u};
43 ALsource
*Sources
{nullptr}; /* 64 */
46 /* Effect slots are rather large, and apps aren't likely to have more than one
47 * or two (let alone 64), so hold them individually.
49 using ALeffectslotPtr
= struct ALeffectslot
*;
51 struct ALCcontext_struct
{
54 al::vector
<SourceSubList
> SourceList
;
58 al::vector
<ALeffectslotPtr
> EffectSlotList
;
59 almtx_t EffectSlotLock
;
61 ATOMIC(ALenum
) LastError
{AL_NO_ERROR
};
63 DistanceModel mDistanceModel
{DistanceModel::Default
};
64 ALboolean SourceDistanceModel
{AL_FALSE
};
66 ALfloat DopplerFactor
{1.0f
};
67 ALfloat DopplerVelocity
{1.0f
};
68 ALfloat SpeedOfSound
{};
69 ALfloat MetersPerUnit
{1.0f
};
71 ATOMIC(ALenum
) PropsClean
{AL_TRUE
};
72 ATOMIC(ALenum
) DeferUpdates
{AL_FALSE
};
76 /* Counter for the pre-mixing updates, in 31.1 fixed point (lowest bit
77 * indicates if updates are currently happening).
79 RefCount UpdateCount
{0u};
80 ATOMIC(ALenum
) HoldUpdates
{AL_FALSE
};
82 ALfloat GainBoost
{1.0f
};
84 ATOMIC(ALcontextProps
*) Update
{nullptr};
86 /* Linked lists of unused property containers, free to use for future
89 ATOMIC(ALcontextProps
*) FreeContextProps
{nullptr};
90 ATOMIC(ALlistenerProps
*) FreeListenerProps
{nullptr};
91 ATOMIC(ALvoiceProps
*) FreeVoiceProps
{nullptr};
92 ATOMIC(ALeffectslotProps
*) FreeEffectslotProps
{nullptr};
94 ALvoice
**Voices
{nullptr};
95 ALsizei VoiceCount
{0};
98 ATOMIC(ALeffectslotArray
*) ActiveAuxSlots
{nullptr};
100 std::thread EventThread
;
102 ll_ringbuffer
*AsyncEvents
{nullptr};
103 ATOMIC(ALbitfieldSOFT
) EnabledEvts
{0u};
105 ALEVENTPROCSOFT EventCb
{};
106 void *EventParam
{nullptr};
108 /* Default effect slot */
109 ALeffectslot
*DefaultSlot
{nullptr};
111 ALCdevice
*const Device
;
112 const ALCchar
*ExtensionList
{nullptr};
114 ATOMIC(ALCcontext
*) next
{nullptr};
116 ALlistener Listener
{};
119 ALCcontext_struct(ALCdevice
*device
) : Device
{device
} { }
120 ALCcontext_struct(const ALCcontext_struct
&) = delete;
121 ALCcontext_struct
& operator=(const ALCcontext_struct
&) = delete;
122 ~ALCcontext_struct();
124 DEF_NEWDEL(ALCcontext
)
127 ALCcontext
*GetContextRef(void);
128 void ALCcontext_DecRef(ALCcontext
*context
);
130 void UpdateContextProps(ALCcontext
*context
);
132 void ALCcontext_DeferUpdates(ALCcontext
*context
);
133 void ALCcontext_ProcessUpdates(ALCcontext
*context
);
135 inline void LockEffectSlotList(ALCcontext
*context
)
136 { almtx_lock(&context
->EffectSlotLock
); }
137 inline void UnlockEffectSlotList(ALCcontext
*context
)
138 { almtx_unlock(&context
->EffectSlotLock
); }
141 /* Simple RAII context reference. Takes the reference of the provided
142 * ALCcontext, and decrements it when leaving scope. Movable (transfer
143 * reference) but not copyable (no new references).
146 ALCcontext
*mCtx
{nullptr};
148 void release() noexcept
151 ALCcontext_DecRef(mCtx
);
156 ContextRef() noexcept
= default;
157 explicit ContextRef(ALCcontext
*ctx
) noexcept
: mCtx(ctx
) { }
158 ~ContextRef() { release(); }
160 ContextRef
& operator=(const ContextRef
&) = delete;
161 ContextRef
& operator=(ContextRef
&& rhs
) noexcept
169 operator bool() const noexcept
{ return mCtx
!= nullptr; }
171 ALCcontext
* operator->() noexcept
{ return mCtx
; }
172 ALCcontext
* get() noexcept
{ return mCtx
; }
176 struct ALcontextProps
{
177 ALfloat DopplerFactor
;
178 ALfloat DopplerVelocity
;
179 ALfloat SpeedOfSound
;
180 ALboolean SourceDistanceModel
;
181 DistanceModel mDistanceModel
;
182 ALfloat MetersPerUnit
;
184 ATOMIC(struct ALcontextProps
*) next
;
187 #endif /* ALCONTEXT_H */