Line | Branch | Exec | Source |
---|---|---|---|
1 | /* | ||
2 | * AAC encoder intensity stereo | ||
3 | * Copyright (C) 2015 Rostislav Pehlivanov | ||
4 | * | ||
5 | * This file is part of FFmpeg. | ||
6 | * | ||
7 | * FFmpeg is free software; you can redistribute it and/or | ||
8 | * modify it under the terms of the GNU Lesser General Public | ||
9 | * License as published by the Free Software Foundation; either | ||
10 | * version 2.1 of the License, or (at your option) any later version. | ||
11 | * | ||
12 | * FFmpeg is distributed in the hope that it will be useful, | ||
13 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
14 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
15 | * Lesser General Public License for more details. | ||
16 | * | ||
17 | * You should have received a copy of the GNU Lesser General Public | ||
18 | * License along with FFmpeg; if not, write to the Free Software | ||
19 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
20 | */ | ||
21 | |||
22 | /** | ||
23 | * @file | ||
24 | * AAC encoder Intensity Stereo | ||
25 | * @author Rostislav Pehlivanov ( atomnuker gmail com ) | ||
26 | */ | ||
27 | |||
28 | #include "aacenc.h" | ||
29 | #include "aacenc_utils.h" | ||
30 | #include "aacenc_is.h" | ||
31 | #include "aacenc_quantization.h" | ||
32 | |||
33 | 21276 | struct AACISError ff_aac_is_encoding_err(AACEncContext *s, ChannelElement *cpe, | |
34 | int start, int w, int g, float ener0, | ||
35 | float ener1, float ener01, | ||
36 | int use_pcoeffs, int phase) | ||
37 | { | ||
38 | int i, w2; | ||
39 | 21276 | SingleChannelElement *sce0 = &cpe->ch[0]; | |
40 | 21276 | SingleChannelElement *sce1 = &cpe->ch[1]; | |
41 |
2/2✓ Branch 0 taken 3986 times.
✓ Branch 1 taken 17290 times.
|
21276 | float *L = use_pcoeffs ? sce0->pcoeffs : sce0->coeffs; |
42 |
2/2✓ Branch 0 taken 3986 times.
✓ Branch 1 taken 17290 times.
|
21276 | float *R = use_pcoeffs ? sce1->pcoeffs : sce1->coeffs; |
43 | 21276 | float *L34 = &s->scoefs[256*0], *R34 = &s->scoefs[256*1]; | |
44 | 21276 | float *IS = &s->scoefs[256*2], *I34 = &s->scoefs[256*3]; | |
45 | 21276 | float dist1 = 0.0f, dist2 = 0.0f; | |
46 | 21276 | struct AACISError is_error = {0}; | |
47 | |||
48 |
3/4✓ Branch 0 taken 20818 times.
✓ Branch 1 taken 458 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 20818 times.
|
21276 | if (ener01 <= 0 || ener0 <= 0) { |
49 | 458 | is_error.pass = 0; | |
50 | 458 | return is_error; | |
51 | } | ||
52 | |||
53 |
2/2✓ Branch 0 taken 21014 times.
✓ Branch 1 taken 20818 times.
|
41832 | for (w2 = 0; w2 < sce0->ics.group_len[w]; w2++) { |
54 | 21014 | FFPsyBand *band0 = &s->psy.ch[s->cur_channel+0].psy_bands[(w+w2)*16+g]; | |
55 | 21014 | FFPsyBand *band1 = &s->psy.ch[s->cur_channel+1].psy_bands[(w+w2)*16+g]; | |
56 | 21014 | int is_band_type, is_sf_idx = FFMAX(1, sce0->sf_idx[w*16+g]-4); | |
57 | 21014 | float e01_34 = phase*pos_pow34(ener1/ener0); | |
58 | 21014 | float maxval, dist_spec_err = 0.0f; | |
59 |
2/2✓ Branch 0 taken 10042 times.
✓ Branch 1 taken 10972 times.
|
21014 | float minthr = FFMIN(band0->threshold, band1->threshold); |
60 |
2/2✓ Branch 0 taken 666404 times.
✓ Branch 1 taken 21014 times.
|
687418 | for (i = 0; i < sce0->ics.swb_sizes[g]; i++) |
61 | 666404 | IS[i] = (L[start+(w+w2)*128+i] + phase*R[start+(w+w2)*128+i])*sqrt(ener0/ener01); | |
62 | 21014 | s->aacdsp.abs_pow34(L34, &L[start+(w+w2)*128], sce0->ics.swb_sizes[g]); | |
63 | 21014 | s->aacdsp.abs_pow34(R34, &R[start+(w+w2)*128], sce0->ics.swb_sizes[g]); | |
64 | 21014 | s->aacdsp.abs_pow34(I34, IS, sce0->ics.swb_sizes[g]); | |
65 | 21014 | maxval = find_max_val(1, sce0->ics.swb_sizes[g], I34); | |
66 | 21014 | is_band_type = find_min_book(maxval, is_sf_idx); | |
67 | 42028 | dist1 += quantize_band_cost(s, &L[start + (w+w2)*128], L34, | |
68 | 21014 | sce0->ics.swb_sizes[g], | |
69 | 21014 | sce0->sf_idx[w*16+g], | |
70 | 21014 | sce0->band_type[w*16+g], | |
71 | 21014 | s->lambda / band0->threshold, INFINITY, NULL, NULL); | |
72 | 42028 | dist1 += quantize_band_cost(s, &R[start + (w+w2)*128], R34, | |
73 | 21014 | sce1->ics.swb_sizes[g], | |
74 | 21014 | sce1->sf_idx[w*16+g], | |
75 | 21014 | sce1->band_type[w*16+g], | |
76 | 21014 | s->lambda / band1->threshold, INFINITY, NULL, NULL); | |
77 | 42028 | dist2 += quantize_band_cost(s, IS, I34, sce0->ics.swb_sizes[g], | |
78 | is_sf_idx, is_band_type, | ||
79 | 21014 | s->lambda / minthr, INFINITY, NULL, NULL); | |
80 |
2/2✓ Branch 0 taken 666404 times.
✓ Branch 1 taken 21014 times.
|
687418 | for (i = 0; i < sce0->ics.swb_sizes[g]; i++) { |
81 | 666404 | dist_spec_err += (L34[i] - I34[i])*(L34[i] - I34[i]); | |
82 | 666404 | dist_spec_err += (R34[i] - I34[i]*e01_34)*(R34[i] - I34[i]*e01_34); | |
83 | } | ||
84 | 21014 | dist_spec_err *= s->lambda / minthr; | |
85 | 21014 | dist2 += dist_spec_err; | |
86 | } | ||
87 | |||
88 | 20818 | is_error.pass = dist2 <= dist1; | |
89 | 20818 | is_error.phase = phase; | |
90 | 20818 | is_error.error = dist2 - dist1; | |
91 | 20818 | is_error.dist1 = dist1; | |
92 | 20818 | is_error.dist2 = dist2; | |
93 | 20818 | is_error.ener01 = ener01; | |
94 | |||
95 | 20818 | return is_error; | |
96 | } | ||
97 | |||
98 | 1334 | void ff_aac_search_for_is(AACEncContext *s, AVCodecContext *avctx, ChannelElement *cpe) | |
99 | { | ||
100 | 1334 | SingleChannelElement *sce0 = &cpe->ch[0]; | |
101 | 1334 | SingleChannelElement *sce1 = &cpe->ch[1]; | |
102 | 1334 | int start = 0, count = 0, w, w2, g, i, prev_sf1 = -1, prev_bt = -1, prev_is = 0; | |
103 | 1334 | const float freq_mult = avctx->sample_rate/(1024.0f/sce0->ics.num_windows)/2.0f; | |
104 | uint8_t nextband1[128]; | ||
105 | |||
106 |
2/2✓ Branch 0 taken 707 times.
✓ Branch 1 taken 627 times.
|
1334 | if (!cpe->common_window) |
107 | 707 | return; | |
108 | |||
109 | /** Scout out next nonzero bands */ | ||
110 | 627 | ff_init_nextband_map(sce1, nextband1); | |
111 | |||
112 |
2/2✓ Branch 0 taken 661 times.
✓ Branch 1 taken 627 times.
|
1288 | for (w = 0; w < sce0->ics.num_windows; w += sce0->ics.group_len[w]) { |
113 | 661 | start = 0; | |
114 |
2/2✓ Branch 0 taken 30709 times.
✓ Branch 1 taken 661 times.
|
31370 | for (g = 0; g < sce0->ics.num_swb; g++) { |
115 |
2/2✓ Branch 0 taken 9451 times.
✓ Branch 1 taken 21258 times.
|
30709 | if (start*freq_mult > INT_STEREO_LOW_LIMIT*(s->lambda/170.0f) && |
116 |
4/4✓ Branch 0 taken 9274 times.
✓ Branch 1 taken 177 times.
✓ Branch 2 taken 8665 times.
✓ Branch 3 taken 609 times.
|
9451 | cpe->ch[0].band_type[w*16+g] != NOISE_BT && !cpe->ch[0].zeroes[w*16+g] && |
117 |
4/6✓ Branch 0 taken 8645 times.
✓ Branch 1 taken 20 times.
✓ Branch 2 taken 8645 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 8645 times.
✗ Branch 5 not taken.
|
17310 | cpe->ch[1].band_type[w*16+g] != NOISE_BT && !cpe->ch[1].zeroes[w*16+g] && |
118 | 8645 | ff_sfdelta_can_remove_band(sce1, nextband1, prev_sf1, w*16+g)) { | |
119 | 8645 | float ener0 = 0.0f, ener1 = 0.0f, ener01 = 0.0f, ener01p = 0.0f; | |
120 | struct AACISError ph_err1, ph_err2, *best; | ||
121 |
2/2✓ Branch 0 taken 8757 times.
✓ Branch 1 taken 8645 times.
|
17402 | for (w2 = 0; w2 < sce0->ics.group_len[w]; w2++) { |
122 |
2/2✓ Branch 0 taken 298564 times.
✓ Branch 1 taken 8757 times.
|
307321 | for (i = 0; i < sce0->ics.swb_sizes[g]; i++) { |
123 | 298564 | float coef0 = sce0->coeffs[start+(w+w2)*128+i]; | |
124 | 298564 | float coef1 = sce1->coeffs[start+(w+w2)*128+i]; | |
125 | 298564 | ener0 += coef0*coef0; | |
126 | 298564 | ener1 += coef1*coef1; | |
127 | 298564 | ener01 += (coef0 + coef1)*(coef0 + coef1); | |
128 | 298564 | ener01p += (coef0 - coef1)*(coef0 - coef1); | |
129 | } | ||
130 | } | ||
131 | 8645 | ph_err1 = ff_aac_is_encoding_err(s, cpe, start, w, g, | |
132 | ener0, ener1, ener01p, 0, -1); | ||
133 | 8645 | ph_err2 = ff_aac_is_encoding_err(s, cpe, start, w, g, | |
134 | ener0, ener1, ener01, 0, +1); | ||
135 |
4/4✓ Branch 0 taken 7886 times.
✓ Branch 1 taken 759 times.
✓ Branch 2 taken 1019 times.
✓ Branch 3 taken 6867 times.
|
8645 | best = (ph_err1.pass && ph_err1.error < ph_err2.error) ? &ph_err1 : &ph_err2; |
136 |
2/2✓ Branch 0 taken 8564 times.
✓ Branch 1 taken 81 times.
|
8645 | if (best->pass) { |
137 | 8564 | cpe->is_mask[w*16+g] = 1; | |
138 | 8564 | cpe->ms_mask[w*16+g] = 0; | |
139 | 8564 | cpe->ch[0].is_ener[w*16+g] = sqrt(ener0 / best->ener01); | |
140 | 8564 | cpe->ch[1].is_ener[w*16+g] = ener0/ener1; | |
141 |
2/2✓ Branch 0 taken 7545 times.
✓ Branch 1 taken 1019 times.
|
8564 | cpe->ch[1].band_type[w*16+g] = (best->phase > 0) ? INTENSITY_BT : INTENSITY_BT2; |
142 |
4/4✓ Branch 0 taken 8055 times.
✓ Branch 1 taken 509 times.
✓ Branch 2 taken 2367 times.
✓ Branch 3 taken 5688 times.
|
8564 | if (prev_is && prev_bt != cpe->ch[1].band_type[w*16+g]) { |
143 | /** Flip M/S mask and pick the other CB, since it encodes more efficiently */ | ||
144 | 2367 | cpe->ms_mask[w*16+g] = 1; | |
145 |
2/2✓ Branch 0 taken 1793 times.
✓ Branch 1 taken 574 times.
|
2367 | cpe->ch[1].band_type[w*16+g] = (best->phase > 0) ? INTENSITY_BT2 : INTENSITY_BT; |
146 | } | ||
147 | 8564 | prev_bt = cpe->ch[1].band_type[w*16+g]; | |
148 | 8564 | count++; | |
149 | } | ||
150 | } | ||
151 |
4/4✓ Branch 0 taken 27510 times.
✓ Branch 1 taken 3199 times.
✓ Branch 2 taken 17848 times.
✓ Branch 3 taken 9662 times.
|
30709 | if (!sce1->zeroes[w*16+g] && sce1->band_type[w*16+g] < RESERVED_BT) |
152 | 17848 | prev_sf1 = sce1->sf_idx[w*16+g]; | |
153 | 30709 | prev_is = cpe->is_mask[w*16+g]; | |
154 | 30709 | start += sce0->ics.swb_sizes[g]; | |
155 | } | ||
156 | } | ||
157 | 627 | cpe->is_mode = !!count; | |
158 | } | ||
159 |