| Chris@69 | 1 /*********************************************************************** | 
| Chris@69 | 2 Copyright (c) 2006-2011, Skype Limited. All rights reserved. | 
| Chris@69 | 3 Redistribution and use in source and binary forms, with or without | 
| Chris@69 | 4 modification, are permitted provided that the following conditions | 
| Chris@69 | 5 are met: | 
| Chris@69 | 6 - Redistributions of source code must retain the above copyright notice, | 
| Chris@69 | 7 this list of conditions and the following disclaimer. | 
| Chris@69 | 8 - Redistributions in binary form must reproduce the above copyright | 
| Chris@69 | 9 notice, this list of conditions and the following disclaimer in the | 
| Chris@69 | 10 documentation and/or other materials provided with the distribution. | 
| Chris@69 | 11 - Neither the name of Internet Society, IETF or IETF Trust, nor the | 
| Chris@69 | 12 names of specific contributors, may be used to endorse or promote | 
| Chris@69 | 13 products derived from this software without specific prior written | 
| Chris@69 | 14 permission. | 
| Chris@69 | 15 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" | 
| Chris@69 | 16 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | 
| Chris@69 | 17 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | 
| Chris@69 | 18 ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE | 
| Chris@69 | 19 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR | 
| Chris@69 | 20 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF | 
| Chris@69 | 21 SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS | 
| Chris@69 | 22 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN | 
| Chris@69 | 23 CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | 
| Chris@69 | 24 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | 
| Chris@69 | 25 POSSIBILITY OF SUCH DAMAGE. | 
| Chris@69 | 26 ***********************************************************************/ | 
| Chris@69 | 27 | 
| Chris@69 | 28 #ifndef SILK_SIGPROC_FLP_H | 
| Chris@69 | 29 #define SILK_SIGPROC_FLP_H | 
| Chris@69 | 30 | 
| Chris@69 | 31 #include "SigProc_FIX.h" | 
| Chris@69 | 32 #include "float_cast.h" | 
| Chris@69 | 33 #include <math.h> | 
| Chris@69 | 34 | 
| Chris@69 | 35 #ifdef  __cplusplus | 
| Chris@69 | 36 extern "C" | 
| Chris@69 | 37 { | 
| Chris@69 | 38 #endif | 
| Chris@69 | 39 | 
| Chris@69 | 40 /********************************************************************/ | 
| Chris@69 | 41 /*                    SIGNAL PROCESSING FUNCTIONS                   */ | 
| Chris@69 | 42 /********************************************************************/ | 
| Chris@69 | 43 | 
| Chris@69 | 44 /* Chirp (bw expand) LP AR filter */ | 
| Chris@69 | 45 void silk_bwexpander_FLP( | 
| Chris@69 | 46     silk_float          *ar,                /* I/O  AR filter to be expanded (without leading 1)                */ | 
| Chris@69 | 47     const opus_int      d,                  /* I    length of ar                                                */ | 
| Chris@69 | 48     const silk_float    chirp               /* I    chirp factor (typically in range (0..1) )                   */ | 
| Chris@69 | 49 ); | 
| Chris@69 | 50 | 
| Chris@69 | 51 /* compute inverse of LPC prediction gain, and                          */ | 
| Chris@69 | 52 /* test if LPC coefficients are stable (all poles within unit circle)   */ | 
| Chris@69 | 53 /* this code is based on silk_FLP_a2k()                                 */ | 
| Chris@69 | 54 silk_float silk_LPC_inverse_pred_gain_FLP(  /* O    return inverse prediction gain, energy domain               */ | 
| Chris@69 | 55     const silk_float    *A,                 /* I    prediction coefficients [order]                             */ | 
| Chris@69 | 56     opus_int32          order               /* I    prediction order                                            */ | 
| Chris@69 | 57 ); | 
| Chris@69 | 58 | 
| Chris@69 | 59 silk_float silk_schur_FLP(                  /* O    returns residual energy                                     */ | 
| Chris@69 | 60     silk_float          refl_coef[],        /* O    reflection coefficients (length order)                      */ | 
| Chris@69 | 61     const silk_float    auto_corr[],        /* I    autocorrelation sequence (length order+1)                   */ | 
| Chris@69 | 62     opus_int            order               /* I    order                                                       */ | 
| Chris@69 | 63 ); | 
| Chris@69 | 64 | 
| Chris@69 | 65 void silk_k2a_FLP( | 
| Chris@69 | 66     silk_float          *A,                 /* O     prediction coefficients [order]                            */ | 
| Chris@69 | 67     const silk_float    *rc,                /* I     reflection coefficients [order]                            */ | 
| Chris@69 | 68     opus_int32          order               /* I     prediction order                                           */ | 
| Chris@69 | 69 ); | 
| Chris@69 | 70 | 
| Chris@69 | 71 /* compute autocorrelation */ | 
| Chris@69 | 72 void silk_autocorrelation_FLP( | 
| Chris@69 | 73     silk_float          *results,           /* O    result (length correlationCount)                            */ | 
| Chris@69 | 74     const silk_float    *inputData,         /* I    input data to correlate                                     */ | 
| Chris@69 | 75     opus_int            inputDataSize,      /* I    length of input                                             */ | 
| Chris@69 | 76     opus_int            correlationCount    /* I    number of correlation taps to compute                       */ | 
| Chris@69 | 77 ); | 
| Chris@69 | 78 | 
| Chris@69 | 79 opus_int silk_pitch_analysis_core_FLP(      /* O    Voicing estimate: 0 voiced, 1 unvoiced                      */ | 
| Chris@69 | 80     const silk_float    *frame,             /* I    Signal of length PE_FRAME_LENGTH_MS*Fs_kHz                  */ | 
| Chris@69 | 81     opus_int            *pitch_out,         /* O    Pitch lag values [nb_subfr]                                 */ | 
| Chris@69 | 82     opus_int16          *lagIndex,          /* O    Lag Index                                                   */ | 
| Chris@69 | 83     opus_int8           *contourIndex,      /* O    Pitch contour Index                                         */ | 
| Chris@69 | 84     silk_float          *LTPCorr,           /* I/O  Normalized correlation; input: value from previous frame    */ | 
| Chris@69 | 85     opus_int            prevLag,            /* I    Last lag of previous frame; set to zero is unvoiced         */ | 
| Chris@69 | 86     const silk_float    search_thres1,      /* I    First stage threshold for lag candidates 0 - 1              */ | 
| Chris@69 | 87     const silk_float    search_thres2,      /* I    Final threshold for lag candidates 0 - 1                    */ | 
| Chris@69 | 88     const opus_int      Fs_kHz,             /* I    sample frequency (kHz)                                      */ | 
| Chris@69 | 89     const opus_int      complexity,         /* I    Complexity setting, 0-2, where 2 is highest                 */ | 
| Chris@69 | 90     const opus_int      nb_subfr,           /* I    Number of 5 ms subframes                                    */ | 
| Chris@69 | 91     int                 arch                /* I    Run-time architecture                                       */ | 
| Chris@69 | 92 ); | 
| Chris@69 | 93 | 
| Chris@69 | 94 void silk_insertion_sort_decreasing_FLP( | 
| Chris@69 | 95     silk_float          *a,                 /* I/O  Unsorted / Sorted vector                                    */ | 
| Chris@69 | 96     opus_int            *idx,               /* O    Index vector for the sorted elements                        */ | 
| Chris@69 | 97     const opus_int      L,                  /* I    Vector length                                               */ | 
| Chris@69 | 98     const opus_int      K                   /* I    Number of correctly sorted positions                        */ | 
| Chris@69 | 99 ); | 
| Chris@69 | 100 | 
| Chris@69 | 101 /* Compute reflection coefficients from input signal */ | 
| Chris@69 | 102 silk_float silk_burg_modified_FLP(          /* O    returns residual energy                                     */ | 
| Chris@69 | 103     silk_float          A[],                /* O    prediction coefficients (length order)                      */ | 
| Chris@69 | 104     const silk_float    x[],                /* I    input signal, length: nb_subfr*(D+L_sub)                    */ | 
| Chris@69 | 105     const silk_float    minInvGain,         /* I    minimum inverse prediction gain                             */ | 
| Chris@69 | 106     const opus_int      subfr_length,       /* I    input signal subframe length (incl. D preceding samples)    */ | 
| Chris@69 | 107     const opus_int      nb_subfr,           /* I    number of subframes stacked in x                            */ | 
| Chris@69 | 108     const opus_int      D                   /* I    order                                                       */ | 
| Chris@69 | 109 ); | 
| Chris@69 | 110 | 
| Chris@69 | 111 /* multiply a vector by a constant */ | 
| Chris@69 | 112 void silk_scale_vector_FLP( | 
| Chris@69 | 113     silk_float          *data1, | 
| Chris@69 | 114     silk_float          gain, | 
| Chris@69 | 115     opus_int            dataSize | 
| Chris@69 | 116 ); | 
| Chris@69 | 117 | 
| Chris@69 | 118 /* copy and multiply a vector by a constant */ | 
| Chris@69 | 119 void silk_scale_copy_vector_FLP( | 
| Chris@69 | 120     silk_float          *data_out, | 
| Chris@69 | 121     const silk_float    *data_in, | 
| Chris@69 | 122     silk_float          gain, | 
| Chris@69 | 123     opus_int            dataSize | 
| Chris@69 | 124 ); | 
| Chris@69 | 125 | 
| Chris@69 | 126 /* inner product of two silk_float arrays, with result as double */ | 
| Chris@69 | 127 double silk_inner_product_FLP( | 
| Chris@69 | 128     const silk_float    *data1, | 
| Chris@69 | 129     const silk_float    *data2, | 
| Chris@69 | 130     opus_int            dataSize | 
| Chris@69 | 131 ); | 
| Chris@69 | 132 | 
| Chris@69 | 133 /* sum of squares of a silk_float array, with result as double */ | 
| Chris@69 | 134 double silk_energy_FLP( | 
| Chris@69 | 135     const silk_float    *data, | 
| Chris@69 | 136     opus_int            dataSize | 
| Chris@69 | 137 ); | 
| Chris@69 | 138 | 
| Chris@69 | 139 /********************************************************************/ | 
| Chris@69 | 140 /*                                MACROS                            */ | 
| Chris@69 | 141 /********************************************************************/ | 
| Chris@69 | 142 | 
| Chris@69 | 143 #define PI              (3.1415926536f) | 
| Chris@69 | 144 | 
| Chris@69 | 145 #define silk_min_float( a, b )                  (((a) < (b)) ? (a) :  (b)) | 
| Chris@69 | 146 #define silk_max_float( a, b )                  (((a) > (b)) ? (a) :  (b)) | 
| Chris@69 | 147 #define silk_abs_float( a )                     ((silk_float)fabs(a)) | 
| Chris@69 | 148 | 
| Chris@69 | 149 /* sigmoid function */ | 
| Chris@69 | 150 static OPUS_INLINE silk_float silk_sigmoid( silk_float x ) | 
| Chris@69 | 151 { | 
| Chris@69 | 152     return (silk_float)(1.0 / (1.0 + exp(-x))); | 
| Chris@69 | 153 } | 
| Chris@69 | 154 | 
| Chris@69 | 155 /* floating-point to integer conversion (rounding) */ | 
| Chris@69 | 156 static OPUS_INLINE opus_int32 silk_float2int( silk_float x ) | 
| Chris@69 | 157 { | 
| Chris@69 | 158     return (opus_int32)float2int( x ); | 
| Chris@69 | 159 } | 
| Chris@69 | 160 | 
| Chris@69 | 161 /* floating-point to integer conversion (rounding) */ | 
| Chris@69 | 162 static OPUS_INLINE void silk_float2short_array( | 
| Chris@69 | 163     opus_int16       *out, | 
| Chris@69 | 164     const silk_float *in, | 
| Chris@69 | 165     opus_int32       length | 
| Chris@69 | 166 ) | 
| Chris@69 | 167 { | 
| Chris@69 | 168     opus_int32 k; | 
| Chris@69 | 169     for( k = length - 1; k >= 0; k-- ) { | 
| Chris@69 | 170         out[k] = silk_SAT16( (opus_int32)float2int( in[k] ) ); | 
| Chris@69 | 171     } | 
| Chris@69 | 172 } | 
| Chris@69 | 173 | 
| Chris@69 | 174 /* integer to floating-point conversion */ | 
| Chris@69 | 175 static OPUS_INLINE void silk_short2float_array( | 
| Chris@69 | 176     silk_float       *out, | 
| Chris@69 | 177     const opus_int16 *in, | 
| Chris@69 | 178     opus_int32       length | 
| Chris@69 | 179 ) | 
| Chris@69 | 180 { | 
| Chris@69 | 181     opus_int32 k; | 
| Chris@69 | 182     for( k = length - 1; k >= 0; k-- ) { | 
| Chris@69 | 183         out[k] = (silk_float)in[k]; | 
| Chris@69 | 184     } | 
| Chris@69 | 185 } | 
| Chris@69 | 186 | 
| Chris@69 | 187 /* using log2() helps the fixed-point conversion */ | 
| Chris@69 | 188 static OPUS_INLINE silk_float silk_log2( double x ) | 
| Chris@69 | 189 { | 
| Chris@69 | 190     return ( silk_float )( 3.32192809488736 * log10( x ) ); | 
| Chris@69 | 191 } | 
| Chris@69 | 192 | 
| Chris@69 | 193 #ifdef  __cplusplus | 
| Chris@69 | 194 } | 
| Chris@69 | 195 #endif | 
| Chris@69 | 196 | 
| Chris@69 | 197 #endif /* SILK_SIGPROC_FLP_H */ |