Fix up according to Coding Style
[pulseaudio-mirror.git] / src / pulsecore / svolume_c.c
blobdfe7ccb06ee60658025a11cce106809f242f3817
1 /***
2 This file is part of PulseAudio.
4 Copyright 2004-2006 Lennart Poettering
5 Copyright 2006 Pierre Ossman <ossman@cendio.se> for Cendio AB
7 PulseAudio is free software; you can redistribute it and/or modify
8 it under the terms of the GNU Lesser General Public License as published
9 by the Free Software Foundation; either version 2.1 of the License,
10 or (at your option) any later version.
12 PulseAudio is distributed in the hope that it will be useful, but
13 WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 General Public License for more details.
17 You should have received a copy of the GNU Lesser General Public License
18 along with PulseAudio; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
20 USA.
21 ***/
23 #ifdef HAVE_CONFIG_H
24 #include <config.h>
25 #endif
28 #include <pulsecore/macro.h>
29 #include <pulsecore/g711.h>
30 #include <pulsecore/core-util.h>
32 #include "sample-util.h"
33 #include "endianmacros.h"
35 static void pa_volume_u8_c(uint8_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
36 unsigned channel;
38 for (channel = 0; length; length--) {
39 int32_t t, hi, lo;
41 hi = volumes[channel] >> 16;
42 lo = volumes[channel] & 0xFFFF;
44 t = (int32_t) *samples - 0x80;
45 t = ((t * lo) >> 16) + (t * hi);
46 t = PA_CLAMP_UNLIKELY(t, -0x80, 0x7F);
47 *samples++ = (uint8_t) (t + 0x80);
49 if (PA_UNLIKELY(++channel >= channels))
50 channel = 0;
54 static void pa_volume_alaw_c(uint8_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
55 unsigned channel;
57 for (channel = 0; length; length--) {
58 int32_t t, hi, lo;
60 hi = volumes[channel] >> 16;
61 lo = volumes[channel] & 0xFFFF;
63 t = (int32_t) st_alaw2linear16(*samples);
64 t = ((t * lo) >> 16) + (t * hi);
65 t = PA_CLAMP_UNLIKELY(t, -0x8000, 0x7FFF);
66 *samples++ = (uint8_t) st_13linear2alaw((int16_t) t >> 3);
68 if (PA_UNLIKELY(++channel >= channels))
69 channel = 0;
73 static void pa_volume_ulaw_c(uint8_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
74 unsigned channel;
76 for (channel = 0; length; length--) {
77 int32_t t, hi, lo;
79 hi = volumes[channel] >> 16;
80 lo = volumes[channel] & 0xFFFF;
82 t = (int32_t) st_ulaw2linear16(*samples);
83 t = ((t * lo) >> 16) + (t * hi);
84 t = PA_CLAMP_UNLIKELY(t, -0x8000, 0x7FFF);
85 *samples++ = (uint8_t) st_14linear2ulaw((int16_t) t >> 2);
87 if (PA_UNLIKELY(++channel >= channels))
88 channel = 0;
92 static void pa_volume_s16ne_c(int16_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
93 unsigned channel;
95 length /= sizeof(int16_t);
97 for (channel = 0; length; length--) {
98 int32_t t, hi, lo;
100 /* Multiplying the 32bit volume factor with the 16bit
101 * sample might result in an 48bit value. We want to
102 * do without 64 bit integers and hence do the
103 * multiplication independantly for the HI and LO part
104 * of the volume. */
106 hi = volumes[channel] >> 16;
107 lo = volumes[channel] & 0xFFFF;
109 t = (int32_t)(*samples);
110 t = ((t * lo) >> 16) + (t * hi);
111 t = PA_CLAMP_UNLIKELY(t, -0x8000, 0x7FFF);
112 *samples++ = (int16_t) t;
114 if (PA_UNLIKELY(++channel >= channels))
115 channel = 0;
119 static void pa_volume_s16re_c(int16_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
120 unsigned channel;
122 length /= sizeof(int16_t);
124 for (channel = 0; length; length--) {
125 int32_t t, hi, lo;
127 hi = volumes[channel] >> 16;
128 lo = volumes[channel] & 0xFFFF;
130 t = (int32_t) PA_INT16_SWAP(*samples);
131 t = ((t * lo) >> 16) + (t * hi);
132 t = PA_CLAMP_UNLIKELY(t, -0x8000, 0x7FFF);
133 *samples++ = PA_INT16_SWAP((int16_t) t);
135 if (PA_UNLIKELY(++channel >= channels))
136 channel = 0;
140 static void pa_volume_float32ne_c(float *samples, float *volumes, unsigned channels, unsigned length) {
141 unsigned channel;
143 length /= sizeof(float);
145 for (channel = 0; length; length--) {
146 *samples++ *= volumes[channel];
148 if (PA_UNLIKELY(++channel >= channels))
149 channel = 0;
153 static void pa_volume_float32re_c(float *samples, float *volumes, unsigned channels, unsigned length) {
154 unsigned channel;
156 length /= sizeof(float);
158 for (channel = 0; length; length--) {
159 float t;
161 t = PA_FLOAT32_SWAP(*samples);
162 t *= volumes[channel];
163 *samples++ = PA_FLOAT32_SWAP(t);
165 if (PA_UNLIKELY(++channel >= channels))
166 channel = 0;
170 static void pa_volume_s32ne_c(int32_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
171 unsigned channel;
173 length /= sizeof(int32_t);
175 for (channel = 0; length; length--) {
176 int64_t t;
178 t = (int64_t)(*samples);
179 t = (t * volumes[channel]) >> 16;
180 t = PA_CLAMP_UNLIKELY(t, -0x80000000LL, 0x7FFFFFFFLL);
181 *samples++ = (int32_t) t;
183 if (PA_UNLIKELY(++channel >= channels))
184 channel = 0;
188 static void pa_volume_s32re_c(int32_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
189 unsigned channel;
191 length /= sizeof(int32_t);
193 for (channel = 0; length; length--) {
194 int64_t t;
196 t = (int64_t) PA_INT32_SWAP(*samples);
197 t = (t * volumes[channel]) >> 16;
198 t = PA_CLAMP_UNLIKELY(t, -0x80000000LL, 0x7FFFFFFFLL);
199 *samples++ = PA_INT32_SWAP((int32_t) t);
201 if (PA_UNLIKELY(++channel >= channels))
202 channel = 0;
206 static void pa_volume_s24ne_c(uint8_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
207 unsigned channel;
208 uint8_t *e;
210 e = samples + length;
212 for (channel = 0; samples < e; samples += 3) {
213 int64_t t;
215 t = (int64_t)((int32_t) (PA_READ24NE(samples) << 8));
216 t = (t * volumes[channel]) >> 16;
217 t = PA_CLAMP_UNLIKELY(t, -0x80000000LL, 0x7FFFFFFFLL);
218 PA_WRITE24NE(samples, ((uint32_t) (int32_t) t) >> 8);
220 if (PA_UNLIKELY(++channel >= channels))
221 channel = 0;
225 static void pa_volume_s24re_c(uint8_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
226 unsigned channel;
227 uint8_t *e;
229 e = samples + length;
231 for (channel = 0; samples < e; samples += 3) {
232 int64_t t;
234 t = (int64_t)((int32_t) (PA_READ24RE(samples) << 8));
235 t = (t * volumes[channel]) >> 16;
236 t = PA_CLAMP_UNLIKELY(t, -0x80000000LL, 0x7FFFFFFFLL);
237 PA_WRITE24RE(samples, ((uint32_t) (int32_t) t) >> 8);
239 if (PA_UNLIKELY(++channel >= channels))
240 channel = 0;
244 static void pa_volume_s24_32ne_c(uint32_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
245 unsigned channel;
247 length /= sizeof(uint32_t);
249 for (channel = 0; length; length--) {
250 int64_t t;
252 t = (int64_t) ((int32_t) (*samples << 8));
253 t = (t * volumes[channel]) >> 16;
254 t = PA_CLAMP_UNLIKELY(t, -0x80000000LL, 0x7FFFFFFFLL);
255 *samples++ = ((uint32_t) ((int32_t) t)) >> 8;
257 if (PA_UNLIKELY(++channel >= channels))
258 channel = 0;
262 static void pa_volume_s24_32re_c(uint32_t *samples, int32_t *volumes, unsigned channels, unsigned length) {
263 unsigned channel;
265 length /= sizeof(uint32_t);
267 for (channel = 0; length; length--) {
268 int64_t t;
270 t = (int64_t) ((int32_t) (PA_UINT32_SWAP(*samples) << 8));
271 t = (t * volumes[channel]) >> 16;
272 t = PA_CLAMP_UNLIKELY(t, -0x80000000LL, 0x7FFFFFFFLL);
273 *samples++ = PA_UINT32_SWAP(((uint32_t) ((int32_t) t)) >> 8);
275 if (PA_UNLIKELY(++channel >= channels))
276 channel = 0;
280 static pa_do_volume_func_t do_volume_table[] = {
281 [PA_SAMPLE_U8] = (pa_do_volume_func_t) pa_volume_u8_c,
282 [PA_SAMPLE_ALAW] = (pa_do_volume_func_t) pa_volume_alaw_c,
283 [PA_SAMPLE_ULAW] = (pa_do_volume_func_t) pa_volume_ulaw_c,
284 [PA_SAMPLE_S16NE] = (pa_do_volume_func_t) pa_volume_s16ne_c,
285 [PA_SAMPLE_S16RE] = (pa_do_volume_func_t) pa_volume_s16re_c,
286 [PA_SAMPLE_FLOAT32NE] = (pa_do_volume_func_t) pa_volume_float32ne_c,
287 [PA_SAMPLE_FLOAT32RE] = (pa_do_volume_func_t) pa_volume_float32re_c,
288 [PA_SAMPLE_S32NE] = (pa_do_volume_func_t) pa_volume_s32ne_c,
289 [PA_SAMPLE_S32RE] = (pa_do_volume_func_t) pa_volume_s32re_c,
290 [PA_SAMPLE_S24NE] = (pa_do_volume_func_t) pa_volume_s24ne_c,
291 [PA_SAMPLE_S24RE] = (pa_do_volume_func_t) pa_volume_s24re_c,
292 [PA_SAMPLE_S24_32NE] = (pa_do_volume_func_t) pa_volume_s24_32ne_c,
293 [PA_SAMPLE_S24_32RE] = (pa_do_volume_func_t) pa_volume_s24_32re_c
296 pa_do_volume_func_t pa_get_volume_func(pa_sample_format_t f) {
297 pa_assert(f >= 0);
298 pa_assert(f < PA_SAMPLE_MAX);
300 return do_volume_table[f];
303 void pa_set_volume_func(pa_sample_format_t f, pa_do_volume_func_t func) {
304 pa_assert(f >= 0);
305 pa_assert(f < PA_SAMPLE_MAX);
307 do_volume_table[f] = func;