⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pvamrwb_math_op.cpp

📁 实现3GPP的GSM中AMR语音的CODECS。
💻 CPP
📖 第 1 页 / 共 2 页
字号:
{    32767, 31790, 30894, 30070, 29309, 28602, 27945, 27330, 26755, 26214,    25705, 25225, 24770, 24339, 23930, 23541, 23170, 22817, 22479, 22155,    21845, 21548, 21263, 20988, 20724, 20470, 20225, 19988, 19760, 19539,    19326, 19119, 18919, 18725, 18536, 18354, 18176, 18004, 17837, 17674,    17515, 17361, 17211, 17064, 16921, 16782, 16646, 16514, 16384};void one_ov_sqrt_norm(    int32 * frac,                        /* (i/o) Q31: normalized value (1.0 < frac <= 0.5) */    int16 * exp                          /* (i/o)    : exponent (value = frac x 2^exponent) */){    int16 i, a, tmp;    if (*frac <= (int32) 0)    {        *exp = 0;        *frac = 0x7fffffffL;        return;    }    if ((*exp & 1) == 1)  /* If exponant odd -> shift right */        *frac >>= 1;    *exp = negate_int16((*exp -  1) >> 1);    *frac >>= 9;    i = extract_h(*frac);                  /* Extract b25-b31 */    *frac >>= 1;    a = (int16)(*frac);                  /* Extract b10-b24 */    a = (int16)(a & (int16) 0x7fff);    i -= 16;    *frac = L_deposit_h(table_isqrt[i]);   /* table[i] << 16         */    tmp = table_isqrt[i] - table_isqrt[i + 1];      /* table[i] - table[i+1]) */    *frac = msu_16by16_from_int32(*frac, tmp, a);          /* frac -=  tmp*a*2       */    return;}/*----------------------------------------------------------------------------     Function Name : power_2()       L_x = pow(2.0, exponant.fraction)         (exponant = interger part)           = pow(2.0, 0.fraction) << exponant  Algorithm:     The function power_2(L_x) is approximated by a table and linear     interpolation.     1- i = bit10-b15 of fraction,   0 <= i <= 31     2- a = bit0-b9   of fraction     3- L_x = table[i]<<16 - (table[i] - table[i+1]) * a * 2     4- L_x = L_x >> (30-exponant)     (with rounding) ----------------------------------------------------------------------------*/const int16 table_pow2[33] ={    16384, 16743, 17109, 17484, 17867, 18258, 18658, 19066, 19484, 19911,    20347, 20792, 21247, 21713, 22188, 22674, 23170, 23678, 24196, 24726,    25268, 25821, 26386, 26964, 27554, 28158, 28774, 29405, 30048, 30706,    31379, 32066, 32767};int32 power_of_2(                         /* (o) Q0  : result       (range: 0<=val<=0x7fffffff) */    int16 exponant,                      /* (i) Q0  : Integer part.      (range: 0<=val<=30)   */    int16 fraction                       /* (i) Q15 : Fractionnal part.  (range: 0.0<=val<1.0) */){    int16 exp, i, a, tmp;    int32 L_x;    L_x = fraction << 5;          /* L_x = fraction<<6           */    i = (fraction >> 10);                  /* Extract b10-b16 of fraction */    a = (int16)(L_x);                    /* Extract b0-b9   of fraction */    a = (int16)(a & (int16) 0x7fff);    L_x = ((int32)table_pow2[i]) << 15;    /* table[i] << 16        */    tmp = table_pow2[i] - table_pow2[i + 1];        /* table[i] - table[i+1] */    L_x -= ((int32)tmp * a);             /* L_x -= tmp*a*2        */    exp = 29 - exponant ;    if (exp)    {        L_x = ((L_x >> exp) + ((L_x >> (exp - 1)) & 1));    }    return (L_x);}/*---------------------------------------------------------------------------- * *   Function Name : Dot_product12() * *       Compute scalar product of <x[],y[]> using accumulator. * *       The result is normalized (in Q31) with exponent (0..30). * *  Algorithm: * *       dot_product = sum(x[i]*y[i])     i=0..N-1 ----------------------------------------------------------------------------*/int32 Dot_product12(   /* (o) Q31: normalized result (1 < val <= -1) */    int16 x[],        /* (i) 12bits: x vector                       */    int16 y[],        /* (i) 12bits: y vector                       */    int16 lg,         /* (i)    : vector length                     */    int16 * exp       /* (o)    : exponent of result (0..+30)       */){    int16 i, sft;    int32 L_sum;    int16 *pt_x = x;    int16 *pt_y = y;    L_sum = 1L;    for (i = lg >> 3; i != 0; i--)    {        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));        L_sum = mac_16by16_to_int32(L_sum, *(pt_x++), *(pt_y++));    }    /* Normalize acc in Q31 */    sft = normalize_amr_wb(L_sum);    L_sum <<= sft;    *exp = 30 - sft;                    /* exponent = 0..30 */    return (L_sum);}/* Table for Log2() */const int16 Log2_norm_table[33] ={    0, 1455, 2866, 4236, 5568, 6863, 8124, 9352, 10549, 11716,    12855, 13967, 15054, 16117, 17156, 18172, 19167, 20142, 21097, 22033,    22951, 23852, 24735, 25603, 26455, 27291, 28113, 28922, 29716, 30497,    31266, 32023, 32767};/*---------------------------------------------------------------------------- * *   FUNCTION:   Lg2_normalized() * *   PURPOSE:   Computes log2(L_x, exp),  where   L_x is positive and *              normalized, and exp is the normalisation exponent *              If L_x is negative or zero, the result is 0. * *   DESCRIPTION: *        The function Log2(L_x) is approximated by a table and linear *        interpolation. The following steps are used to compute Log2(L_x) * *           1- exponent = 30-norm_exponent *           2- i = bit25-b31 of L_x;  32<=i<=63  (because of normalization). *           3- a = bit10-b24 *           4- i -=32 *           5- fraction = table[i]<<16 - (table[i] - table[i+1]) * a * 2 *----------------------------------------------------------------------------*/void Lg2_normalized(    int32 L_x,         /* (i) : input value (normalized)                    */    int16 exp,         /* (i) : norm_l (L_x)                                */    int16 *exponent,   /* (o) : Integer part of Log2.   (range: 0<=val<=30) */    int16 *fraction    /* (o) : Fractional part of Log2. (range: 0<=val<1)  */){    int16 i, a, tmp;    int32 L_y;    if (L_x <= (int32) 0)    {        *exponent = 0;        *fraction = 0;;        return;    }    *exponent = 30 - exp;    L_x >>= 9;    i = extract_h(L_x);                 /* Extract b25-b31 */    L_x >>= 1;    a = (int16)(L_x);                 /* Extract b10-b24 of fraction */    a &= 0x7fff;    i -= 32;    L_y = L_deposit_h(Log2_norm_table[i]);             /* table[i] << 16        */    tmp = Log2_norm_table[i] - Log2_norm_table[i + 1]; /* table[i] - table[i+1] */    L_y = msu_16by16_from_int32(L_y, tmp, a);           /* L_y -= tmp*a*2        */    *fraction = extract_h(L_y);    return;}/*---------------------------------------------------------------------------- * *   FUNCTION:   amrwb_log_2() * *   PURPOSE:   Computes log2(L_x),  where   L_x is positive. *              If L_x is negative or zero, the result is 0. * *   DESCRIPTION: *        normalizes L_x and then calls Lg2_normalized(). * ----------------------------------------------------------------------------*/void amrwb_log_2(    int32 L_x,         /* (i) : input value                                 */    int16 *exponent,   /* (o) : Integer part of Log2.   (range: 0<=val<=30) */    int16 *fraction    /* (o) : Fractional part of Log2. (range: 0<=val<1) */){    int16 exp;    exp = normalize_amr_wb(L_x);    Lg2_normalized(shl_int32(L_x, exp), exp, exponent, fraction);}/***************************************************************************** * *  These operations are not standard double precision operations.           * *  They are used where single precision is not enough but the full 32 bits  * *  precision is not necessary. For example, the function Div_32() has a     * *  24 bits precision which is enough for our purposes.                      * *                                                                           * *  The double precision numbers use a special representation:               * *                                                                           * *     L_32 = hi<<16 + lo<<1                                                 * *                                                                           * *  L_32 is a 32 bit integer.                                                * *  hi and lo are 16 bit signed integers.                                    * *  As the low part also contains the sign, this allows fast multiplication. * *                                                                           * *      0x8000 0000 <= L_32 <= 0x7fff fffe.                                  * *                                                                           * *  We will use DPF (Double Precision Format )in this file to specify        * *  this special format.                                                     * ******************************************************************************//*---------------------------------------------------------------------------- * *  Function int32_to_dpf() * *  Extract from a 32 bit integer two 16 bit DPF. * *  Arguments: * *   L_32      : 32 bit integer. *               0x8000 0000 <= L_32 <= 0x7fff ffff. *   hi        : b16 to b31 of L_32 *   lo        : (L_32 - hi<<16)>>1 * ----------------------------------------------------------------------------*/void int32_to_dpf(int32 L_32, int16 *hi, int16 *lo){    *hi = (int16)(L_32 >> 16);    *lo = (int16)((L_32 - (*hi << 16)) >> 1);    return;}/*---------------------------------------------------------------------------- * Function mpy_dpf_32() * *   Multiply two 32 bit integers (DPF). The result is divided by 2**31 * *   L_32 = (hi1*hi2)<<1 + ( (hi1*lo2)>>15 + (lo1*hi2)>>15 )<<1 * *   This operation can also be viewed as the multiplication of two Q31 *   number and the result is also in Q31. * * Arguments: * *  hi1         hi part of first number *  lo1         lo part of first number *  hi2         hi part of second number *  lo2         lo part of second number * ----------------------------------------------------------------------------*/int32 mpy_dpf_32(int16 hi1, int16 lo1, int16 hi2, int16 lo2){    int32 L_32;    L_32 = mul_16by16_to_int32(hi1, hi2);    L_32 = mac_16by16_to_int32(L_32, mult_int16(hi1, lo2), 1);    L_32 = mac_16by16_to_int32(L_32, mult_int16(lo1, hi2), 1);    return (L_32);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -