18 #define F_PI (3.14159265358979323846f) /* pi */
19 #define F_PI_2 (1.57079632679489661923f) /* pi/2 */
22 static __inline
float powf(float x
, float y
)
23 { return (float)pow(x
, y
); }
27 static __inline
float sqrtf(float x
)
28 { return (float)sqrt(x
); }
32 static __inline
float cosf(float x
)
33 { return (float)cos(x
); }
37 static __inline
float sinf(float x
)
38 { return (float)sin(x
); }
42 static __inline
float acosf(float x
)
43 { return (float)acos(x
); }
47 static __inline
float asinf(float x
)
48 { return (float)asin(x
); }
52 static __inline
float atanf(float x
)
53 { return (float)atan(x
); }
57 static __inline
float atan2f(float x
, float y
)
58 { return (float)atan2(x
, y
); }
62 static __inline
float fabsf(float x
)
63 { return (float)fabs(x
); }
67 static __inline
float log10f(float x
)
68 { return (float)log10(x
); }
72 static __inline
float floorf(float x
)
73 { return (float)floor(x
); }
85 typedef ALvoid (*DryMixerFunc
)(struct ALsource
*self
, ALCdevice
*Device
,
86 struct DirectParams
*params
,
87 const ALfloat
*RESTRICT data
, ALuint srcchan
,
88 ALuint OutPos
, ALuint SamplesToDo
,
90 typedef ALvoid (*WetMixerFunc
)(struct SendParams
*params
,
91 const ALfloat
*RESTRICT data
,
92 ALuint OutPos
, ALuint SamplesToDo
,
118 InverseDistanceClamped
= AL_INVERSE_DISTANCE_CLAMPED
,
119 LinearDistanceClamped
= AL_LINEAR_DISTANCE_CLAMPED
,
120 ExponentDistanceClamped
= AL_EXPONENT_DISTANCE_CLAMPED
,
121 InverseDistance
= AL_INVERSE_DISTANCE
,
122 LinearDistance
= AL_LINEAR_DISTANCE
,
123 ExponentDistance
= AL_EXPONENT_DISTANCE
,
124 DisableDistance
= AL_NONE
,
126 DefaultDistanceModel
= InverseDistanceClamped
130 /* Size for temporary storage of buffer data, in ALfloats. Larger values need
131 * more stack, while smaller values may need more iterations. The value needs
132 * to be a sensible size, however, as it constrains the max stepping value used
133 * for mixing, as well as the maximum number of samples per mixing iteration.
134 * The mixer requires being able to do two samplings per mixing loop. A 16KB
135 * buffer can hold 512 sample frames for a 7.1 float buffer. With the cubic
136 * resampler (which requires 3 padding sample frames), this limits the maximum
137 * step to about 508. This means that buffer_freq*source_pitch cannot exceed
138 * device_freq*508 for an 8-channel 32-bit buffer.
141 #define BUFFERSIZE 4096
144 #define FRACTIONBITS (14)
145 #define FRACTIONONE (1<<FRACTIONBITS)
146 #define FRACTIONMASK (FRACTIONONE-1)
149 static __inline ALfloat
minf(ALfloat a
, ALfloat b
)
150 { return ((a
> b
) ? b
: a
); }
151 static __inline ALfloat
maxf(ALfloat a
, ALfloat b
)
152 { return ((a
> b
) ? a
: b
); }
153 static __inline ALfloat
clampf(ALfloat val
, ALfloat min
, ALfloat max
)
154 { return minf(max
, maxf(min
, val
)); }
156 static __inline ALuint
minu(ALuint a
, ALuint b
)
157 { return ((a
> b
) ? b
: a
); }
158 static __inline ALuint
maxu(ALuint a
, ALuint b
)
159 { return ((a
> b
) ? a
: b
); }
160 static __inline ALuint
clampu(ALuint val
, ALuint min
, ALuint max
)
161 { return minu(max
, maxu(min
, val
)); }
163 static __inline ALint
mini(ALint a
, ALint b
)
164 { return ((a
> b
) ? b
: a
); }
165 static __inline ALint
maxi(ALint a
, ALint b
)
166 { return ((a
> b
) ? a
: b
); }
167 static __inline ALint
clampi(ALint val
, ALint min
, ALint max
)
168 { return mini(max
, maxi(min
, val
)); }
170 static __inline ALint64
mini64(ALint64 a
, ALint64 b
)
171 { return ((a
> b
) ? b
: a
); }
172 static __inline ALint64
maxi64(ALint64 a
, ALint64 b
)
173 { return ((a
> b
) ? a
: b
); }
174 static __inline ALint64
clampi64(ALint64 val
, ALint64 min
, ALint64 max
)
175 { return mini64(max
, maxi64(min
, val
)); }
177 static __inline ALuint64
minu64(ALuint64 a
, ALuint64 b
)
178 { return ((a
> b
) ? b
: a
); }
179 static __inline ALuint64
maxu64(ALuint64 a
, ALuint64 b
)
180 { return ((a
> b
) ? a
: b
); }
181 static __inline ALuint64
clampu64(ALuint64 val
, ALuint64 min
, ALuint64 max
)
182 { return minu64(max
, maxu64(min
, val
)); }
185 static __inline ALfloat
lerp(ALfloat val1
, ALfloat val2
, ALfloat mu
)
187 return val1
+ (val2
-val1
)*mu
;
189 static __inline ALfloat
cubic(ALfloat val0
, ALfloat val1
, ALfloat val2
, ALfloat val3
, ALfloat mu
)
192 ALfloat a0
= -0.5f
*val0
+ 1.5f
*val1
+ -1.5f
*val2
+ 0.5f
*val3
;
193 ALfloat a1
= val0
+ -2.5f
*val1
+ 2.0f
*val2
+ -0.5f
*val3
;
194 ALfloat a2
= -0.5f
*val0
+ 0.5f
*val2
;
197 return a0
*mu
*mu2
+ a1
*mu2
+ a2
*mu
+ a3
;
201 static __inline
int SetMixerFPUMode(void)
203 #if defined(_FPU_GETCW) && defined(_FPU_SETCW) && (defined(__i386__) || defined(__x86_64__))
204 fpu_control_t fpuState
, newState
;
205 _FPU_GETCW(fpuState
);
206 newState
= fpuState
&~(_FPU_EXTENDED
|_FPU_DOUBLE
|_FPU_SINGLE
|
207 _FPU_RC_NEAREST
|_FPU_RC_DOWN
|_FPU_RC_UP
|_FPU_RC_ZERO
);
208 newState
|= _FPU_SINGLE
| _FPU_RC_ZERO
;
209 _FPU_SETCW(newState
);
212 #if defined(HAVE__CONTROLFP)
213 fpuState
= _controlfp(0, 0);
214 (void)_controlfp(_RC_CHOP
|_PC_24
, _MCW_RC
|_MCW_PC
);
215 #elif defined(HAVE_FESETROUND)
216 fpuState
= fegetround();
218 fesetround(FE_TOWARDZERO
);
225 static __inline
void RestoreFPUMode(int state
)
227 #if defined(_FPU_GETCW) && defined(_FPU_SETCW) && (defined(__i386__) || defined(__x86_64__))
228 fpu_control_t fpuState
= state
;
229 _FPU_SETCW(fpuState
);
230 #elif defined(HAVE__CONTROLFP)
231 _controlfp(state
, _MCW_RC
|_MCW_PC
);
232 #elif defined(HAVE_FESETROUND)
238 static __inline
void aluCrossproduct(const ALfloat
*inVector1
, const ALfloat
*inVector2
, ALfloat
*outVector
)
240 outVector
[0] = inVector1
[1]*inVector2
[2] - inVector1
[2]*inVector2
[1];
241 outVector
[1] = inVector1
[2]*inVector2
[0] - inVector1
[0]*inVector2
[2];
242 outVector
[2] = inVector1
[0]*inVector2
[1] - inVector1
[1]*inVector2
[0];
245 static __inline ALfloat
aluDotproduct(const ALfloat
*inVector1
, const ALfloat
*inVector2
)
247 return inVector1
[0]*inVector2
[0] + inVector1
[1]*inVector2
[1] +
248 inVector1
[2]*inVector2
[2];
251 static __inline
void aluNormalize(ALfloat
*inVector
)
253 ALfloat lengthsqr
= aluDotproduct(inVector
, inVector
);
256 ALfloat inv_length
= 1.0f
/sqrtf(lengthsqr
);
257 inVector
[0] *= inv_length
;
258 inVector
[1] *= inv_length
;
259 inVector
[2] *= inv_length
;
264 ALvoid
aluInitPanning(ALCdevice
*Device
);
266 ALvoid
ComputeAngleGains(const ALCdevice
*device
, ALfloat angle
, ALfloat hwidth
, ALfloat ingain
, ALfloat
*gains
);
268 ALvoid
CalcSourceParams(struct ALsource
*ALSource
, const ALCcontext
*ALContext
);
269 ALvoid
CalcNonAttnSourceParams(struct ALsource
*ALSource
, const ALCcontext
*ALContext
);
271 ALvoid
MixSource(struct ALsource
*Source
, ALCdevice
*Device
, ALuint SamplesToDo
);
273 ALvoid
aluMixData(ALCdevice
*device
, ALvoid
*buffer
, ALsizei size
);
274 ALvoid
aluHandleDisconnect(ALCdevice
*device
);
276 extern ALfloat ConeScale
;
277 extern ALfloat ZScale
;