Home | History | Annotate | Download | only in src
      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 ------------------------------------------------------------------------------
     31 
     32 
     33 
     34  Pathname: ./audio/gsm-amr/c/src/q_gain_c.c
     35  Functions: q_gain_code
     36 
     37      Date: 02/05/2002
     38 
     39 ------------------------------------------------------------------------------
     40  REVISION HISTORY
     41 
     42  Description: Updated template used to PV coding template.
     43  Changed to accept the pOverflow flag for EPOC compatibility.
     44 
     45  Description:
     46  (1) Removed optimization -- mult(i, 3, pOverflow) is NOT the same as adding
     47      i to itself 3 times.  The reason is because the mult function does a
     48      right shift by 15, which will obliterate smaller numbers.
     49 
     50  Description:
     51               1. Eliminated unused include files.
     52               2. Eliminated math operations that unnecessary checked for
     53                  saturation by evaluating the operands
     54 
     55  Description:  Replaced "int" and/or "char" with OSCL defined types.
     56 
     57  Description: Added #ifdef __cplusplus around extern'ed table.
     58 
     59  Description:
     60 
     61 ------------------------------------------------------------------------------
     62  MODULE DESCRIPTION
     63 
     64     Scalar quantization of the innovative codebook gain.
     65 
     66 ------------------------------------------------------------------------------
     67 */
     68 
     69 /*----------------------------------------------------------------------------
     70 ; INCLUDES
     71 ----------------------------------------------------------------------------*/
     72 #include "q_gain_c.h"
     73 #include "mode.h"
     74 #include "oper_32b.h"
     75 #include "basic_op.h"
     76 #include "log2.h"
     77 #include "pow2.h"
     78 
     79 /*--------------------------------------------------------------------------*/
     80 #ifdef __cplusplus
     81 extern "C"
     82 {
     83 #endif
     84 
     85     /*----------------------------------------------------------------------------
     86     ; MACROS
     87     ; Define module specific macros here
     88     ----------------------------------------------------------------------------*/
     89 
     90     /*----------------------------------------------------------------------------
     91     ; DEFINES
     92     ; Include all pre-processor statements here. Include conditional
     93     ; compile variables also.
     94     ----------------------------------------------------------------------------*/
     95 #define NB_QUA_CODE 32
     96 
     97     /*----------------------------------------------------------------------------
     98     ; LOCAL FUNCTION DEFINITIONS
     99     ; Function Prototype declaration
    100     ----------------------------------------------------------------------------*/
    101 
    102     /*----------------------------------------------------------------------------
    103     ; LOCAL VARIABLE DEFINITIONS
    104     ; Variable declaration - defined here and used outside this module
    105     ----------------------------------------------------------------------------*/
    106 
    107     /*----------------------------------------------------------------------------
    108     ; EXTERNAL GLOBAL STORE/BUFFER/POINTER REFERENCES
    109     ; Declare variables used in this module but defined elsewhere
    110     ----------------------------------------------------------------------------*/
    111     extern const Word16 qua_gain_code[NB_QUA_CODE*3];
    112 
    113     /*--------------------------------------------------------------------------*/
    114 #ifdef __cplusplus
    115 }
    116 #endif
    117 
    118 /*
    119 ------------------------------------------------------------------------------
    120  FUNCTION NAME: q_gain_code
    121 ------------------------------------------------------------------------------
    122  INPUT AND OUTPUT DEFINITIONS
    123 
    124  Inputs:
    125     mode -- enum Mode -- AMR mode
    126     exp_gcode0 -- Word16 -- predicted CB gain (exponent),  Q0
    127     frac_gcode0 -- Word16 -- predicted CB gain (fraction),  Q15
    128     gain -- Pointer to Word16 -- quantized fixed codebook gain, Q1
    129 
    130  Outputs:
    131     gain -- Pointer to Word16 -- quantized fixed codebook gain, Q1
    132 
    133     qua_ener_MR122 -- Pointer to Word16 -- quantized energy error, Q10
    134                                            (for MR122 MA predictor update)
    135 
    136     qua_ener -- Pointer to Word16 -- quantized energy error,        Q10
    137                                      (for other MA predictor update)
    138 
    139     pOverflow -- Pointer to Flag -- overflow indicator
    140  Returns:
    141     quantization index -- Word16 -- Q0
    142 
    143  Global Variables Used:
    144     qua_gain_code[]
    145 
    146  Local Variables Needed:
    147     None
    148 
    149 ------------------------------------------------------------------------------
    150  FUNCTION DESCRIPTION
    151 
    152     Scalar quantization of the innovative codebook gain.
    153 
    154 ------------------------------------------------------------------------------
    155  REQUIREMENTS
    156 
    157  None
    158 
    159 ------------------------------------------------------------------------------
    160  REFERENCES
    161 
    162  q_gain_c.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
    163 
    164 ------------------------------------------------------------------------------
    165  PSEUDO-CODE
    166 
    167 
    168 ------------------------------------------------------------------------------
    169  RESOURCES USED [optional]
    170 
    171  When the code is written for a specific target processor the
    172  the resources used should be documented below.
    173 
    174  HEAP MEMORY USED: x bytes
    175 
    176  STACK MEMORY USED: x bytes
    177 
    178  CLOCK CYCLES: (cycle count equation for this function) + (variable
    179                 used to represent cycle count for each subroutine
    180                 called)
    181      where: (cycle count variable) = cycle count for [subroutine
    182                                      name]
    183 
    184 ------------------------------------------------------------------------------
    185  CAUTION [optional]
    186  [State any special notes, constraints or cautions for users of this function]
    187 
    188 ------------------------------------------------------------------------------
    189 */
    190 
    191 Word16 q_gain_code(         /* o  : quantization index,            Q0  */
    192     enum Mode mode,         /* i  : AMR mode                           */
    193     Word16 exp_gcode0,      /* i  : predicted CB gain (exponent),  Q0  */
    194     Word16 frac_gcode0,     /* i  : predicted CB gain (fraction),  Q15 */
    195     Word16 *gain,           /* i/o: quantized fixed codebook gain, Q1  */
    196     Word16 *qua_ener_MR122, /* o  : quantized energy error,        Q10 */
    197     /*      (for MR122 MA predictor update)    */
    198     Word16 *qua_ener,       /* o  : quantized energy error,        Q10 */
    199     /*      (for other MA predictor update)    */
    200     Flag   *pOverflow
    201 )
    202 {
    203     const Word16 *p;
    204     Word16 i;
    205     Word16 index;
    206     Word16 gcode0;
    207     Word16 err;
    208     Word16 err_min;
    209     Word16 g_q0;
    210     Word16 temp;
    211 
    212     if (mode == MR122)
    213     {
    214         g_q0 = *gain >> 1; /* Q1 -> Q0 */
    215     }
    216     else
    217     {
    218         g_q0 = *gain;
    219     }
    220 
    221     /*-------------------------------------------------------------------*
    222      *  predicted codebook gain                                          *
    223      *  ~~~~~~~~~~~~~~~~~~~~~~~                                          *
    224      *  gc0     = Pow2(int(d)+frac(d))                                   *
    225      *          = 2^exp + 2^frac                                         *
    226      *                                                                   *
    227      *-------------------------------------------------------------------*/
    228 
    229     gcode0 = (Word16) Pow2(exp_gcode0, frac_gcode0, pOverflow);  /* predicted gain */
    230 
    231     if (mode == MR122)
    232     {
    233         gcode0 = shl(gcode0, 4, pOverflow);
    234     }
    235     else
    236     {
    237         gcode0 = shl(gcode0, 5, pOverflow);
    238     }
    239 
    240     /*-------------------------------------------------------------------*
    241      *                   Search for best quantizer                        *
    242      *-------------------------------------------------------------------*/
    243 
    244     p = &qua_gain_code[0];
    245     err_min = ((Word32)gcode0 * *(p++)) >> 15;
    246     err_min =  g_q0 - err_min;
    247     if (err_min < 0)
    248     {
    249         err_min = -err_min;
    250     }
    251 
    252     p += 2;                                  /* skip quantized energy errors */
    253     index = 0;
    254 
    255     for (i = 1; i < NB_QUA_CODE; i++)
    256     {
    257         err = ((Word32)gcode0 * *(p++)) >> 15;
    258         err =  g_q0 - err;
    259 
    260         if (err < 0)
    261         {
    262             err = -err;
    263         }
    264 
    265         p += 2;                              /* skip quantized energy error */
    266 
    267         if (err < err_min)
    268         {
    269             err_min = err;
    270             index = i;
    271         }
    272     }
    273 
    274     temp = index + (index << 1);
    275 
    276     p = &qua_gain_code[temp];
    277 
    278     temp  = (gcode0 * *(p++)) >> 15;
    279     if (mode == MR122)
    280     {
    281         *gain =  temp << 1;
    282     }
    283     else
    284     {
    285         *gain = temp;
    286     }
    287 
    288     /* quantized error energies (for MA predictor update) */
    289     *qua_ener_MR122 = *p++;
    290     *qua_ener = *p;
    291 
    292     return index;
    293 }
    294