annotate qcelpdec.c @ 8130:c45366b01126 libavcodec

ARM: fix j_rev_dct_ARM This is a bugfix for ARMv4 assembly implementation of 'j_rev_dct' function. The problem was in the incorrect partially empty row detection. Even if the first two coefficients in the row were nonzero, it handled this just like the case with only the first nonzero coefficient. Now this function produces exactly the same output as the stripped down reference C version of 'j_rev_dct' (with the nested checks like 'if (d6) { if (d2) { ...' always evaluated as true, avoiding shortcut branches).
author mru
date Wed, 12 Nov 2008 20:23:36 +0000
parents 3b5256153553
children f27d01aff4af
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
8096
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
1 /*
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
2 * QCELP decoder
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
3 * Copyright (c) 2007 Reynaldo H. Verdejo Pinochet
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
4 *
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
5 * This file is part of FFmpeg.
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
6 *
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
7 * FFmpeg is free software; you can redistribute it and/or
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
8 * modify it under the terms of the GNU Lesser General Public
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
9 * License as published by the Free Software Foundation; either
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
10 * version 2.1 of the License, or (at your option) any later version.
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
11 *
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
12 * FFmpeg is distributed in the hope that it will be useful,
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
15 * Lesser General Public License for more details.
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
16 *
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
17 * You should have received a copy of the GNU Lesser General Public
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
18 * License along with FFmpeg; if not, write to the Free Software
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
20 */
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
21 /**
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
22 * @file qcelpdec.c
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
23 * QCELP decoder
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
24 * @author Reynaldo H. Verdejo Pinochet
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
25 */
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
26
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
27 #include <stddef.h>
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
28
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
29 #include "avcodec.h"
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
30 #include "bitstream.h"
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
31
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
32 #include "qcelp.h"
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
33 #include "qcelpdata.h"
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
34
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
35 #include "celp_math.h"
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
36 #include "celp_filters.h"
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
37
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
38 #undef NDEBUG
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
39 #include <assert.h>
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
40
8123
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
41 static void weighted_vector_sumf(float *out,
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
42 const float *in_a,
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
43 const float *in_b,
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
44 float weight_coeff_a,
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
45 float weight_coeff_b,
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
46 int length) {
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
47 int i;
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
48
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
49 for (i = 0; i < length; i++)
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
50 out[i] = weight_coeff_a * in_a[i]
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
51 + weight_coeff_b * in_b[i];
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
52 }
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
53
8096
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
54 /**
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
55 * Apply filter in pitch-subframe steps.
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
56 *
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
57 * @param memory buffer for the previous state of the filter
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
58 * - must be able to contain 303 elements
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
59 * - the 143 first elements are from the previous state
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
60 * - the next 160 are for output
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
61 * @param v_in input filter vector
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
62 * @param gain per-subframe gain array, each element is between 0.0 and 2.0
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
63 * @param lag per-subframe lag array, each element is
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
64 * - between 16 and 143 if its corresponding pfrac is 0,
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
65 * - between 16 and 139 otherwise
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
66 * @param pfrac per-subframe boolean array, 1 if the lag is fractional, 0 otherwise
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
67 *
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
68 * @return filter output vector
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
69 */
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
70 static const float *do_pitchfilter(float memory[303],
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
71 const float v_in[160],
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
72 const float gain[4],
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
73 const uint8_t *lag,
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
74 const uint8_t pfrac[4]) {
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
75 int i, j;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
76 float *v_lag, *v_out;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
77 const float *v_len;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
78
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
79 v_out = memory + 143; // Output vector starts at memory[143].
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
80
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
81 for (i = 0; i < 4; i++)
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
82 if (gain[i]) {
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
83 v_lag = memory + 143 + 40 * i - lag[i];
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
84 for (v_len = v_in + 40; v_in < v_len; v_in++) {
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
85 if (pfrac[i]) { // If it is a fractional lag...
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
86 for (j = 0, *v_out = 0.; j < 4; j++)
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
87 *v_out += qcelp_hammsinc_table[j] * (v_lag[j-4] + v_lag[3-j]);
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
88 } else
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
89 *v_out = *v_lag;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
90
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
91 *v_out = *v_in + gain[i] * *v_out;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
92
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
93 v_lag++;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
94 v_out++;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
95 }
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
96 } else {
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
97 memcpy(v_out, v_in, 40 * sizeof(float));
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
98 v_in += 40;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
99 v_out += 40;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
100 }
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
101
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
102 memmove(memory, memory + 160, 143 * sizeof(float));
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
103 return memory + 143;
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
104 }
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
105
8127
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
106 /**
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
107 * Interpolates LSP frequencies and computes LPC coefficients
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
108 * for a given framerate & pitch subframe.
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
109 *
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
110 * TIA/EIA/IS-733 2.4.3.3.4
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
111 *
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
112 * @param q the context
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
113 * @param curr_lspf LSP frequencies vector of the current frame
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
114 * @param lpc float vector for the resulting LPC
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
115 * @param subframe_num frame number in decoded stream
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
116 */
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
117 void interpolate_lpc(QCELPContext *q,
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
118 const float *curr_lspf,
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
119 float *lpc,
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
120 const int subframe_num) {
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
121 float interpolated_lspf[10];
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
122 float weight;
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
123
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
124 if (q->framerate >= RATE_QUARTER) {
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
125 weight = 0.25 * (subframe_num + 1);
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
126 } else if (q->framerate == RATE_OCTAVE && !subframe_num) {
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
127 weight = 0.625;
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
128 } else {
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
129 weight = 1.0;
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
130 }
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
131
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
132 if (weight != 1.0) {
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
133 weighted_vector_sumf(interpolated_lspf, curr_lspf, q->prev_lspf, weight, 1.0 - weight, 10);
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
134 lspf2lpc(q, interpolated_lspf, lpc);
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
135 } else if (q->framerate >= RATE_QUARTER || (q->framerate == I_F_Q && !subframe_num))
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
136 lspf2lpc(q, curr_lspf, lpc);
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
137 }
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
138
8123
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
139 static int buf_size2framerate(const int buf_size) {
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
140 switch (buf_size) {
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
141 case 35:
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
142 return RATE_FULL;
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
143 case 17:
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
144 return RATE_HALF;
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
145 case 8:
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
146 return RATE_QUARTER;
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
147 case 4:
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
148 return RATE_OCTAVE;
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
149 case 1:
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
150 return SILENCE;
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
151 }
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
152 return -1;
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
153 }
cd756806be02 More OKed parts of the QCELP decoder
vitor
parents: 8096
diff changeset
154
8096
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
155 static void warn_insufficient_frame_quality(AVCodecContext *avctx,
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
156 const char *message) {
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
157 av_log(avctx, AV_LOG_WARNING, "Frame #%d, IFQ: %s\n", avctx->frame_number, message);
eb55481f35fa OKed parts of the QCELP decoder
vitor
parents:
diff changeset
158 }
8127
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
159
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
160 AVCodec qcelp_decoder =
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
161 {
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
162 .name = "qcelp",
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
163 .type = CODEC_TYPE_AUDIO,
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
164 .id = CODEC_ID_QCELP,
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
165 .init = qcelp_decode_init,
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
166 .decode = qcelp_decode_frame,
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
167 .priv_data_size = sizeof(QCELPContext),
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
168 .long_name = NULL_IF_CONFIG_SMALL("QCELP / PureVoice"),
3b5256153553 More OKed parts of the QCELP decoder
vitor
parents: 8123
diff changeset
169 };