Git init
[external/opencore-amr.git] / opencore / codecs_v2 / audio / gsm_amr / amr_nb / common / src / lsp_lsf.cpp
1 /* ------------------------------------------------------------------
2  * Copyright (C) 1998-2009 PacketVideo
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
13  * express or implied.
14  * See the License for the specific language governing permissions
15  * and limitations under the License.
16  * -------------------------------------------------------------------
17  */
18 /****************************************************************************************
19 Portions of this file are derived from the following 3GPP standard:
20
21     3GPP TS 26.073
22     ANSI-C code for the Adaptive Multi-Rate (AMR) speech codec
23     Available from http://www.3gpp.org
24
25 (C) 2004, 3GPP Organizational Partners (ARIB, ATIS, CCSA, ETSI, TTA, TTC)
26 Permission to distribute, modify and use this file under the standard license
27 terms listed above has been obtained from the copyright holder.
28 ****************************************************************************************/
29 /*
30  Filename: lsp_lsf.cpp
31  Functions: Lsp_lsf
32             Lsf_lsp
33
34 ------------------------------------------------------------------------------
35  MODULE DESCRIPTION
36
37  This file contains the functions that convert line spectral pairs (LSP) to
38  line spectral frequencies (LSF) and vice-versa.
39
40 ------------------------------------------------------------------------------
41 */
42
43 /*----------------------------------------------------------------------------
44 ; INCLUDES
45 ----------------------------------------------------------------------------*/
46 #include "lsp_lsf.h"
47 #include "basicop_malloc.h"
48 #include "basic_op.h"
49
50 /*--------------------------------------------------------------------------*/
51 #ifdef __cplusplus
52 extern "C"
53 {
54 #endif
55
56     /*----------------------------------------------------------------------------
57     ; MACROS
58     ; Define module specific macros here
59     ----------------------------------------------------------------------------*/
60
61     /*----------------------------------------------------------------------------
62     ; DEFINES
63     ; Include all pre-processor statements here. Include conditional
64     ; compile variables also.
65     ----------------------------------------------------------------------------*/
66
67     /*----------------------------------------------------------------------------
68     ; LOCAL FUNCTION DEFINITIONS
69     ; Function Prototype declaration
70     ----------------------------------------------------------------------------*/
71
72     /*----------------------------------------------------------------------------
73     ; LOCAL VARIABLE DEFINITIONS
74     ; Variable declaration - defined here and used outside this module
75     ----------------------------------------------------------------------------*/
76
77     extern const Word16 table[];
78     extern const Word16 slope[];
79
80
81     /*--------------------------------------------------------------------------*/
82 #ifdef __cplusplus
83 }
84 #endif
85
86 /*
87 ------------------------------------------------------------------------------
88  FUNCTION NAME: Lsf_lsp
89 ------------------------------------------------------------------------------
90  INPUT AND OUTPUT DEFINITIONS
91
92  Inputs:
93     lsf = buffer containing normalized line spectral frequencies; valid
94           range is between 0 and 0.5 (Word16)
95     lsp = buffer containing line spectral pairs; valid range is between
96           -1 and 1 (Word16)
97     m = LPC order (Word16)
98
99  Outputs:
100     lsp contains the newly calculated line spectral pairs
101
102  Returns:
103     None
104
105  Global Variables Used:
106     table = cosine table
107
108  Local Variables Needed:
109     None
110
111 ------------------------------------------------------------------------------
112  FUNCTION DESCRIPTION
113
114  This function performs the LSF to LSP transformation using the equation:
115
116     lsf[i] = arccos(lsp[i])/(2*pi)
117
118  The transformation from lsp[i] to lsf[i] is approximated by a look-up table
119  and interpolation.
120
121 ------------------------------------------------------------------------------
122  REQUIREMENTS
123
124  None
125
126 ------------------------------------------------------------------------------
127  REFERENCES
128
129  lsp_lsf.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
130
131 ------------------------------------------------------------------------------
132  PSEUDO-CODE
133
134 void Lsf_lsp (
135     Word16 lsf[],       // (i) : lsf[m] normalized (range: 0.0<=val<=0.5)
136     Word16 lsp[],       // (o) : lsp[m] (range: -1<=val<1)
137     Word16 m            // (i) : LPC order
138 )
139 {
140     Word16 i, ind, offset;
141     Word32 L_tmp;
142
143     for (i = 0; i < m; i++)
144     {
145         ind = shr (lsf[i], 8);      // ind    = b8-b15 of lsf[i]
146         offset = lsf[i] & 0x00ff;    // offset = b0-b7  of lsf[i]
147
148         // lsp[i] = table[ind]+ ((table[ind+1]-table[ind])*offset) / 256
149
150         L_tmp = L_mult (sub (table[ind + 1], table[ind]), offset);
151         lsp[i] = add (table[ind], extract_l (L_shr (L_tmp, 9)));
152
153     }
154     return;
155 }
156
157 ------------------------------------------------------------------------------
158  CAUTION [optional]
159  [State any special notes, constraints or cautions for users of this function]
160
161 ------------------------------------------------------------------------------
162 */
163
164 OSCL_EXPORT_REF void Lsf_lsp(
165     Word16 lsf[],       /* (i) : lsf[m] normalized (range: 0.0<=val<=0.5) */
166     Word16 lsp[],       /* (o) : lsp[m] (range: -1<=val<1)                */
167     Word16 m,           /* (i) : LPC order                                */
168     Flag   *pOverflow   /* (o) : Flag set when overflow occurs            */
169 )
170 {
171     Word16 i, ind, offset;
172     Word32 L_tmp;
173
174     for (i = 0; i < m; i++)
175     {
176         ind = lsf[i] >> 8;           /* ind    = b8-b15 of lsf[i] */
177         offset = lsf[i] & 0x00ff;    /* offset = b0-b7  of lsf[i] */
178
179         /* lsp[i] = table[ind]+ ((table[ind+1]-table[ind])*offset) / 256 */
180
181         L_tmp = ((Word32)(table[ind + 1] - table[ind]) * offset) >> 8;
182         lsp[i] = table[ind] + (Word16) L_tmp;
183
184     }
185
186     return;
187 }
188
189 /****************************************************************************/
190
191
192 /*
193 ------------------------------------------------------------------------------
194  FUNCTION NAME: Lsp_lsf
195 ------------------------------------------------------------------------------
196  INPUT AND OUTPUT DEFINITIONS
197
198  Inputs:
199     lsp = buffer containing line spectral pairs; valid range is between
200           -1 and 1 (Word16)
201     lsf = buffer containing normalized line spectral frequencies; valid
202           range is between 0 and 0.5 (Word16)
203     m = LPC order (Word16)
204
205  Outputs:
206     lsf contains the newly calculated normalized line spectral frequencies
207
208  Returns:
209     None
210
211  Global Variables Used:
212     table = cosine table
213     slope = table to used to calculate inverse cosine
214
215  Local Variables Needed:
216     None
217
218 ------------------------------------------------------------------------------
219  FUNCTION DESCRIPTION
220
221  This function performs the LSP to LSF transformation using the equation:
222
223     lsp[i] = cos(2*pi*lsf[i])
224
225  The transformation from lsf[i] to lsp[i] is approximated by a look-up table
226  and interpolation.
227
228 ------------------------------------------------------------------------------
229  REQUIREMENTS
230
231  None
232
233 ------------------------------------------------------------------------------
234  REFERENCES
235
236  lsp_lsf.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
237
238 ------------------------------------------------------------------------------
239  PSEUDO-CODE
240
241 void Lsp_lsf (
242     Word16 lsp[],       // (i)  : lsp[m] (range: -1<=val<1)
243     Word16 lsf[],       // (o)  : lsf[m] normalized (range: 0.0<=val<=0.5)
244     Word16 m            // (i)  : LPC order
245 )
246 {
247     Word16 i, ind;
248     Word32 L_tmp;
249
250     ind = 63;                        // begin at end of table -1
251
252     for (i = m - 1; i >= 0; i--)
253     {
254         // find value in table that is just greater than lsp[i]
255
256         while (sub (table[ind], lsp[i]) < 0)
257         {
258             ind--;
259
260         }
261
262         // acos(lsp[i])= ind*256 + ( ( lsp[i]-table[ind] ) *
263            slope[ind] )/4096
264
265         L_tmp = L_mult (sub (lsp[i], table[ind]), slope[ind]);
266         //(lsp[i]-table[ind])*slope[ind])>>12
267         lsf[i] = pv_round (L_shl (L_tmp, 3));
268         lsf[i] = add (lsf[i], shl (ind, 8));
269     }
270     return;
271 }
272
273 ------------------------------------------------------------------------------
274  CAUTION [optional]
275  [State any special notes, constraints or cautions for users of this function]
276
277 ------------------------------------------------------------------------------
278 */
279
280 OSCL_EXPORT_REF void Lsp_lsf(
281     Word16 lsp[],       /* (i)  : lsp[m] (range: -1<=val<1)                */
282     Word16 lsf[],       /* (o)  : lsf[m] normalized (range: 0.0<=val<=0.5) */
283     Word16 m,           /* (i)  : LPC order                                */
284     Flag  *pOverflow    /* (o)  : Flag set when overflow occurs            */
285 )
286 {
287     Word16 i;
288     Word16 ind;
289     Word16 temp;
290     Word32 L_tmp;
291     Word16 *p_lsp = &lsp[m-1];
292     Word16 *p_lsf = &lsf[m-1];
293     OSCL_UNUSED_ARG(pOverflow);
294
295     ind = 63;                        /* begin at end of table -1 */
296
297     for (i = m - 1; i >= 0; i--)
298     {
299         /* find value in table that is just greater than lsp[i] */
300         temp = *(p_lsp--);
301         while (table[ind] < temp)
302         {
303             ind--;
304         }
305
306         /* acos(lsp[i])= ind*256 + ( ( lsp[i]-table[ind] ) *
307            slope[ind] )/4096 */
308
309         L_tmp = (Word32)(temp - table[ind]) * slope[ind];
310
311         /*(lsp[i]-table[ind])*slope[ind])>>12*/
312         L_tmp  = (L_tmp + 0x00000800) >> 12;
313
314         *(p_lsf--) = (Word16)(L_tmp) + (ind << 8);
315     }
316
317     return;
318 }