Line | Count | Source (jump to first uncovered line) |
1 | | /* Copyright (c) 2011 Xiph.Org Foundation, Skype Limited |
2 | | Written by Jean-Marc Valin and Koen Vos */ |
3 | | /* |
4 | | Redistribution and use in source and binary forms, with or without |
5 | | modification, are permitted provided that the following conditions |
6 | | are met: |
7 | | |
8 | | - Redistributions of source code must retain the above copyright |
9 | | notice, this list of conditions and the following disclaimer. |
10 | | |
11 | | - Redistributions in binary form must reproduce the above copyright |
12 | | notice, this list of conditions and the following disclaimer in the |
13 | | documentation and/or other materials provided with the distribution. |
14 | | |
15 | | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
16 | | ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
17 | | LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
18 | | A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER |
19 | | OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, |
20 | | EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, |
21 | | PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR |
22 | | PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF |
23 | | LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING |
24 | | NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
25 | | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
26 | | */ |
27 | | |
28 | | #ifdef HAVE_CONFIG_H |
29 | | #include "config.h" |
30 | | #endif |
31 | | |
32 | | #include "opus.h" |
33 | | #include "opus_private.h" |
34 | | |
35 | | #ifndef DISABLE_FLOAT_API |
36 | | OPUS_EXPORT void opus_pcm_soft_clip(float *_x, int N, int C, float *declip_mem) |
37 | 37.1k | { |
38 | 37.1k | int c; |
39 | 37.1k | int i; |
40 | 37.1k | float *x; |
41 | | |
42 | 37.1k | if (C<1 || N<1 || !_x || !declip_mem) return; |
43 | | |
44 | | /* First thing: saturate everything to +/- 2 which is the highest level our |
45 | | non-linearity can handle. At the point where the signal reaches +/-2, |
46 | | the derivative will be zero anyway, so this doesn't introduce any |
47 | | discontinuity in the derivative. */ |
48 | 49.8M | for (i=0;i<N*C;i++) |
49 | 49.8M | _x[i] = MAX16(-2.f, MIN16(2.f, _x[i])); |
50 | 90.5k | for (c=0;c<C;c++) |
51 | 53.4k | { |
52 | 53.4k | float a; |
53 | 53.4k | float x0; |
54 | 53.4k | int curr; |
55 | | |
56 | 53.4k | x = _x+c; |
57 | 53.4k | a = declip_mem[c]; |
58 | | /* Continue applying the non-linearity from the previous frame to avoid |
59 | | any discontinuity. */ |
60 | 53.4k | for (i=0;i<N;i++) |
61 | 53.4k | { |
62 | 53.4k | if (x[i*C]*a>=0) |
63 | 53.4k | break; |
64 | 0 | x[i*C] = x[i*C]+a*x[i*C]*x[i*C]; |
65 | 0 | } |
66 | | |
67 | 53.4k | curr=0; |
68 | 53.4k | x0 = x[0]; |
69 | 133k | while(1) |
70 | 133k | { |
71 | 133k | int start, end; |
72 | 133k | float maxval; |
73 | 133k | int special=0; |
74 | 133k | int peak_pos; |
75 | 49.0M | for (i=curr;i<N;i++) |
76 | 49.0M | { |
77 | 49.0M | if (x[i*C]>1 || x[i*C]<-1) |
78 | 81.4k | break; |
79 | 49.0M | } |
80 | 133k | if (i==N) |
81 | 51.7k | { |
82 | 51.7k | a=0; |
83 | 51.7k | break; |
84 | 51.7k | } |
85 | 81.4k | peak_pos = i; |
86 | 81.4k | start=end=i; |
87 | 81.4k | maxval=ABS16(x[i*C]); |
88 | | /* Look for first zero crossing before clipping */ |
89 | 212k | while (start>0 && x[i*C]*x[(start-1)*C]>=0) |
90 | 130k | start--; |
91 | | /* Look for first zero crossing after clipping */ |
92 | 960k | while (end<N && x[i*C]*x[end*C]>=0) |
93 | 878k | { |
94 | | /* Look for other peaks until the next zero-crossing. */ |
95 | 878k | if (ABS16(x[end*C])>maxval) |
96 | 27.7k | { |
97 | 27.7k | maxval = ABS16(x[end*C]); |
98 | 27.7k | peak_pos = end; |
99 | 27.7k | } |
100 | 878k | end++; |
101 | 878k | } |
102 | | /* Detect the special case where we clip before the first zero crossing */ |
103 | 81.4k | special = (start==0 && x[i*C]*x[0]>=0); |
104 | | |
105 | | /* Compute a such that maxval + a*maxval^2 = 1 */ |
106 | 81.4k | a=(maxval-1)/(maxval*maxval); |
107 | | /* Slightly boost "a" by 2^-22. This is just enough to ensure -ffast-math |
108 | | does not cause output values larger than +/-1, but small enough not |
109 | | to matter even for 24-bit output. */ |
110 | 81.4k | a += a*2.4e-7f; |
111 | 81.4k | if (x[i*C]>0) |
112 | 40.8k | a = -a; |
113 | | /* Apply soft clipping */ |
114 | 1.09M | for (i=start;i<end;i++) |
115 | 1.00M | x[i*C] = x[i*C]+a*x[i*C]*x[i*C]; |
116 | | |
117 | 81.4k | if (special && peak_pos>=2) |
118 | 525 | { |
119 | | /* Add a linear ramp from the first sample to the signal peak. |
120 | | This avoids a discontinuity at the beginning of the frame. */ |
121 | 525 | float delta; |
122 | 525 | float offset = x0-x[0]; |
123 | 525 | delta = offset / peak_pos; |
124 | 48.4k | for (i=curr;i<peak_pos;i++) |
125 | 47.9k | { |
126 | 47.9k | offset -= delta; |
127 | 47.9k | x[i*C] += offset; |
128 | 47.9k | x[i*C] = MAX16(-1.f, MIN16(1.f, x[i*C])); |
129 | 47.9k | } |
130 | 525 | } |
131 | 81.4k | curr = end; |
132 | 81.4k | if (curr==N) |
133 | 1.61k | break; |
134 | 81.4k | } |
135 | 53.4k | declip_mem[c] = a; |
136 | 53.4k | } |
137 | 37.1k | } |
138 | | #endif |
139 | | |
140 | | int encode_size(int size, unsigned char *data) |
141 | 2.85M | { |
142 | 2.85M | if (size < 252) |
143 | 2.84M | { |
144 | 2.84M | data[0] = size; |
145 | 2.84M | return 1; |
146 | 2.84M | } else { |
147 | 10.0k | data[0] = 252+(size&0x3); |
148 | 10.0k | data[1] = (size-(int)data[0])>>2; |
149 | 10.0k | return 2; |
150 | 10.0k | } |
151 | 2.85M | } |
152 | | |
153 | | static int parse_size(const unsigned char *data, opus_int32 len, opus_int16 *size) |
154 | 680k | { |
155 | 680k | if (len<1) |
156 | 795 | { |
157 | 795 | *size = -1; |
158 | 795 | return -1; |
159 | 679k | } else if (data[0]<252) |
160 | 672k | { |
161 | 672k | *size = data[0]; |
162 | 672k | return 1; |
163 | 672k | } else if (len<2) |
164 | 285 | { |
165 | 285 | *size = -1; |
166 | 285 | return -1; |
167 | 6.08k | } else { |
168 | 6.08k | *size = 4*data[1] + data[0]; |
169 | 6.08k | return 2; |
170 | 6.08k | } |
171 | 680k | } |
172 | | |
173 | | int opus_packet_get_samples_per_frame(const unsigned char *data, |
174 | | opus_int32 Fs) |
175 | 52.1M | { |
176 | 52.1M | int audiosize; |
177 | 52.1M | if (data[0]&0x80) |
178 | 12.7M | { |
179 | 12.7M | audiosize = ((data[0]>>3)&0x3); |
180 | 12.7M | audiosize = (Fs<<audiosize)/400; |
181 | 39.3M | } else if ((data[0]&0x60) == 0x60) |
182 | 4.53M | { |
183 | 4.53M | audiosize = (data[0]&0x08) ? Fs/50 : Fs/100; |
184 | 34.8M | } else { |
185 | 34.8M | audiosize = ((data[0]>>3)&0x3); |
186 | 34.8M | if (audiosize == 3) |
187 | 2.78M | audiosize = Fs*60/1000; |
188 | 32.0M | else |
189 | 32.0M | audiosize = (Fs<<audiosize)/100; |
190 | 34.8M | } |
191 | 52.1M | return audiosize; |
192 | 52.1M | } |
193 | | |
194 | | int opus_packet_parse_impl(const unsigned char *data, opus_int32 len, |
195 | | int self_delimited, unsigned char *out_toc, |
196 | | const unsigned char *frames[48], opus_int16 size[48], |
197 | | int *payload_offset, opus_int32 *packet_offset, |
198 | | const unsigned char **padding, opus_int32 *padding_len) |
199 | 32.9M | { |
200 | 32.9M | int i, bytes; |
201 | 32.9M | int count; |
202 | 32.9M | int cbr; |
203 | 32.9M | unsigned char ch, toc; |
204 | 32.9M | int framesize; |
205 | 32.9M | opus_int32 last_size; |
206 | 32.9M | opus_int32 pad = 0; |
207 | 32.9M | const unsigned char *data0 = data; |
208 | | |
209 | 32.9M | if (size==NULL || len<0) |
210 | 0 | return OPUS_BAD_ARG; |
211 | 32.9M | if (len==0) |
212 | 0 | return OPUS_INVALID_PACKET; |
213 | | |
214 | 32.9M | framesize = opus_packet_get_samples_per_frame(data, 48000); |
215 | | |
216 | 32.9M | cbr = 0; |
217 | 32.9M | toc = *data++; |
218 | 32.9M | len--; |
219 | 32.9M | last_size = len; |
220 | 32.9M | switch (toc&0x3) |
221 | 32.9M | { |
222 | | /* One frame */ |
223 | 29.8M | case 0: |
224 | 29.8M | count=1; |
225 | 29.8M | break; |
226 | | /* Two CBR frames */ |
227 | 49.1k | case 1: |
228 | 49.1k | count=2; |
229 | 49.1k | cbr = 1; |
230 | 49.1k | if (!self_delimited) |
231 | 9.74k | { |
232 | 9.74k | if (len&0x1) |
233 | 145 | return OPUS_INVALID_PACKET; |
234 | 9.59k | last_size = len/2; |
235 | | /* If last_size doesn't fit in size[0], we'll catch it later */ |
236 | 9.59k | size[0] = (opus_int16)last_size; |
237 | 9.59k | } |
238 | 48.9k | break; |
239 | | /* Two VBR frames */ |
240 | 83.0k | case 2: |
241 | 83.0k | count = 2; |
242 | 83.0k | bytes = parse_size(data, len, size); |
243 | 83.0k | len -= bytes; |
244 | 83.0k | if (size[0]<0 || size[0] > len) |
245 | 1.09k | return OPUS_INVALID_PACKET; |
246 | 81.9k | data += bytes; |
247 | 81.9k | last_size = len-size[0]; |
248 | 81.9k | break; |
249 | | /* Multiple CBR/VBR frames (from 0 to 120 ms) */ |
250 | 3.02M | default: /*case 3:*/ |
251 | 3.02M | if (len<1) |
252 | 20 | return OPUS_INVALID_PACKET; |
253 | | /* Number of frames encoded in bits 0 to 5 */ |
254 | 3.02M | ch = *data++; |
255 | 3.02M | count = ch&0x3F; |
256 | 3.02M | if (count <= 0 || framesize*(opus_int32)count > 5760) |
257 | 61 | return OPUS_INVALID_PACKET; |
258 | 3.02M | len--; |
259 | | /* Padding flag is bit 6 */ |
260 | 3.02M | if (ch&0x40) |
261 | 2.93M | { |
262 | 2.93M | int p; |
263 | 3.06M | do { |
264 | 3.06M | int tmp; |
265 | 3.06M | if (len<=0) |
266 | 387 | return OPUS_INVALID_PACKET; |
267 | 3.06M | p = *data++; |
268 | 3.06M | len--; |
269 | 3.06M | tmp = p==255 ? 254: p; |
270 | 3.06M | len -= tmp; |
271 | 3.06M | pad += tmp; |
272 | 3.06M | } while (p==255); |
273 | 2.93M | } |
274 | 3.02M | if (len<0) |
275 | 250 | return OPUS_INVALID_PACKET; |
276 | | /* VBR flag is bit 7 */ |
277 | 3.02M | cbr = !(ch&0x80); |
278 | 3.02M | if (!cbr) |
279 | 39.3k | { |
280 | | /* VBR case */ |
281 | 39.3k | last_size = len; |
282 | 416k | for (i=0;i<count-1;i++) |
283 | 378k | { |
284 | 378k | bytes = parse_size(data, len, size+i); |
285 | 378k | len -= bytes; |
286 | 378k | if (size[i]<0 || size[i] > len) |
287 | 778 | return OPUS_INVALID_PACKET; |
288 | 377k | data += bytes; |
289 | 377k | last_size -= bytes+size[i]; |
290 | 377k | } |
291 | 38.5k | if (last_size<0) |
292 | 308 | return OPUS_INVALID_PACKET; |
293 | 2.98M | } else if (!self_delimited) |
294 | 2.97M | { |
295 | | /* CBR case */ |
296 | 2.97M | last_size = len/count; |
297 | 2.97M | if (last_size*count!=len) |
298 | 228 | return OPUS_INVALID_PACKET; |
299 | 3.09M | for (i=0;i<count-1;i++) |
300 | 110k | size[i] = (opus_int16)last_size; |
301 | 2.97M | } |
302 | 3.02M | break; |
303 | 32.9M | } |
304 | | /* Self-delimited framing has an extra size for the last frame. */ |
305 | 32.9M | if (self_delimited) |
306 | 218k | { |
307 | 218k | bytes = parse_size(data, len, size+count-1); |
308 | 218k | len -= bytes; |
309 | 218k | if (size[count-1]<0 || size[count-1] > len) |
310 | 110 | return OPUS_INVALID_PACKET; |
311 | 218k | data += bytes; |
312 | | /* For CBR packets, apply the size to all the frames. */ |
313 | 218k | if (cbr) |
314 | 47.3k | { |
315 | 47.3k | if (size[count-1]*count > len) |
316 | 75 | return OPUS_INVALID_PACKET; |
317 | 122k | for (i=0;i<count-1;i++) |
318 | 74.7k | size[i] = size[count-1]; |
319 | 171k | } else if (bytes+size[count-1] > last_size) |
320 | 24 | return OPUS_INVALID_PACKET; |
321 | 218k | } else |
322 | 32.7M | { |
323 | | /* Because it's not encoded explicitly, it's possible the size of the |
324 | | last packet (or all the packets, for the CBR case) is larger than |
325 | | 1275. Reject them here.*/ |
326 | 32.7M | if (last_size > 1275) |
327 | 374 | return OPUS_INVALID_PACKET; |
328 | 32.7M | size[count-1] = (opus_int16)last_size; |
329 | 32.7M | } |
330 | | |
331 | 32.9M | if (payload_offset) |
332 | 130k | *payload_offset = (int)(data-data0); |
333 | | |
334 | 66.6M | for (i=0;i<count;i++) |
335 | 33.6M | { |
336 | 33.6M | if (frames) |
337 | 32.8M | frames[i] = data; |
338 | 33.6M | data += size[i]; |
339 | 33.6M | } |
340 | | |
341 | 32.9M | if (padding != NULL) |
342 | 32.7M | { |
343 | 32.7M | *padding = data; |
344 | 32.7M | *padding_len = pad; |
345 | 32.7M | } |
346 | 32.9M | if (packet_offset) |
347 | 264k | *packet_offset = pad+(opus_int32)(data-data0); |
348 | | |
349 | 32.9M | if (out_toc) |
350 | 32.9M | *out_toc = toc; |
351 | | |
352 | 32.9M | return count; |
353 | 32.9M | } |
354 | | |
355 | | int opus_packet_parse(const unsigned char *data, opus_int32 len, |
356 | | unsigned char *out_toc, const unsigned char *frames[48], |
357 | | opus_int16 size[48], int *payload_offset) |
358 | 0 | { |
359 | 0 | return opus_packet_parse_impl(data, len, 0, out_toc, |
360 | 0 | frames, size, payload_offset, NULL, NULL, NULL); |
361 | 0 | } |
362 | | |