Revision 39ded680

View differences:

libavcodec/qcelpdata.h
461 461
#define QCELP_RATE_HALF_CODEBOOK_RATIO 0.5
462 462

  
463 463
/**
464
 * sqrt(1.887) is the maximum of the pseudorandom
465
 * white sequence used to generate the scaled codebook
466
 * vector for framerate 1/4.
467
 *
468
 * TIA/EIA/IS-733 2.4.8.1.2
469
 */
470
#define QCELP_SQRT1887 1.373681186
471

  
472
/**
464 473
 * table for impulse response of BPF used to filter
465 474
 * the white excitation for framerate 1/4 synthesis
466 475
 *
libavcodec/qcelpdec.c
52 52
}
53 53

  
54 54
/**
55
 * Initialize the speech codec according to the specification.
56
 *
57
 * TIA/EIA/IS-733 2.4.9
58
 */
59
static av_cold int qcelp_decode_init(AVCodecContext *avctx) {
60
    QCELPContext *q = avctx->priv_data;
61
    int i;
62

  
63
    avctx->sample_fmt = SAMPLE_FMT_FLT;
64

  
65
    for (i = 0; i < 10; i++)
66
        q->prev_lspf[i] = (i + 1) / 11.;
67

  
68
    return 0;
69
}
70

  
71
/**
72
 * Computes the scaled codebook vector Cdn From INDEX and GAIN
73
 * for all rates.
74
 *
75
 * The specification lacks some information here.
76
 *
77
 * TIA/EIA/IS-733 has an omission on the codebook index determination
78
 * formula for RATE_FULL and RATE_HALF frames at section 2.4.8.1.1. It says
79
 * you have to subtract the decoded index parameter from the given scaled
80
 * codebook vector index 'n' to get the desired circular codebook index, but
81
 * it does not mention that you have to clamp 'n' to [0-9] in order to get
82
 * RI-compliant results.
83
 *
84
 * The reason for this mistake seems to be the fact they forgot to mention you
85
 * have to do these calculations per codebook subframe and adjust given
86
 * equation values accordingly.
87
 *
88
 * @param q the context
89
 * @param gain array holding the 4 pitch subframe gain values
90
 * @param cdn_vector array for the generated scaled codebook vector
91
 */
