• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2003 - 2016 Sony Corporation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include "ldac.h"
18 
19 /***************************************************************************************************
20     Subfunction: Process MDCT Core
21 ***************************************************************************************************/
proc_mdct_core_ldac(INT32 * p_x,INT32 * p_y,int nlnn)22 static void proc_mdct_core_ldac(
23 INT32 *p_x,
24 INT32 *p_y,
25 int nlnn)
26 {
27     INT32 i, j, k;
28     INT32 loop1, loop2;
29     INT32 coef, index0, index1, offset;
30     int nsmpl = npow2_ldac(nlnn);
31     int shift;
32     const int *p_p;
33     const INT32 *p_w, *p_c, *p_s;
34     INT32 a_work[LDAC_MAXLSU];
35     INT32 g0, g1, g2, g3;
36 
37     i = nlnn - LDAC_1FSLNN;
38     p_w = gaa_fwin_ldac[i];
39     p_c = gaa_wcos_ldac[i];
40     p_s = gaa_wsin_ldac[i];
41     p_p = gaa_perm_ldac[i];
42 
43     /* Block Floating */
44     shift = LDAC_C_BLKFLT - get_bit_length_ldac(get_absmax_ldac(p_x, nsmpl<<1)) - 1;
45     if (shift < 0) {
46         shift = 0;
47     }
48 
49     /* Windowing */
50     if (LDAC_Q_MDCT_WIN-shift > 0){
51         for (i = 0; i < nsmpl>>1; i++) {
52             g0 = mul_rsftrnd_ldac(-p_x[3*nsmpl/2-1-i], p_w[nsmpl/2+i], LDAC_Q_MDCT_WIN-shift);
53             g1 = mul_rsftrnd_ldac(-p_x[3*nsmpl/2+i], p_w[nsmpl/2-1-i], LDAC_Q_MDCT_WIN-shift);
54             a_work[p_p[i]] = g0 + g1;
55 
56             g0 = mul_rsftrnd_ldac(p_x[i], p_w[i], LDAC_Q_MDCT_WIN-shift);
57             g1 = mul_rsftrnd_ldac(-p_x[nsmpl-1-i], p_w[nsmpl-1-i], LDAC_Q_MDCT_WIN-shift);
58             a_work[p_p[nsmpl/2+i]] = g0 + g1;
59         }
60     }
61     else{
62         for (i = 0; i < nsmpl>>1; i++) {
63             g0 = mul_lsftrnd_ldac(-p_x[3*nsmpl/2-1-i], p_w[nsmpl/2+i], LDAC_Q_MDCT_WIN-shift);
64             g1 = mul_lsftrnd_ldac(-p_x[3*nsmpl/2+i], p_w[nsmpl/2-1-i], LDAC_Q_MDCT_WIN-shift);
65             a_work[p_p[i]] = g0 + g1;
66 
67             g0 = mul_lsftrnd_ldac(p_x[i], p_w[i], LDAC_Q_MDCT_WIN-shift);
68             g1 = mul_lsftrnd_ldac(-p_x[nsmpl-1-i], p_w[nsmpl-1-i], LDAC_Q_MDCT_WIN-shift);
69             a_work[p_p[nsmpl/2+i]] = g0 + g1;
70         }
71     }
72 
73     /* Butterfly */
74     coef = 0;
75     for (i = 0; i < nlnn-1; i++) {
76         loop1 = 1 << (nlnn-2-i);
77         loop2 = 1 << i;
78         index0 = 0;
79         index1 = 1 << (i+1);
80         offset = 1 << (i+1);
81 
82         for (j = 0; j < loop1; j++) {
83             for (k = 0; k < loop2; k++) {
84                 g0 = mul_rsftrnd_ldac(a_work[index1], p_c[coef], LDAC_Q_MDCT_COS+1);
85                 g1 = mul_rsftrnd_ldac(a_work[index1+1], p_s[coef], LDAC_Q_MDCT_SIN+1);
86                 g2 = g0 + g1;
87 
88                 g0 = mul_rsftrnd_ldac(a_work[index1], p_s[coef], LDAC_Q_MDCT_SIN+1);
89                 g1 = mul_rsftrnd_ldac(a_work[index1+1], p_c[coef], LDAC_Q_MDCT_COS+1);
90                 g3 = g0 - g1;
91 
92                 g0 = a_work[index0] >> 1;
93                 g1 = a_work[index0+1] >> 1;
94 
95                 a_work[index0] = g0 + g2;
96                 a_work[index0+1] = g1 + g3;
97                 a_work[index1] = g0 - g2;
98                 a_work[index1+1] = g1 - g3;
99 
100                 index0 += 2;
101                 index1 += 2;
102                 coef++;
103             }
104             index0 += offset;
105             index1 += offset;
106             coef -= loop2;
107         }
108         coef += loop2;
109     }
110 
111     for (i = 0; i < nsmpl>>1; i++) {
112         index0 = i << 1;
113 
114         g0 = mul_rsftrnd_ldac(a_work[index0], p_c[coef], LDAC_Q_MDCT_COS+shift);
115         g1 = mul_rsftrnd_ldac(a_work[index0+1], p_s[coef], LDAC_Q_MDCT_SIN+shift);
116         p_y[index0] = g0 + g1;
117 
118         g0 = mul_rsftrnd_ldac(a_work[index0], p_s[coef], LDAC_Q_MDCT_SIN+shift);
119         g1 = mul_rsftrnd_ldac(a_work[index0+1], p_c[coef], LDAC_Q_MDCT_COS+shift);
120         p_y[nsmpl-index0-1] = g0 - g1;
121 
122         coef++;
123     }
124 
125 
126     return;
127 }
128 
129 /***************************************************************************************************
130     Process MDCT
131 ***************************************************************************************************/
proc_mdct_ldac(SFINFO * p_sfinfo,int nlnn)132 DECLFUNC void proc_mdct_ldac(
133 SFINFO *p_sfinfo,
134 int nlnn)
135 {
136     AC *p_ac;
137     int ich;
138     int nchs = p_sfinfo->cfg.ch;
139 
140     for (ich = 0; ich < nchs; ich++) {
141         p_ac = p_sfinfo->ap_ac[ich];
142         proc_mdct_core_ldac(p_ac->p_acsub->a_time, p_ac->p_acsub->a_spec, nlnn);
143     }
144 
145     return;
146 }
147 
148