1 /*
2 * This file is part of libdcadec.
3 *
4 * This library is free software; you can redistribute it and/or modify it
5 * under the terms of the GNU Lesser General Public License as published by the
6 * Free Software Foundation; either version 2.1 of the License, or (at your
7 * option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
12 * for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public License
15 * along with this library; if not, write to the Free Software Foundation,
16 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17 */
18
19 #ifndef COMMON_H
20 #define COMMON_H
21
22 #include <stdlib.h>
23 #include <stdio.h>
24 #include <stdint.h>
25 #include <stdbool.h>
26 #include <stdarg.h>
27 #include <string.h>
28 #include <math.h>
29 #include <errno.h>
30 #include <assert.h>
31 #include <limits.h>
32
33 #include "compiler.h"
34 #include "dca_context.h"
35 #include "ta.h"
36
37 #if AT_LEAST_GCC(3, 4)
38 #define dca_clz(x) __builtin_clz(x)
39 #else
dca_clz(uint32_t x)40 static inline int dca_clz(uint32_t x)
41 {
42 int r = 0;
43
44 assert(x);
45 if (x & 0xffff0000) { x >>= 16; r |= 16; }
46 if (x & 0x0000ff00) { x >>= 8; r |= 8; }
47 if (x & 0x000000f0) { x >>= 4; r |= 4; }
48 if (x & 0x0000000c) { x >>= 2; r |= 2; }
49 if (x & 0x00000002) { x >>= 1; r |= 1; }
50
51 return 31 - r;
52 }
53 #endif
54
55 #if (defined __GNUC__) && (defined __POPCNT__)
56 #define dca_popcount(x) __builtin_popcount(x)
57 #else
dca_popcount(uint32_t x)58 static inline int dca_popcount(uint32_t x)
59 {
60 x -= (x >> 1) & 0x55555555;
61 x = (x & 0x33333333) + ((x >> 2) & 0x33333333);
62 x = (x + (x >> 4)) & 0x0f0f0f0f;
63 x += x >> 8;
64 return (x + (x >> 16)) & 0x3f;
65 }
66 #endif
67
68 #define dca_countof(x) (sizeof(x) / sizeof((x)[0]))
69
70 #if AT_LEAST_GCC(4, 8)
71 #define dca_bswap16(x) __builtin_bswap16(x)
72 #else
dca_bswap16(uint16_t x)73 static inline uint16_t dca_bswap16(uint16_t x)
74 {
75 return (x << 8) | (x >> 8);
76 }
77 #endif
78
79 #if AT_LEAST_GCC(4, 3)
80 #define dca_bswap32(x) __builtin_bswap32(x)
81 #define dca_bswap64(x) __builtin_bswap64(x)
82 #else
dca_bswap32(uint32_t x)83 static inline uint32_t dca_bswap32(uint32_t x)
84 {
85 x = ((x & 0x00ff00ff) << 8) | ((x & 0xff00ff00) >> 8);
86 return (x << 16) | (x >> 16);
87 }
88
dca_bswap64(uint64_t x)89 static inline uint64_t dca_bswap64(uint64_t x)
90 {
91 x = ((x & 0x00ff00ff00ff00ff) << 8) | ((x & 0xff00ff00ff00ff00) >> 8);
92 x = ((x & 0x0000ffff0000ffff) << 16) | ((x & 0xffff0000ffff0000) >> 16);
93 return (x << 32) | (x >> 32);
94 }
95 #endif
96
97 #define DCA_BSWAP16_C(x) ((((x) & 0x00ff) << 8) | (((x) & 0xff00) >> 8))
98 #define DCA_BSWAP32_C(x) ((DCA_BSWAP16_C(x) << 16) | (DCA_BSWAP16_C(x >> 16)))
99 #define DCA_BSWAP64_C(x) ((DCA_BSWAP32_C(x) << 32) | (DCA_BSWAP32_C(x >> 32)))
100
101 #if HAVE_BIGENDIAN
102 #define DCA_16LE(x) dca_bswap16(x)
103 #define DCA_32LE(x) dca_bswap32(x)
104 #define DCA_64LE(x) dca_bswap64(x)
105 #define DCA_16BE(x) ((uint16_t)(x))
106 #define DCA_32BE(x) ((uint32_t)(x))
107 #define DCA_64BE(x) ((uint64_t)(x))
108 #define DCA_16LE_C(x) DCA_BSWAP16_C(x)
109 #define DCA_32LE_C(x) DCA_BSWAP32_C(x)
110 #define DCA_64LE_C(x) DCA_BSWAP64_C(x)
111 #define DCA_16BE_C(x) (x)
112 #define DCA_32BE_C(x) (x)
113 #define DCA_64BE_C(x) (x)
114 #else
115 #define DCA_16LE(x) ((uint16_t)(x))
116 #define DCA_32LE(x) ((uint32_t)(x))
117 #define DCA_64LE(x) ((uint64_t)(x))
118 #define DCA_16BE(x) dca_bswap16(x)
119 #define DCA_32BE(x) dca_bswap32(x)
120 #define DCA_64BE(x) dca_bswap64(x)
121 #define DCA_16LE_C(x) (x)
122 #define DCA_32LE_C(x) (x)
123 #define DCA_64LE_C(x) (x)
124 #define DCA_16BE_C(x) DCA_BSWAP16_C(x)
125 #define DCA_32BE_C(x) DCA_BSWAP32_C(x)
126 #define DCA_64BE_C(x) DCA_BSWAP64_C(x)
127 #endif
128
129 #define DCA_MIN(a, b) ((a) < (b) ? (a) : (b))
130 #define DCA_MAX(a, b) ((a) > (b) ? (a) : (b))
131
132 #define DCA_ALIGN(value, align) \
133 (((value) + (align) - 1) & ~((align) - 1))
134
135 #define DCA_MEM16BE(data) \
136 (((uint32_t)(data)[0] << 8) | (data)[1])
137
138 #define DCA_MEM24BE(data) \
139 (((uint32_t)(data)[0] << 16) | DCA_MEM16BE(&(data)[1]))
140
141 #define DCA_MEM32BE(data) \
142 (((uint32_t)(data)[0] << 24) | DCA_MEM24BE(&(data)[1]))
143
144 #define DCA_MEM40BE(data) \
145 (((uint64_t)(data)[0] << 32) | DCA_MEM32BE(&(data)[1]))
146
DCA_MEM32NE(const void * data)147 static inline uint32_t DCA_MEM32NE(const void *data)
148 {
149 uint32_t res;
150 memcpy(&res, data, sizeof(res));
151 return res;
152 }
153
154 void dca_format_log(struct dcadec_context *dca, int level,
155 const char *file, int line, const char *fmt, ...)
156 __attribute__((format(printf, 5, 6)));
157
158 #define DCADEC_LOG_ONCE 0x80000000
159
160 #define dca_log(obj, lvl, ...) \
161 dca_format_log((obj)->ctx, DCADEC_LOG_##lvl, __FILE__, __LINE__, __VA_ARGS__)
162
163 #define dca_log_once(obj, lvl, ...) \
164 dca_format_log((obj)->ctx, DCADEC_LOG_##lvl | DCADEC_LOG_ONCE, __FILE__, __LINE__, __VA_ARGS__)
165
166 #define DCADEC_FLAG_KEEP_DMIX_MASK \
167 (DCADEC_FLAG_KEEP_DMIX_2CH | DCADEC_FLAG_KEEP_DMIX_6CH)
168
169 #define SPEAKER_LAYOUT_MONO (SPEAKER_MASK_C)
170 #define SPEAKER_LAYOUT_STEREO (SPEAKER_MASK_L | SPEAKER_MASK_R)
171 #define SPEAKER_LAYOUT_2POINT1 (SPEAKER_LAYOUT_STEREO | SPEAKER_MASK_LFE1)
172 #define SPEAKER_LAYOUT_3_0 (SPEAKER_LAYOUT_STEREO | SPEAKER_MASK_C)
173 #define SPEAKER_LAYOUT_2_1 (SPEAKER_LAYOUT_STEREO | SPEAKER_MASK_Cs)
174 #define SPEAKER_LAYOUT_3_1 (SPEAKER_LAYOUT_3_0 | SPEAKER_MASK_Cs)
175 #define SPEAKER_LAYOUT_2_2 (SPEAKER_LAYOUT_STEREO | SPEAKER_MASK_Ls | SPEAKER_MASK_Rs)
176 #define SPEAKER_LAYOUT_5POINT0 (SPEAKER_LAYOUT_3_0 | SPEAKER_MASK_Ls | SPEAKER_MASK_Rs)
177 #define SPEAKER_LAYOUT_7POINT0_WIDE (SPEAKER_LAYOUT_5POINT0 | SPEAKER_MASK_Lw | SPEAKER_MASK_Rw)
178 #define SPEAKER_LAYOUT_7POINT1_WIDE (SPEAKER_LAYOUT_7POINT0_WIDE | SPEAKER_MASK_LFE1)
179
180 enum WaveTag {
181 TAG_RIFF = 0x46464952,
182 TAG_WAVE = 0x45564157,
183 TAG_data = 0x61746164,
184 TAG_fmt = 0x20746d66
185 };
186
187 // WAVEFORMATEXTENSIBLE speakers
188 enum WaveSpeaker {
189 WAVESPKR_FL, WAVESPKR_FR, WAVESPKR_FC, WAVESPKR_LFE,
190 WAVESPKR_BL, WAVESPKR_BR, WAVESPKR_FLC, WAVESPKR_FRC,
191 WAVESPKR_BC, WAVESPKR_SL, WAVESPKR_SR, WAVESPKR_TC,
192 WAVESPKR_TFL, WAVESPKR_TFC, WAVESPKR_TFR, WAVESPKR_TBL,
193 WAVESPKR_TBC, WAVESPKR_TBR,
194
195 WAVESPKR_COUNT
196 };
197
198 // Table 6-22: Loudspeaker masks
199 enum SpeakerMask {
200 SPEAKER_MASK_C = 0x00000001,
201 SPEAKER_MASK_L = 0x00000002,
202 SPEAKER_MASK_R = 0x00000004,
203 SPEAKER_MASK_Ls = 0x00000008,
204 SPEAKER_MASK_Rs = 0x00000010,
205 SPEAKER_MASK_LFE1 = 0x00000020,
206 SPEAKER_MASK_Cs = 0x00000040,
207 SPEAKER_MASK_Lsr = 0x00000080,
208 SPEAKER_MASK_Rsr = 0x00000100,
209 SPEAKER_MASK_Lss = 0x00000200,
210 SPEAKER_MASK_Rss = 0x00000400,
211 SPEAKER_MASK_Lc = 0x00000800,
212 SPEAKER_MASK_Rc = 0x00001000,
213 SPEAKER_MASK_Lh = 0x00002000,
214 SPEAKER_MASK_Ch = 0x00004000,
215 SPEAKER_MASK_Rh = 0x00008000,
216 SPEAKER_MASK_LFE2 = 0x00010000,
217 SPEAKER_MASK_Lw = 0x00020000,
218 SPEAKER_MASK_Rw = 0x00040000,
219 SPEAKER_MASK_Oh = 0x00080000,
220 SPEAKER_MASK_Lhs = 0x00100000,
221 SPEAKER_MASK_Rhs = 0x00200000,
222 SPEAKER_MASK_Chr = 0x00400000,
223 SPEAKER_MASK_Lhr = 0x00800000,
224 SPEAKER_MASK_Rhr = 0x01000000,
225 SPEAKER_MASK_Cl = 0x02000000,
226 SPEAKER_MASK_Ll = 0x04000000,
227 SPEAKER_MASK_Rl = 0x08000000,
228 SPEAKER_MASK_RSV1 = 0x10000000,
229 SPEAKER_MASK_RSV2 = 0x20000000,
230 SPEAKER_MASK_RSV3 = 0x40000000,
231 SPEAKER_MASK_RSV4 = 0x80000000
232 };
233
234 // Table 6-22: Loudspeaker masks
235 enum Speaker {
236 SPEAKER_C, SPEAKER_L, SPEAKER_R, SPEAKER_Ls,
237 SPEAKER_Rs, SPEAKER_LFE1, SPEAKER_Cs, SPEAKER_Lsr,
238 SPEAKER_Rsr, SPEAKER_Lss, SPEAKER_Rss, SPEAKER_Lc,
239 SPEAKER_Rc, SPEAKER_Lh, SPEAKER_Ch, SPEAKER_Rh,
240 SPEAKER_LFE2, SPEAKER_Lw, SPEAKER_Rw, SPEAKER_Oh,
241 SPEAKER_Lhs, SPEAKER_Rhs, SPEAKER_Chr, SPEAKER_Lhr,
242 SPEAKER_Rhr, SPEAKER_Cl, SPEAKER_Ll, SPEAKER_Rl,
243 SPEAKER_RSV1, SPEAKER_RSV2, SPEAKER_RSV3, SPEAKER_RSV4,
244
245 SPEAKER_COUNT
246 };
247
248 // Table 7-1: Sync words
249 enum SyncWord {
250 SYNC_WORD_CORE = 0x7ffe8001,
251 SYNC_WORD_CORE_LE = 0xfe7f0180,
252 SYNC_WORD_CORE_LE14 = 0xff1f00e8,
253 SYNC_WORD_CORE_BE14 = 0x1fffe800,
254 SYNC_WORD_REV1AUX = 0x9a1105a0,
255 SYNC_WORD_REV2AUX = 0x7004c070,
256 SYNC_WORD_XCH = 0x5a5a5a5a,
257 SYNC_WORD_XXCH = 0x47004a03,
258 SYNC_WORD_X96 = 0x1d95f262,
259 SYNC_WORD_XBR = 0x655e315e,
260 SYNC_WORD_LBR = 0x0a801921,
261 SYNC_WORD_XLL = 0x41a29547,
262 SYNC_WORD_EXSS = 0x64582025,
263 SYNC_WORD_EXSS_LE = 0x58642520,
264 SYNC_WORD_CORE_EXSS = 0x02b09261,
265 };
266
267 // Table 7-10: Loudspeaker bit mask for speaker activity
268 enum SpeakerPair {
269 SPEAKER_PAIR_C = 0x0001,
270 SPEAKER_PAIR_LR = 0x0002,
271 SPEAKER_PAIR_LsRs = 0x0004,
272 SPEAKER_PAIR_LFE1 = 0x0008,
273 SPEAKER_PAIR_Cs = 0x0010,
274 SPEAKER_PAIR_LhRh = 0x0020,
275 SPEAKER_PAIR_LsrRsr = 0x0040,
276 SPEAKER_PAIR_Ch = 0x0080,
277 SPEAKER_PAIR_Oh = 0x0100,
278 SPEAKER_PAIR_LcRc = 0x0200,
279 SPEAKER_PAIR_LwRw = 0x0400,
280 SPEAKER_PAIR_LssRss = 0x0800,
281 SPEAKER_PAIR_LFE2 = 0x1000,
282 SPEAKER_PAIR_LhsRhs = 0x2000,
283 SPEAKER_PAIR_Chr = 0x4000,
284 SPEAKER_PAIR_LhrRhr = 0x8000,
285 SPEAKER_PAIR_ALL_1 = 0x5199,
286 SPEAKER_PAIR_ALL_2 = 0xae66
287 };
288
289 // Table 7-11: Representation type
290 enum RepresentationType {
291 REPR_TYPE_LtRt = 2,
292 REPR_TYPE_LhRh = 3
293 };
294
295 // Table 7-15: Core/extension mask
296 enum ExtensionMask {
297 CSS_CORE = 0x001,
298 CSS_XXCH = 0x002,
299 CSS_X96 = 0x004,
300 CSS_XCH = 0x008,
301 EXSS_CORE = 0x010,
302 EXSS_XBR = 0x020,
303 EXSS_XXCH = 0x040,
304 EXSS_X96 = 0x080,
305 EXSS_LBR = 0x100,
306 EXSS_XLL = 0x200,
307 EXSS_RSV1 = 0x400,
308 EXSS_RSV2 = 0x800
309 };
310
311 // Table 8-8: Downmix type
312 enum DownMixType {
313 DMIX_TYPE_1_0,
314 DMIX_TYPE_LoRo,
315 DMIX_TYPE_LtRt,
316 DMIX_TYPE_3_0,
317 DMIX_TYPE_2_1,
318 DMIX_TYPE_2_2,
319 DMIX_TYPE_3_1,
320
321 DMIX_TYPE_COUNT
322 };
323
324 #endif
325