Line data Source code
1 : /*====================================================================================
2 : EVS Codec 3GPP TS26.452 Aug 12, 2021. Version 16.3.0
3 : ====================================================================================*/
4 : #include <stdint.h>
5 : #include "options.h"
6 : #include "cnst.h"
7 : //#include "prot_fx.h"
8 : #include "prot_fx.h" /* Function prototypes */
9 : #include "prot_fx_enc.h" /* Function prototypes */
10 :
11 : /*-------------------------------------------------------------------*
12 : * local constants
13 : * -----------------------------------------------------------------*/
14 :
15 : #define NB_TRACK 4
16 : #define STEP NB_TRACK
17 :
18 : /*-------------------------------------------------------------------*
19 : * corr_xh_fx:
20 : *
21 : * Compute the correlation between the target signal and the impulse
22 : * response of the weighted synthesis filter.
23 : *
24 : * y[i]=sum(j=i,l-1) x[j]*h[j-i], i=0,l-1
25 : *-------------------------------------------------------------------*/
26 2968 : void corr_xh_fx(
27 : const Word16 x[], /* i : target signal Qx*/
28 : Word16 dn[], /* o : correlation between x[] and h[] Qdn = Qx+j-1*/
29 : const Word16 h[] /* i : impulse response (of weighted synthesis filter) Q14*/
30 : )
31 : {
32 : Word16 i, j, k;
33 : Word32 L_tmp, y32[L_SUBFR], L_maxloc, L_tot;
34 :
35 : /* first keep the result on 32 bits and find absolute maximum */
36 2968 : L_tot = L_deposit_l( 1 );
37 :
38 14840 : FOR( k = 0; k < NB_TRACK; k++ )
39 : {
40 11872 : L_maxloc = L_deposit_l( 0 );
41 201824 : FOR( i = k; i < L_SUBFR; i += STEP )
42 : {
43 189952 : L_tmp = L_mac( 1L, x[i], h[0] ); /* 1 -> to avoid null dn[] Qx+15*/
44 6173440 : FOR( j = i; j < L_SUBFR - 1; j++ )
45 : {
46 5983488 : L_tmp = L_mac_sat( L_tmp, x[j + 1], h[j + 1 - i] ); /*Qx+15*/
47 : }
48 :
49 189952 : y32[i] = L_tmp; /*Qx+15*/
50 189952 : move32();
51 189952 : L_tmp = L_abs( L_tmp );
52 189952 : L_maxloc = L_max( L_tmp, L_maxloc ); /*Qx+15*/
53 : }
54 : /* tot += 3*max / 8 */
55 11872 : L_maxloc = L_shr( L_maxloc, 2 );
56 11872 : L_tot = L_add_sat( L_tot, L_maxloc ); /* +max/4 */
57 11872 : L_tot = L_add_sat( L_tot, L_shr( L_maxloc, 1 ) ); /* +max/8 */
58 : }
59 :
60 : /* Find the number of right shifts to do on y32[] so that */
61 : /* 6.0 x sumation of max of dn[] in each track not saturate. */
62 :
63 2968 : j = sub( norm_l( L_tot ), 4 ); /* 4 -> 16 x tot */
64 :
65 192920 : FOR( i = 0; i < L_SUBFR; i++ )
66 : {
67 189952 : dn[i] = round_fx( L_shl( y32[i], j ) ); /*Qx+15+j-16*/
68 : }
69 2968 : return;
70 : }
71 :
72 0 : void corr_hh_ivas_fx(
73 : const Word16 *h, /* i : target signal e(norm_s(h1[0])+1) */
74 : Word16 *y, /* o : correlation between x[] and h[] Q_new + 1 */
75 : Word16 *Qy,
76 : const Word16 L_subfr /* i : length of the subframe Q0*/
77 : )
78 : {
79 : Word16 i, j, k;
80 : Word32 L_tmp, y32[L_SUBFR * 2], L_maxloc, L_tot;
81 :
82 : /* first keep the result on 32 bits and find absolute maximum */
83 0 : L_tot = L_deposit_l( 1 );
84 :
85 0 : FOR( k = 0; k < NB_TRACK; k++ )
86 : {
87 0 : L_maxloc = L_deposit_l( 0 );
88 0 : FOR( i = k; i < L_subfr; i += STEP )
89 : {
90 0 : L_tmp = L_mac( 1L, shr( h[i], 3 ), shr( h[0], 3 ) ); /* 1 -> to avoid null dn[] */ // 2*(15 - norm_s(h[0]) -3) - 1
91 0 : FOR( j = i; j < L_subfr - 1; j++ )
92 : {
93 0 : L_tmp = L_mac_sat( L_tmp, shr( h[j + 1], 3 ), shr( h[j + 1 - i], 3 ) ); // 2*(15 - norm_s(h[0]) -3) - 1 //?sat
94 : }
95 :
96 0 : y32[i] = L_tmp; // 2*(15 - norm_s(h[0]) -3) - 1
97 0 : move32();
98 0 : L_tmp = L_abs( L_tmp );
99 0 : L_maxloc = L_max( L_tmp, L_maxloc ); // 2*(15 - norm_s(h[0]) -3) - 1
100 : }
101 : /* tot += 3*max / 8 */
102 0 : L_maxloc = L_shr( L_maxloc, 2 );
103 0 : L_tot = L_add_sat( L_tot, L_maxloc ); /* +max/4 */
104 0 : L_tot = L_add_sat( L_tot, L_shr( L_maxloc, 1 ) ); /* +max/8 */
105 : }
106 :
107 : /* Find the number of right shifts to do on y32[] so that */
108 : /* 6.0 x sumation of max of dn[] in each track not saturate. */
109 :
110 0 : j = sub( norm_l( L_tot ), 4 ); /* 4 -> 16 x tot */
111 :
112 0 : FOR( i = 0; i < L_subfr; i++ )
113 : {
114 0 : y[i] = round_fx( L_shl( y32[i], j ) ); // 2*(15 - norm_s(h[0])) - 1 +j - 16
115 0 : move16();
116 : }
117 :
118 0 : *Qy = sub( add( shl( sub( 15 - 3, norm_s( h[0] ) ), 1 ), j ), 17 ); // h scaled down by 3 to avoid saturation while accumulating Ltmp
119 0 : move16();
120 0 : return;
121 : }
122 :
123 229292 : void corr_xh_ivas_fx(
124 : const Word16 x[], /* i : target signal Qx*/
125 : const Word16 Qx,
126 : Word16 dn[], /* o : correlation between x[] and h[] Qdn*/
127 : Word16 *Qdn,
128 : const Word16 h[], /* i : impulse response (of weighted synthesis filter) (Q14 - norm_s(h[0]))*/
129 : const Word16 L_subfr /* i : length of the subframe Q0*/
130 : )
131 : {
132 : Word16 i, j, k;
133 : Word32 L_tmp, y32[L_SUBFR * 2], L_maxloc, L_tot;
134 :
135 : /* first keep the result on 32 bits and find absolute maximum */
136 229292 : L_tot = L_deposit_l( 0 );
137 :
138 1146460 : FOR( k = 0; k < NB_TRACK; k++ )
139 : {
140 917168 : L_maxloc = L_deposit_l( 0 );
141 15905456 : FOR( i = k; i < L_subfr; i += STEP )
142 : {
143 14988288 : L_tmp = L_mac( 0, x[i], h[0] ); // Qx+(14 - norm_s(h[0])) + 1
144 507189760 : FOR( j = i; j < L_subfr - 1; j++ )
145 : {
146 492201472 : L_tmp = L_mac_sat( L_tmp, x[j + 1], h[j + 1 - i] ); // Qx+(14 - norm_s(h[0])) + 1
147 : }
148 :
149 14988288 : y32[i] = L_tmp; // Qx+(14 - norm_s(h[0])) + 1
150 14988288 : move32();
151 14988288 : L_tmp = L_abs( L_tmp );
152 14988288 : L_maxloc = L_max( L_tmp, L_maxloc ); // Qx+(14 - norm_s(h[0])) +1
153 : }
154 : /* tot += 3*max / 8 */
155 917168 : L_maxloc = L_shr( L_maxloc, 2 );
156 917168 : L_tot = L_add_sat( L_tot, L_maxloc ); /* +max/4 */
157 917168 : L_tot = L_add_sat( L_tot, L_shr( L_maxloc, 1 ) ); /* +max/8 */
158 : }
159 :
160 : /* Find the number of right shifts to do on y32[] so that */
161 : /* 6.0 x sumation of max of dn[] in each track not saturate. */
162 :
163 229292 : j = sub( norm_l( L_tot ), 4 ); /* 4 -> 16 x tot */
164 :
165 15217580 : FOR( i = 0; i < L_subfr; i++ )
166 : {
167 14988288 : dn[i] = round_fx( L_shl( y32[i], j ) ); // Qx+(14 - norm_s(h[0])) + 1 +j - 16
168 14988288 : move16();
169 : }
170 :
171 229292 : *Qdn = sub( add( add( Qx, add( sub( 14, norm_s( h[0] ) ), 1 ) ), j ), 16 );
172 229292 : move16();
173 229292 : return;
174 : }
|