Mercurial > libavcodec.hg
annotate lpc.c @ 12483:0159a19bfff7 libavcodec
aacdec: Rework channel mapping compatibility hacks.
For a PCE based configuration map the channels solely based on tags.
For an indexed configuration map the channels solely based on position.
This works with all known exotic samples including al17, elem_id0, bad_concat,
and lfe_is_sce.
author | alexc |
---|---|
date | Fri, 10 Sep 2010 18:01:48 +0000 |
parents | e59926e2c50c |
children |
rev | line source |
---|---|
3353
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
1 /** |
7589
8b695a99e8df
flacenc, lpc: Move LPC code from flacenc.c to new lpc.[ch] files.
ramiro
parents:
7588
diff
changeset
|
2 * LPC utility code |
7594
cd6217c9ce92
update my email address to one which does not depend on my service provider
jbr
parents:
7593
diff
changeset
|
3 * Copyright (c) 2006 Justin Ruggles <justin.ruggles@gmail.com> |
3353
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
4 * |
3947
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3481
diff
changeset
|
5 * This file is part of FFmpeg. |
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3481
diff
changeset
|
6 * |
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3481
diff
changeset
|
7 * FFmpeg is free software; you can redistribute it and/or |
3353
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
8 * modify it under the terms of the GNU Lesser General Public |
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
9 * License as published by the Free Software Foundation; either |
3947
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3481
diff
changeset
|
10 * version 2.1 of the License, or (at your option) any later version. |
3353
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
11 * |
3947
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3481
diff
changeset
|
12 * FFmpeg is distributed in the hope that it will be useful, |
3353
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
15 * Lesser General Public License for more details. |
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
16 * |
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
17 * You should have received a copy of the GNU Lesser General Public |
3947
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3481
diff
changeset
|
18 * License along with FFmpeg; if not, write to the Free Software |
3353
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
20 */ |
5b901881d6ed
first rudimentary version of (Justin Ruggles jruggle earthlink net) flac encoder
michael
parents:
diff
changeset
|
21 |
6763 | 22 #include "libavutil/lls.h" |
5737 | 23 #include "dsputil.h" |
7788
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
24 |
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
25 #define LPC_USE_DOUBLE |
7589
8b695a99e8df
flacenc, lpc: Move LPC code from flacenc.c to new lpc.[ch] files.
ramiro
parents:
7588
diff
changeset
|
26 #include "lpc.h" |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
27 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
28 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
29 /** |
10424
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
30 * Apply Welch window function to audio block |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
31 */ |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
32 static void apply_welch_window(const int32_t *data, int len, double *w_data) |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
33 { |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
34 int i, n2; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
35 double w; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
36 double c; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
37 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
38 assert(!(len&1)); //the optimization in r11881 does not support odd len |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
39 //if someone wants odd len extend the change in r11881 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
40 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
41 n2 = (len >> 1); |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
42 c = 2.0 / (len - 1.0); |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
43 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
44 w_data+=n2; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
45 data+=n2; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
46 for(i=0; i<n2; i++) { |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
47 w = c - n2 + i; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
48 w = 1.0 - (w * w); |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
49 w_data[-i-1] = data[-i-1] * w; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
50 w_data[+i ] = data[+i ] * w; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
51 } |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
52 } |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
53 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
54 /** |
12024 | 55 * Calculate autocorrelation data from audio samples |
10424
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
56 * A Welch window function is applied before calculation. |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
57 */ |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
58 void ff_lpc_compute_autocorr(const int32_t *data, int len, int lag, |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
59 double *autoc) |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
60 { |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
61 int i, j; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
62 double tmp[len + lag + 1]; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
63 double *data1= tmp + lag; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
64 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
65 apply_welch_window(data, len, data1); |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
66 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
67 for(j=0; j<lag; j++) |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
68 data1[j-lag]= 0.0; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
69 data1[len] = 0.0; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
70 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
71 for(j=0; j<lag; j+=2){ |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
72 double sum0 = 1.0, sum1 = 1.0; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
73 for(i=j; i<len; i++){ |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
74 sum0 += data1[i] * data1[i-j]; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
75 sum1 += data1[i] * data1[i-j-1]; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
76 } |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
77 autoc[j ] = sum0; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
78 autoc[j+1] = sum1; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
79 } |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
80 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
81 if(j==lag){ |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
82 double sum = 1.0; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
83 for(i=j-1; i<len; i+=2){ |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
84 sum += data1[i ] * data1[i-j ] |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
85 + data1[i+1] * data1[i-j+1]; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
86 } |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
87 autoc[j] = sum; |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
88 } |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
89 } |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
90 |
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
91 /** |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
92 * Quantize LPC coefficients |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
93 */ |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
94 static void quantize_lpc_coefs(double *lpc_in, int order, int precision, |
7588
f6a1bff47a3b
flacenc: Allow more flexible shift calculation in LPC.
ramiro
parents:
7451
diff
changeset
|
95 int32_t *lpc_out, int *shift, int max_shift, int zero_shift) |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
96 { |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
97 int i; |
3464 | 98 double cmax, error; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
99 int32_t qmax; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
100 int sh; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
101 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
102 /* define maximum levels */ |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
103 qmax = (1 << (precision - 1)) - 1; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
104 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
105 /* find maximum coefficient value */ |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
106 cmax = 0.0; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
107 for(i=0; i<order; i++) { |
3389 | 108 cmax= FFMAX(cmax, fabs(lpc_in[i])); |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
109 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
110 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
111 /* if maximum value quantizes to zero, return all zeros */ |
7588
f6a1bff47a3b
flacenc: Allow more flexible shift calculation in LPC.
ramiro
parents:
7451
diff
changeset
|
112 if(cmax * (1 << max_shift) < 1.0) { |
f6a1bff47a3b
flacenc: Allow more flexible shift calculation in LPC.
ramiro
parents:
7451
diff
changeset
|
113 *shift = zero_shift; |
3389 | 114 memset(lpc_out, 0, sizeof(int32_t) * order); |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
115 return; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
116 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
117 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
118 /* calculate level shift which scales max coeff to available bits */ |
7588
f6a1bff47a3b
flacenc: Allow more flexible shift calculation in LPC.
ramiro
parents:
7451
diff
changeset
|
119 sh = max_shift; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
120 while((cmax * (1 << sh) > qmax) && (sh > 0)) { |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
121 sh--; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
122 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
123 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
124 /* since negative shift values are unsupported in decoder, scale down |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
125 coefficients instead */ |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
126 if(sh == 0 && cmax > qmax) { |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
127 double scale = ((double)qmax) / cmax; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
128 for(i=0; i<order; i++) { |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
129 lpc_in[i] *= scale; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
130 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
131 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
132 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
133 /* output quantized coefficients and level shift */ |
3464 | 134 error=0; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
135 for(i=0; i<order; i++) { |
7788
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
136 error -= lpc_in[i] * (1 << sh); |
4594 | 137 lpc_out[i] = av_clip(lrintf(error), -qmax, qmax); |
3464 | 138 error -= lpc_out[i]; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
139 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
140 *shift = sh; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
141 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
142 |
7593 | 143 static int estimate_best_order(double *ref, int min_order, int max_order) |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
144 { |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
145 int i, est; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
146 |
7593 | 147 est = min_order; |
148 for(i=max_order-1; i>=min_order-1; i--) { | |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
149 if(ref[i] > 0.10) { |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
150 est = i+1; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
151 break; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
152 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
153 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
154 return est; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
155 } |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
156 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
157 /** |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
158 * Calculate LPC coefficients for multiple orders |
8824
9f929379bbca
lpc: Document the use_lpc parameter to ff_lpc_calc_coefs().
jbr
parents:
7788
diff
changeset
|
159 * |
9f929379bbca
lpc: Document the use_lpc parameter to ff_lpc_calc_coefs().
jbr
parents:
7788
diff
changeset
|
160 * @param use_lpc LPC method for determining coefficients |
9f929379bbca
lpc: Document the use_lpc parameter to ff_lpc_calc_coefs().
jbr
parents:
7788
diff
changeset
|
161 * 0 = LPC with fixed pre-defined coeffs |
9f929379bbca
lpc: Document the use_lpc parameter to ff_lpc_calc_coefs().
jbr
parents:
7788
diff
changeset
|
162 * 1 = LPC with coeffs determined by Levinson-Durbin recursion |
9f929379bbca
lpc: Document the use_lpc parameter to ff_lpc_calc_coefs().
jbr
parents:
7788
diff
changeset
|
163 * 2+ = LPC with coeffs determined by Cholesky factorization using (use_lpc-1) passes. |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
164 */ |
7589
8b695a99e8df
flacenc, lpc: Move LPC code from flacenc.c to new lpc.[ch] files.
ramiro
parents:
7588
diff
changeset
|
165 int ff_lpc_calc_coefs(DSPContext *s, |
7592 | 166 const int32_t *samples, int blocksize, int min_order, |
167 int max_order, int precision, | |
12139
e59926e2c50c
Add AVCodecContext.lpc_type and Add AVCodecContext.lpc_passes fields.
jbr
parents:
12024
diff
changeset
|
168 int32_t coefs[][MAX_LPC_ORDER], int *shift, |
e59926e2c50c
Add AVCodecContext.lpc_type and Add AVCodecContext.lpc_passes fields.
jbr
parents:
12024
diff
changeset
|
169 enum AVLPCType lpc_type, int lpc_passes, |
7592 | 170 int omethod, int max_shift, int zero_shift) |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
171 { |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
172 double autoc[MAX_LPC_ORDER+1]; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
173 double ref[MAX_LPC_ORDER]; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
174 double lpc[MAX_LPC_ORDER][MAX_LPC_ORDER]; |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
175 int i, j, pass; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
176 int opt_order; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
177 |
12139
e59926e2c50c
Add AVCodecContext.lpc_type and Add AVCodecContext.lpc_passes fields.
jbr
parents:
12024
diff
changeset
|
178 assert(max_order >= MIN_LPC_ORDER && max_order <= MAX_LPC_ORDER && |
e59926e2c50c
Add AVCodecContext.lpc_type and Add AVCodecContext.lpc_passes fields.
jbr
parents:
12024
diff
changeset
|
179 lpc_type > AV_LPC_TYPE_FIXED); |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
180 |
12139
e59926e2c50c
Add AVCodecContext.lpc_type and Add AVCodecContext.lpc_passes fields.
jbr
parents:
12024
diff
changeset
|
181 if (lpc_type == AV_LPC_TYPE_LEVINSON) { |
10424
94595d0e617c
Move autocorrelation function from flacenc.c to lpc.c. Also rename the
jbr
parents:
8826
diff
changeset
|
182 s->lpc_compute_autocorr(samples, blocksize, max_order, autoc); |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
183 |
7788
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
184 compute_lpc_coefs(autoc, max_order, &lpc[0][0], MAX_LPC_ORDER, 0, 1); |
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
185 |
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
186 for(i=0; i<max_order; i++) |
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
187 ref[i] = fabs(lpc[i][i]); |
12139
e59926e2c50c
Add AVCodecContext.lpc_type and Add AVCodecContext.lpc_passes fields.
jbr
parents:
12024
diff
changeset
|
188 } else if (lpc_type == AV_LPC_TYPE_CHOLESKY) { |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
189 LLSModel m[2]; |
8826
bffe8e6cb10e
lpc: Remove false positive compilation warning about weight being
jbr
parents:
8825
diff
changeset
|
190 double var[MAX_LPC_ORDER+1], av_uninit(weight); |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
191 |
12139
e59926e2c50c
Add AVCodecContext.lpc_type and Add AVCodecContext.lpc_passes fields.
jbr
parents:
12024
diff
changeset
|
192 for(pass=0; pass<lpc_passes; pass++){ |
3470 | 193 av_init_lls(&m[pass&1], max_order); |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
194 |
3473
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
195 weight=0; |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
196 for(i=max_order; i<blocksize; i++){ |
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
197 for(j=0; j<=max_order; j++) |
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
198 var[j]= samples[i-j]; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
199 |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
200 if(pass){ |
5743 | 201 double eval, inv, rinv; |
3473
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
202 eval= av_evaluate_lls(&m[(pass-1)&1], var+1, max_order-1); |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
203 eval= (512>>pass) + fabs(eval - var[0]); |
5743 | 204 inv = 1/eval; |
205 rinv = sqrt(inv); | |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
206 for(j=0; j<=max_order; j++) |
5743 | 207 var[j] *= rinv; |
208 weight += inv; | |
3473
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
209 }else |
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
210 weight++; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
211 |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
212 av_update_lls(&m[pass&1], var, 1.0); |
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
213 } |
3473
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
214 av_solve_lls(&m[pass&1], 0.001, 0); |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
215 } |
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
216 |
3473
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
217 for(i=0; i<max_order; i++){ |
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
218 for(j=0; j<max_order; j++) |
7788
ffd4b1364b62
Avoid duplicating compute_lpc_coefs() function in both the RA288 and AAC decoders.
vitor
parents:
7753
diff
changeset
|
219 lpc[i][j]=-m[(pass-1)&1].coeff[i][j]; |
3473
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
220 ref[i]= sqrt(m[(pass-1)&1].variance[i] / weight) * (blocksize - max_order) / 4000; |
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
221 } |
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
222 for(i=max_order-1; i>0; i--) |
fa545ed305c9
calculate all coefficients for several orders during cholesky factorization, the resulting coefficients are not strictly optimal though as there is a small difference in the autocorrelation matrixes which is ignored for the smaller orders
michael
parents:
3470
diff
changeset
|
223 ref[i] = ref[i-1] - ref[i]; |
3467
33af013504d5
optionally (use_lpc=2) support Cholesky factorization for finding the lpc coeficients
michael
parents:
3464
diff
changeset
|
224 } |
3477
30ac8a424448
Add lpc order search. This creates new compression levels 6 to 12.
jbr
parents:
3473
diff
changeset
|
225 opt_order = max_order; |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
226 |
3477
30ac8a424448
Add lpc order search. This creates new compression levels 6 to 12.
jbr
parents:
3473
diff
changeset
|
227 if(omethod == ORDER_METHOD_EST) { |
7593 | 228 opt_order = estimate_best_order(ref, min_order, max_order); |
3477
30ac8a424448
Add lpc order search. This creates new compression levels 6 to 12.
jbr
parents:
3473
diff
changeset
|
229 i = opt_order-1; |
7588
f6a1bff47a3b
flacenc: Allow more flexible shift calculation in LPC.
ramiro
parents:
7451
diff
changeset
|
230 quantize_lpc_coefs(lpc[i], i+1, precision, coefs[i], &shift[i], max_shift, zero_shift); |
3477
30ac8a424448
Add lpc order search. This creates new compression levels 6 to 12.
jbr
parents:
3473
diff
changeset
|
231 } else { |
7591
7dfb28d3ccd1
use limited range of lpc orders when quantizing coefficients
jbr
parents:
7590
diff
changeset
|
232 for(i=min_order-1; i<max_order; i++) { |
7588
f6a1bff47a3b
flacenc: Allow more flexible shift calculation in LPC.
ramiro
parents:
7451
diff
changeset
|
233 quantize_lpc_coefs(lpc[i], i+1, precision, coefs[i], &shift[i], max_shift, zero_shift); |
3477
30ac8a424448
Add lpc order search. This creates new compression levels 6 to 12.
jbr
parents:
3473
diff
changeset
|
234 } |
30ac8a424448
Add lpc order search. This creates new compression levels 6 to 12.
jbr
parents:
3473
diff
changeset
|
235 } |
3385
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
236 |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
237 return opt_order; |
340e5d35b326
flac-lpc patch by (Justin Ruggles jruggle earthlink net)
michael
parents:
3384
diff
changeset
|
238 } |