OLD | NEW |
1 /* | 1 /* |
2 * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
11 /* | 11 /* |
12 * entropy_coding.c | 12 * entropy_coding.c |
13 * | 13 * |
14 * This file contains all functions used to arithmetically | 14 * This file contains all functions used to arithmetically |
15 * encode the iSAC bistream. | 15 * encode the iSAC bistream. |
16 * | 16 * |
17 */ | 17 */ |
18 | 18 |
19 #include <stddef.h> | 19 #include <stddef.h> |
20 | 20 |
21 #include "arith_routins.h" | 21 #include "arith_routins.h" |
22 #include "spectrum_ar_model_tables.h" | 22 #include "spectrum_ar_model_tables.h" |
23 #include "pitch_gain_tables.h" | 23 #include "pitch_gain_tables.h" |
24 #include "pitch_lag_tables.h" | 24 #include "pitch_lag_tables.h" |
25 #include "entropy_coding.h" | 25 #include "entropy_coding.h" |
26 #include "lpc_tables.h" | 26 #include "lpc_tables.h" |
27 #include "settings.h" | 27 #include "settings.h" |
28 #include "signal_processing_library.h" | 28 #include "signal_processing_library.h" |
| 29 #include "webrtc/base/checks.h" |
29 | 30 |
30 /* | 31 /* |
31 * Eenumerations for arguments to functions WebRtcIsacfix_MatrixProduct1() | 32 * Eenumerations for arguments to functions WebRtcIsacfix_MatrixProduct1() |
32 * and WebRtcIsacfix_MatrixProduct2(). | 33 * and WebRtcIsacfix_MatrixProduct2(). |
33 */ | 34 */ |
34 | 35 |
35 enum matrix_index_factor { | 36 enum matrix_index_factor { |
36 kTIndexFactor1 = 1, | 37 kTIndexFactor1 = 1, |
37 kTIndexFactor2 = 2, | 38 kTIndexFactor2 = 2, |
38 kTIndexFactor3 = SUBFRAMES, | 39 kTIndexFactor3 = SUBFRAMES, |
(...skipping 184 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
223 for (n = k; n < AR_ORDER+1; n++) | 224 for (n = k; n < AR_ORDER+1; n++) |
224 sum += WEBRTC_SPL_MUL(ARCoefQ12[n-k], ARCoefQ12[n]); /* Q24 */ | 225 sum += WEBRTC_SPL_MUL(ARCoefQ12[n-k], ARCoefQ12[n]); /* Q24 */ |
225 sum >>= 15; | 226 sum >>= 15; |
226 CorrQ11[k] = (sum * tmpGain + round) >> shftVal; | 227 CorrQ11[k] = (sum * tmpGain + round) >> shftVal; |
227 } | 228 } |
228 sum = CorrQ11[0] << 7; | 229 sum = CorrQ11[0] << 7; |
229 for (n = 0; n < FRAMESAMPLES/8; n++) | 230 for (n = 0; n < FRAMESAMPLES/8; n++) |
230 CurveQ16[n] = sum; | 231 CurveQ16[n] = sum; |
231 | 232 |
232 for (k = 1; k < AR_ORDER; k += 2) { | 233 for (k = 1; k < AR_ORDER; k += 2) { |
233 for (n = 0; n < FRAMESAMPLES/8; n++) | 234 for (n = 0; n < FRAMESAMPLES/8; n++) { |
234 CurveQ16[n] += (WebRtcIsacfix_kCos[k][n] * CorrQ11[k + 1] + 2) >> 2; | 235 const int64_t p = |
| 236 (WebRtcIsacfix_kCos[k][n] * (int64_t)CorrQ11[k + 1] + 2) >> 2; |
| 237 RTC_DCHECK_EQ(p, (int32_t)p); // p fits in 32 bits |
| 238 CurveQ16[n] += (int32_t)p; |
| 239 } |
235 } | 240 } |
236 | 241 |
237 CS_ptrQ9 = WebRtcIsacfix_kCos[0]; | 242 CS_ptrQ9 = WebRtcIsacfix_kCos[0]; |
238 | 243 |
239 /* If CorrQ11[1] too large we avoid getting overflow in the calculation by shi
fting */ | 244 /* If CorrQ11[1] too large we avoid getting overflow in the calculation by shi
fting */ |
240 sh=WebRtcSpl_NormW32(CorrQ11[1]); | 245 sh=WebRtcSpl_NormW32(CorrQ11[1]); |
241 if (CorrQ11[1]==0) /* Use next correlation */ | 246 if (CorrQ11[1]==0) /* Use next correlation */ |
242 sh=WebRtcSpl_NormW32(CorrQ11[2]); | 247 sh=WebRtcSpl_NormW32(CorrQ11[2]); |
243 | 248 |
244 if (sh<9) | 249 if (sh<9) |
245 shftVal = 9 - sh; | 250 shftVal = 9 - sh; |
246 else | 251 else |
247 shftVal = 0; | 252 shftVal = 0; |
248 | 253 |
249 for (n = 0; n < FRAMESAMPLES/8; n++) | 254 for (n = 0; n < FRAMESAMPLES/8; n++) |
250 diffQ16[n] = (CS_ptrQ9[n] * (CorrQ11[1] >> shftVal) + 2) >> 2; | 255 diffQ16[n] = (CS_ptrQ9[n] * (CorrQ11[1] >> shftVal) + 2) >> 2; |
251 for (k = 2; k < AR_ORDER; k += 2) { | 256 for (k = 2; k < AR_ORDER; k += 2) { |
252 CS_ptrQ9 = WebRtcIsacfix_kCos[k]; | 257 CS_ptrQ9 = WebRtcIsacfix_kCos[k]; |
253 for (n = 0; n < FRAMESAMPLES/8; n++) | 258 for (n = 0; n < FRAMESAMPLES/8; n++) |
254 diffQ16[n] += (CS_ptrQ9[n] * (CorrQ11[k + 1] >> shftVal) + 2) >> 2; | 259 diffQ16[n] += (CS_ptrQ9[n] * (CorrQ11[k + 1] >> shftVal) + 2) >> 2; |
255 } | 260 } |
256 | 261 |
257 for (k=0; k<FRAMESAMPLES/8; k++) { | 262 for (k=0; k<FRAMESAMPLES/8; k++) { |
258 int32_t diff_q16 = diffQ16[k] * (1 << shftVal); | 263 int32_t diff_q16 = diffQ16[k] * (1 << shftVal); |
259 CurveQ16[FRAMESAMPLES / 4 - 1 - k] = CurveQ16[k] - diff_q16; | 264 CurveQ16[FRAMESAMPLES / 4 - 1 - k] = |
260 CurveQ16[k] += diff_q16; | 265 WebRtcSpl_SubSatW32(CurveQ16[k], diff_q16); |
| 266 CurveQ16[k] = WebRtcSpl_AddSatW32(CurveQ16[k], diff_q16); |
261 } | 267 } |
262 } | 268 } |
263 | 269 |
264 static void CalcRootInvArSpec(const int16_t *ARCoefQ12, | 270 static void CalcRootInvArSpec(const int16_t *ARCoefQ12, |
265 const int32_t gainQ10, | 271 const int32_t gainQ10, |
266 uint16_t *CurveQ8) | 272 uint16_t *CurveQ8) |
267 { | 273 { |
268 int32_t CorrQ11[AR_ORDER+1]; | 274 int32_t CorrQ11[AR_ORDER+1]; |
269 int32_t sum, tmpGain; | 275 int32_t sum, tmpGain; |
270 int32_t summQ16[FRAMESAMPLES/8]; | 276 int32_t summQ16[FRAMESAMPLES/8]; |
(...skipping 214 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
485 len = WebRtcIsacfix_DecLogisticMulti2(data, streamdata, invARSpec2_Q16, (int16
_t)FRAMESAMPLES); | 491 len = WebRtcIsacfix_DecLogisticMulti2(data, streamdata, invARSpec2_Q16, (int16
_t)FRAMESAMPLES); |
486 | 492 |
487 if (len<1) | 493 if (len<1) |
488 return -ISAC_RANGE_ERROR_DECODE_SPECTRUM; | 494 return -ISAC_RANGE_ERROR_DECODE_SPECTRUM; |
489 | 495 |
490 /* subtract dither and scale down spectral samples with low SNR */ | 496 /* subtract dither and scale down spectral samples with low SNR */ |
491 if (AvgPitchGain_Q12 <= 614) | 497 if (AvgPitchGain_Q12 <= 614) |
492 { | 498 { |
493 for (k = 0; k < FRAMESAMPLES; k += 4) | 499 for (k = 0; k < FRAMESAMPLES; k += 4) |
494 { | 500 { |
495 gainQ10 = WebRtcSpl_DivW32W16ResW16(30 << 10, | 501 gainQ10 = WebRtcSpl_DivW32W16ResW16( |
496 (int16_t)((uint32_t)(invARSpec2_Q16[k >> 2] + 2195456) >> 16)); | 502 30 << 10, (int16_t)((uint32_t)(WebRtcSpl_AddSatW32( |
| 503 invARSpec2_Q16[k >> 2], 2195456)) >> |
| 504 16)); |
497 *frQ7++ = (int16_t)((data[k] * gainQ10 + 512) >> 10); | 505 *frQ7++ = (int16_t)((data[k] * gainQ10 + 512) >> 10); |
498 *fiQ7++ = (int16_t)((data[k + 1] * gainQ10 + 512) >> 10); | 506 *fiQ7++ = (int16_t)((data[k + 1] * gainQ10 + 512) >> 10); |
499 *frQ7++ = (int16_t)((data[k + 2] * gainQ10 + 512) >> 10); | 507 *frQ7++ = (int16_t)((data[k + 2] * gainQ10 + 512) >> 10); |
500 *fiQ7++ = (int16_t)((data[k + 3] * gainQ10 + 512) >> 10); | 508 *fiQ7++ = (int16_t)((data[k + 3] * gainQ10 + 512) >> 10); |
501 } | 509 } |
502 } | 510 } |
503 else | 511 else |
504 { | 512 { |
505 for (k = 0; k < FRAMESAMPLES; k += 4) | 513 for (k = 0; k < FRAMESAMPLES; k += 4) |
506 { | 514 { |
507 gainQ10 = WebRtcSpl_DivW32W16ResW16(36 << 10, | 515 gainQ10 = WebRtcSpl_DivW32W16ResW16( |
508 (int16_t)((uint32_t)(invARSpec2_Q16[k >> 2] + 2654208) >> 16)); | 516 36 << 10, (int16_t)((uint32_t)(WebRtcSpl_AddSatW32( |
| 517 invARSpec2_Q16[k >> 2], 2654208)) >> |
| 518 16)); |
509 *frQ7++ = (int16_t)((data[k] * gainQ10 + 512) >> 10); | 519 *frQ7++ = (int16_t)((data[k] * gainQ10 + 512) >> 10); |
510 *fiQ7++ = (int16_t)((data[k + 1] * gainQ10 + 512) >> 10); | 520 *fiQ7++ = (int16_t)((data[k + 1] * gainQ10 + 512) >> 10); |
511 *frQ7++ = (int16_t)((data[k + 2] * gainQ10 + 512) >> 10); | 521 *frQ7++ = (int16_t)((data[k + 2] * gainQ10 + 512) >> 10); |
512 *fiQ7++ = (int16_t)((data[k + 3] * gainQ10 + 512) >> 10); | 522 *fiQ7++ = (int16_t)((data[k + 3] * gainQ10 + 512) >> 10); |
513 } | 523 } |
514 } | 524 } |
515 | 525 |
516 return len; | 526 return len; |
517 } | 527 } |
518 | 528 |
(...skipping 1507 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2026 | 2036 |
2027 index_gQQ[k] = pos2QQ + WebRtcIsacfix_kQuantMinGain[k]; //ATTN: ok? | 2037 index_gQQ[k] = pos2QQ + WebRtcIsacfix_kQuantMinGain[k]; //ATTN: ok? |
2028 if (index_gQQ[k] < 0) { | 2038 if (index_gQQ[k] < 0) { |
2029 index_gQQ[k] = 0; | 2039 index_gQQ[k] = 0; |
2030 } | 2040 } |
2031 else if (index_gQQ[k] > WebRtcIsacfix_kMaxIndGain[k]) { | 2041 else if (index_gQQ[k] > WebRtcIsacfix_kMaxIndGain[k]) { |
2032 index_gQQ[k] = WebRtcIsacfix_kMaxIndGain[k]; | 2042 index_gQQ[k] = WebRtcIsacfix_kMaxIndGain[k]; |
2033 } | 2043 } |
2034 } | 2044 } |
2035 } | 2045 } |
OLD | NEW |