92
static void compute_svector(const QCELPContext *q,
93
                            const float *gain,
94
                            float *cdn_vector) {
95
    int      i, j, k;
96
    uint16_t cbseed, cindex;
97
    float    *rnd, tmp_gain, fir_filter_value;
98

  
99
    switch (q->framerate) {
100
    case RATE_FULL:
101
        for (i = 0; i < 16; i++) {
102
            tmp_gain = gain[i] * QCELP_RATE_FULL_CODEBOOK_RATIO;
103
            cindex = -q->cindex[i];
104
            for (j = 0; j < 10; j++)
105
                *cdn_vector++ = tmp_gain * qcelp_rate_full_codebook[cindex++ & 127];
106
        }
107
        break;
108
    case RATE_HALF:
109
        for (i = 0; i < 4; i++) {
110
            tmp_gain = gain[i] * QCELP_RATE_HALF_CODEBOOK_RATIO;
111
            cindex = -q->cindex[i];
112
            for (j = 0; j < 40; j++)
113
                *cdn_vector++ = tmp_gain * qcelp_rate_half_codebook[cindex++ & 127];
114
        }
115
        break;
116
    case RATE_QUARTER:
117
        cbseed = (0x0003 & q->lspv[4])<<14 |
118
                 (0x003F & q->lspv[3])<< 8 |
119
                 (0x0060 & q->lspv[2])<< 1 |
120
                 (0x0007 & q->lspv[1])<< 3 |
121
                 (0x0038 & q->lspv[0])>> 3 ;
122
        rnd = q->rnd_fir_filter_mem + 20;
123
        for (i = 0; i < 8; i++) {
124
            tmp_gain = gain[i] * (QCELP_SQRT1887 / 32768.0);
125
            for (k = 0; k < 20; k++) {
126
                cbseed = 521 * cbseed + 259;
127
                *rnd = (int16_t)cbseed;
128

  
129
                // FIR filter
130
                fir_filter_value = 0.0;
131
                for (j = 0; j < 10; j++)
132
                    fir_filter_value += qcelp_rnd_fir_coefs[j ] * (rnd[-j ] + rnd[-20+j]);
133
                fir_filter_value     += qcelp_rnd_fir_coefs[10] *  rnd[-10];
134

  
135
                *cdn_vector++ = tmp_gain * fir_filter_value;
136
                rnd++;
137
            }
138
        }
139
        memcpy(q->rnd_fir_filter_mem, q->rnd_fir_filter_mem + 160, 20 * sizeof(float));
140
        break;
141
    case RATE_OCTAVE:
142
        cbseed = q->first16bits;
143
        for (i = 0; i < 8; i++) {
144
            tmp_gain = gain[i] * (QCELP_SQRT1887 / 32768.0);
145
            for (j = 0; j < 20; j++) {
146
                cbseed = 521 * cbseed + 259;
147
                *cdn_vector++ = tmp_gain * (int16_t)cbseed;
148
            }
149
        }
150
        break;
151
    case I_F_Q:
152
        cbseed = -44; // random codebook index
153
        for (i = 0; i < 4; i++) {
154
            tmp_gain = gain[i] * QCELP_RATE_FULL_CODEBOOK_RATIO;
155
            for (j = 0; j < 40; j++)
156
                *cdn_vector++ = tmp_gain * qcelp_rate_full_codebook[cbseed++ & 127];
157
        }
158
        break;
159
    }
160
}
161

  
162
/**
163
 * Apply generic gain control.
164
 *
165
 * @param v_out output vector
166
 * @param v_in gain-controlled vector
167
 * @param v_ref vector to control gain of
168
 *
169
 * FIXME: If v_ref is a zero vector, it energy is zero
170
 *        and the behavior of the gain control is
171
 *        undefined in the specs.
172
 *
173
 * TIA/EIA/IS-733 2.4.8.3-2/3/4/5, 2.4.8.6
174
 */
175
static void apply_gain_ctrl(float *v_out,
176
                            const float *v_ref,
177
                            const float *v_in) {
178
    int   i, j, len;
179
    float scalefactor;
180

  
181
    for (i = 0, j = 0; i < 4; i++) {
182
        scalefactor = ff_dot_productf(v_in + j, v_in + j, 40);
183
        if (scalefactor)
184
            scalefactor = sqrt(ff_dot_productf(v_ref + j, v_ref + j, 40) / scalefactor);
185
        else
186
            av_log_missing_feature(NULL, "Zero energy for gain control", 1);
187
        for (len = j + 40; j < len; j++)
188
            v_out[j] = scalefactor * v_in[j];
189
    }
190
}
191

  
192
/**
55 193
 * Apply filter in pitch-subframe steps.
56 194
 *
57 195
 * @param memory buffer for the previous state of the filter
......
131 269

  
132 270
    if (weight != 1.0) {
133 271
        weighted_vector_sumf(interpolated_lspf, curr_lspf, q->prev_lspf, weight, 1.0 - weight, 10);
134
        lspf2lpc(q, interpolated_lspf, lpc);
272
        qcelp_lspf2lpc(interpolated_lspf, lpc);
135 273
    } else if (q->framerate >= RATE_QUARTER || (q->framerate == I_F_Q && !subframe_num))
136
        lspf2lpc(q, curr_lspf, lpc);
274
        qcelp_lspf2lpc(curr_lspf, lpc);
137 275
}
138 276

  
139 277
static int buf_size2framerate(const int buf_size) {

Also available in: Unified diff