Mercurial > hg > audiostuff
comparison intercom/gsm/short_te.c @ 2:13be24d74cd2
import intercom-0.4.1
| author | Peter Meerwald <pmeerw@cosy.sbg.ac.at> |
|---|---|
| date | Fri, 25 Jun 2010 09:57:52 +0200 |
| parents | |
| children |
comparison
equal
deleted
inserted
replaced
| 1:9cadc470e3da | 2:13be24d74cd2 |
|---|---|
| 1 /* | |
| 2 * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische | |
| 3 * Universitaet Berlin. See the accompanying file "COPYRIGHT" for | |
| 4 * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. | |
| 5 */ | |
| 6 | |
| 7 /* $Header: /home/kbs/jutta/src/gsm/gsm-1.0/src/RCS/short_term.c,v 1.1 1992/10/28 00:15:50 jutta Exp $ */ | |
| 8 | |
| 9 #include <stdio.h> | |
| 10 #include <assert.h> | |
| 11 | |
| 12 #include "private.h" | |
| 13 | |
| 14 #include "gsm.h" | |
| 15 #include "proto.h" | |
| 16 | |
| 17 /* | |
| 18 * SHORT TERM ANALYSIS FILTERING SECTION | |
| 19 */ | |
| 20 | |
| 21 /* 4.2.8 */ | |
| 22 | |
| 23 static void Decoding_of_the_coded_Log_Area_Ratios P2((LARc, LARpp), word * LARc, /* coded log area ratio [0..7] IN */ | |
| 24 word * LARpp) | |
| 25 { /* out: decoded .. */ | |
| 26 register word temp1; | |
| 27 /* register word temp2; -> This is unused */ | |
| 28 register long ltmp; /* for GSM_ADD */ | |
| 29 | |
| 30 /* This procedure requires for efficient implementation | |
| 31 * two tables. | |
| 32 * | |
| 33 * INVA[1..8] = integer( (32768 * 8) / real_A[1..8]) | |
| 34 * MIC[1..8] = minimum value of the LARc[1..8] | |
| 35 */ | |
| 36 | |
| 37 /* Compute the LARpp[1..8] | |
| 38 */ | |
| 39 | |
| 40 /* for (i = 1; i <= 8; i++, B++, MIC++, INVA++, LARc++, LARpp++) { | |
| 41 * | |
| 42 * temp1 = GSM_ADD( *LARc, *MIC ) << 10; | |
| 43 * temp2 = *B << 1; | |
| 44 * temp1 = GSM_SUB( temp1, temp2 ); | |
| 45 * | |
| 46 * assert(*INVA != MIN_WORD); | |
| 47 * | |
| 48 * temp1 = GSM_MULT_R( *INVA, temp1 ); | |
| 49 * *LARpp = GSM_ADD( temp1, temp1 ); | |
| 50 * } | |
| 51 */ | |
| 52 | |
| 53 #ifdef STEP | |
| 54 #undef STEP | |
| 55 #endif | |
| 56 | |
| 57 #define STEP( B, MIC, INVA ) \ | |
| 58 temp1 = GSM_ADD( *LARc++, MIC ) << 10; \ | |
| 59 temp1 = GSM_SUB( temp1, B << 1 ); \ | |
| 60 temp1 = GSM_MULT_R( INVA, temp1 ); \ | |
| 61 *LARpp++ = GSM_ADD( temp1, temp1 ); | |
| 62 | |
| 63 STEP(0, -32, 13107); | |
| 64 STEP(0, -32, 13107); | |
| 65 STEP(2048, -16, 13107); | |
| 66 STEP(-2560, -16, 13107); | |
| 67 | |
| 68 STEP(94, -8, 19223); | |
| 69 STEP(-1792, -8, 17476); | |
| 70 STEP(-341, -4, 31454); | |
| 71 STEP(-1144, -4, 29708); | |
| 72 | |
| 73 /* NOTE: the addition of *MIC is used to restore | |
| 74 * the sign of *LARc. | |
| 75 */ | |
| 76 } | |
| 77 | |
| 78 /* 4.2.9 */ | |
| 79 /* Computation of the quantized reflection coefficients | |
| 80 */ | |
| 81 | |
| 82 /* 4.2.9.1 Interpolation of the LARpp[1..8] to get the LARp[1..8] | |
| 83 */ | |
| 84 | |
| 85 /* | |
| 86 * Within each frame of 160 analyzed speech samples the short term | |
| 87 * analysis and synthesis filters operate with four different sets of | |
| 88 * coefficients, derived from the previous set of decoded LARs(LARpp(j-1)) | |
| 89 * and the actual set of decoded LARs (LARpp(j)) | |
| 90 * | |
| 91 * (Initial value: LARpp(j-1)[1..8] = 0.) | |
| 92 */ | |
| 93 | |
| 94 static void Coefficients_0_12 P3((LARpp_j_1, LARpp_j, LARp), | |
| 95 register word * LARpp_j_1, | |
| 96 register word * LARpp_j, register word * LARp) | |
| 97 { | |
| 98 register int i; | |
| 99 register longword ltmp; | |
| 100 | |
| 101 for (i = 1; i <= 8; i++, LARp++, LARpp_j_1++, LARpp_j++) { | |
| 102 *LARp = GSM_ADD(SASR(*LARpp_j_1, 2), SASR(*LARpp_j, 2)); | |
| 103 *LARp = GSM_ADD(*LARp, SASR(*LARpp_j_1, 1)); | |
| 104 } | |
| 105 } | |
| 106 | |
| 107 static void Coefficients_13_26 P3((LARpp_j_1, LARpp_j, LARp), | |
| 108 register word * LARpp_j_1, | |
| 109 register word * LARpp_j, register word * LARp) | |
| 110 { | |
| 111 register int i; | |
| 112 register longword ltmp; | |
| 113 for (i = 1; i <= 8; i++, LARpp_j_1++, LARpp_j++, LARp++) { | |
| 114 *LARp = GSM_ADD(SASR(*LARpp_j_1, 1), SASR(*LARpp_j, 1)); | |
| 115 } | |
| 116 } | |
| 117 | |
| 118 static void Coefficients_27_39 P3((LARpp_j_1, LARpp_j, LARp), | |
| 119 register word * LARpp_j_1, | |
| 120 register word * LARpp_j, register word * LARp) | |
| 121 { | |
| 122 register int i; | |
| 123 register longword ltmp; | |
| 124 | |
| 125 for (i = 1; i <= 8; i++, LARpp_j_1++, LARpp_j++, LARp++) { | |
| 126 *LARp = GSM_ADD(SASR(*LARpp_j_1, 2), SASR(*LARpp_j, 2)); | |
| 127 *LARp = GSM_ADD(*LARp, SASR(*LARpp_j, 1)); | |
| 128 } | |
| 129 } | |
| 130 | |
| 131 | |
| 132 static void Coefficients_40_159 P2((LARpp_j, LARp), | |
| 133 register word * LARpp_j, register word * LARp) | |
| 134 { | |
| 135 register int i; | |
| 136 | |
| 137 for (i = 1; i <= 8; i++, LARp++, LARpp_j++) | |
| 138 *LARp = *LARpp_j; | |
| 139 } | |
| 140 | |
| 141 /* 4.2.9.2 */ | |
| 142 | |
| 143 static void LARp_to_rp P1((LARp), register word * LARp) | |
| 144 { /* [0..7] IN/OUT */ | |
| 145 /* | |
| 146 * The input of this procedure is the interpolated LARp[0..7] array. | |
| 147 * The reflection coefficients, rp[i], are used in the analysis | |
| 148 * filter and in the synthesis filter. | |
| 149 */ | |
| 150 register int i; | |
| 151 register word temp; | |
| 152 register longword ltmp; | |
| 153 | |
| 154 for (i = 1; i <= 8; i++, LARp++) { | |
| 155 | |
| 156 /* temp = GSM_ABS( *LARp ); | |
| 157 * | |
| 158 * if (temp < 11059) temp <<= 1; | |
| 159 * else if (temp < 20070) temp += 11059; | |
| 160 * else temp = GSM_ADD( temp >> 2, 26112 ); | |
| 161 * | |
| 162 * *LARp = *LARp < 0 ? -temp : temp; | |
| 163 */ | |
| 164 | |
| 165 if (*LARp < 0) { | |
| 166 temp = *LARp == MIN_WORD ? MAX_WORD : -(*LARp); | |
| 167 *LARp = -((temp < 11059) ? temp << 1 | |
| 168 : ((temp < 20070) ? temp + 11059 : GSM_ADD(temp >> 2, 26112))); | |
| 169 } else { | |
| 170 temp = *LARp; | |
| 171 *LARp = (temp < 11059) ? temp << 1 | |
| 172 : ((temp < 20070) ? temp + 11059 : GSM_ADD(temp >> 2, 26112)); | |
| 173 } | |
| 174 } | |
| 175 } | |
| 176 | |
| 177 | |
| 178 /* 4.2.10 */ | |
| 179 static void Short_term_analysis_filtering P4((S, rp, k_n, s), struct gsm_state *S, register word * rp, /* [0..7] IN */ | |
| 180 register int k_n, /* k_end - k_start */ | |
| 181 register word * s /* [0..n-1] IN/OUT */ | |
| 182 ) | |
| 183 /* | |
| 184 * This procedure computes the short term residual signal d[..] to be fed | |
| 185 * to the RPE-LTP loop from the s[..] signal and from the local rp[..] | |
| 186 * array (quantized reflection coefficients). As the call of this | |
| 187 * procedure can be done in many ways (see the interpolation of the LAR | |
| 188 * coefficient), it is assumed that the computation begins with index | |
| 189 * k_start (for arrays d[..] and s[..]) and stops with index k_end | |
| 190 * (k_start and k_end are defined in 4.2.9.1). This procedure also | |
| 191 * needs to keep the array u[0..7] in memory for each call. | |
| 192 */ | |
| 193 { | |
| 194 register word *u = S->u; | |
| 195 register int i; | |
| 196 register word di, zzz, ui, sav, rpi; | |
| 197 register longword ltmp; | |
| 198 | |
| 199 for (; k_n--; s++) { | |
| 200 | |
| 201 di = sav = *s; | |
| 202 | |
| 203 for (i = 0; i < 8; i++) { /* YYY */ | |
| 204 | |
| 205 ui = u[i]; | |
| 206 rpi = rp[i]; | |
| 207 u[i] = sav; | |
| 208 | |
| 209 zzz = GSM_MULT_R(rpi, di); | |
| 210 sav = GSM_ADD(ui, zzz); | |
| 211 | |
| 212 zzz = GSM_MULT_R(rpi, ui); | |
| 213 di = GSM_ADD(di, zzz); | |
| 214 } | |
| 215 | |
| 216 *s = di; | |
| 217 } | |
| 218 } | |
| 219 | |
| 220 #if defined(USE_FLOAT_MUL) && defined(FAST) | |
| 221 | |
| 222 static void Fast_Short_term_analysis_filtering P4((S, rp, k_n, s), struct gsm_state *S, register word * rp, /* [0..7] IN */ | |
| 223 register int k_n, /* k_end - k_start */ | |
| 224 register word * s /* [0..n-1] IN/OUT */ | |
| 225 ) | |
| 226 { | |
| 227 register word *u = S->u; | |
| 228 register int i; | |
| 229 | |
| 230 float uf[8], rpf[8]; | |
| 231 | |
| 232 register float scalef = 3.0517578125e-5; | |
| 233 register float sav, di, temp; | |
| 234 | |
| 235 for (i = 0; i < 8; ++i) { | |
| 236 uf[i] = u[i]; | |
| 237 rpf[i] = rp[i] * scalef; | |
| 238 } | |
| 239 for (; k_n--; s++) { | |
| 240 sav = di = *s; | |
| 241 for (i = 0; i < 8; ++i) { | |
| 242 register float rpfi = rpf[i]; | |
| 243 register float ufi = uf[i]; | |
| 244 | |
| 245 uf[i] = sav; | |
| 246 temp = rpfi * di + ufi; | |
| 247 di += rpfi * ufi; | |
| 248 sav = temp; | |
| 249 } | |
| 250 *s = di; | |
| 251 } | |
| 252 for (i = 0; i < 8; ++i) | |
| 253 u[i] = uf[i]; | |
| 254 } | |
| 255 #endif /* ! (defined (USE_FLOAT_MUL) && defined (FAST)) */ | |
| 256 | |
| 257 static void Short_term_synthesis_filtering P5((S, rrp, k, wt, sr), struct gsm_state *S, register word * rrp, /* [0..7] IN */ | |
| 258 register int k, /* k_end - k_start */ | |
| 259 register word * wt, /* [0..k-1] IN */ | |
| 260 register word * sr /* [0..k-1] OUT */ | |
| 261 ) | |
| 262 { | |
| 263 register word *v = S->v; | |
| 264 register int i; | |
| 265 register word sri, tmp1, tmp2; | |
| 266 register longword ltmp; /* for GSM_ADD & GSM_SUB */ | |
| 267 | |
| 268 while (k--) { | |
| 269 sri = *wt++; | |
| 270 for (i = 8; i--;) { | |
| 271 | |
| 272 /* sri = GSM_SUB( sri, gsm_mult_r( rrp[i], v[i] ) ); | |
| 273 */ | |
| 274 tmp1 = rrp[i]; | |
| 275 tmp2 = v[i]; | |
| 276 tmp2 = (tmp1 == MIN_WORD && tmp2 == MIN_WORD | |
| 277 ? MAX_WORD | |
| 278 : 0x0FFFF & (((longword) tmp1 * (longword) tmp2 | |
| 279 + 16384) >> 15)); | |
| 280 | |
| 281 sri = GSM_SUB(sri, tmp2); | |
| 282 | |
| 283 /* v[i+1] = GSM_ADD( v[i], gsm_mult_r( rrp[i], sri ) ); | |
| 284 */ | |
| 285 tmp1 = (tmp1 == MIN_WORD && sri == MIN_WORD | |
| 286 ? MAX_WORD | |
| 287 : 0x0FFFF & (((longword) tmp1 * (longword) sri + 16384) >> 15)); | |
| 288 | |
| 289 v[i + 1] = GSM_ADD(v[i], tmp1); | |
| 290 } | |
| 291 *sr++ = v[0] = sri; | |
| 292 } | |
| 293 } | |
| 294 | |
| 295 | |
| 296 #if defined(FAST) && defined(USE_FLOAT_MUL) | |
| 297 | |
| 298 static void Fast_Short_term_synthesis_filtering P5((S, rrp, k, wt, sr), struct gsm_state *S, register word * rrp, /* [0..7] IN */ | |
| 299 register int k, /* k_end - k_start */ | |
| 300 register word * wt, /* [0..k-1] IN */ | |
| 301 register word * sr /* [0..k-1] OUT */ | |
| 302 ) | |
| 303 { | |
| 304 register word *v = S->v; | |
| 305 register int i; | |
| 306 | |
| 307 float va[9], rrpa[8]; | |
| 308 register float scalef = 3.0517578125e-5, temp; | |
| 309 | |
| 310 for (i = 0; i < 8; ++i) { | |
| 311 va[i] = v[i]; | |
| 312 rrpa[i] = (float) rrp[i] * scalef; | |
| 313 } | |
| 314 while (k--) { | |
| 315 register float sri = *wt++; | |
| 316 for (i = 8; i--;) { | |
| 317 sri -= rrpa[i] * va[i]; | |
| 318 if (sri < -32768.) | |
| 319 sri = -32768.; | |
| 320 else if (sri > 32767.) | |
| 321 sri = 32767.; | |
| 322 | |
| 323 temp = va[i] + rrpa[i] * sri; | |
| 324 if (temp < -32768.) | |
| 325 temp = -32768.; | |
| 326 else if (temp > 32767.) | |
| 327 temp = 32767.; | |
| 328 va[i + 1] = temp; | |
| 329 } | |
| 330 *sr++ = va[0] = sri; | |
| 331 } | |
| 332 for (i = 0; i < 9; ++i) | |
| 333 v[i] = va[i]; | |
| 334 } | |
| 335 | |
| 336 #endif /* defined(FAST) && defined(USE_FLOAT_MUL) */ | |
| 337 | |
| 338 void Gsm_Short_Term_Analysis_Filter P3((S, LARc, s), struct gsm_state *S, word * LARc, /* coded log area ratio [0..7] IN */ | |
| 339 word * s /* signal [0..159] IN/OUT */ | |
| 340 ) | |
| 341 { | |
| 342 word *LARpp_j = S->LARpp[S->j]; | |
| 343 word *LARpp_j_1 = S->LARpp[S->j ^= 1]; | |
| 344 | |
| 345 word LARp[8]; | |
| 346 | |
| 347 #ifdef FILTER | |
| 348 #undef FILTER | |
| 349 #endif | |
| 350 | |
| 351 #if defined(FAST) && defined(USE_FLOAT_MUL) | |
| 352 # define FILTER (* (S->fast \ | |
| 353 ? Fast_Short_term_analysis_filtering \ | |
| 354 : Short_term_analysis_filtering )) | |
| 355 | |
| 356 #else | |
| 357 # define FILTER Short_term_analysis_filtering | |
| 358 #endif | |
| 359 | |
| 360 Decoding_of_the_coded_Log_Area_Ratios(LARc, LARpp_j); | |
| 361 | |
| 362 Coefficients_0_12(LARpp_j_1, LARpp_j, LARp); | |
| 363 LARp_to_rp(LARp); | |
| 364 FILTER(S, LARp, 13, s); | |
| 365 | |
| 366 Coefficients_13_26(LARpp_j_1, LARpp_j, LARp); | |
| 367 LARp_to_rp(LARp); | |
| 368 FILTER(S, LARp, 14, s + 13); | |
| 369 | |
| 370 Coefficients_27_39(LARpp_j_1, LARpp_j, LARp); | |
| 371 LARp_to_rp(LARp); | |
| 372 FILTER(S, LARp, 13, s + 27); | |
| 373 | |
| 374 Coefficients_40_159(LARpp_j, LARp); | |
| 375 LARp_to_rp(LARp); | |
| 376 FILTER(S, LARp, 120, s + 40); | |
| 377 } | |
| 378 | |
| 379 void Gsm_Short_Term_Synthesis_Filter P4((S, LARcr, wt, s), struct gsm_state *S, word * LARcr, /* received log area ratios [0..7] IN */ | |
| 380 word * wt, /* received d [0..159] IN */ | |
| 381 word * s /* signal s [0..159] OUT */ | |
| 382 ) | |
| 383 { | |
| 384 word *LARpp_j = S->LARpp[S->j]; | |
| 385 word *LARpp_j_1 = S->LARpp[S->j ^= 1]; | |
| 386 | |
| 387 word LARp[8]; | |
| 388 | |
| 389 #ifdef FILTER | |
| 390 #undef FILTER | |
| 391 #endif | |
| 392 | |
| 393 #if defined(FAST) && defined(USE_FLOAT_MUL) | |
| 394 | |
| 395 # define FILTER (* (S->fast \ | |
| 396 ? Fast_Short_term_synthesis_filtering \ | |
| 397 : Short_term_synthesis_filtering )) | |
| 398 #else | |
| 399 # define FILTER Short_term_synthesis_filtering | |
| 400 #endif | |
| 401 | |
| 402 Decoding_of_the_coded_Log_Area_Ratios(LARcr, LARpp_j); | |
| 403 | |
| 404 Coefficients_0_12(LARpp_j_1, LARpp_j, LARp); | |
| 405 LARp_to_rp(LARp); | |
| 406 FILTER(S, LARp, 13, wt, s); | |
| 407 | |
| 408 Coefficients_13_26(LARpp_j_1, LARpp_j, LARp); | |
| 409 LARp_to_rp(LARp); | |
| 410 FILTER(S, LARp, 14, wt + 13, s + 13); | |
| 411 | |
| 412 Coefficients_27_39(LARpp_j_1, LARpp_j, LARp); | |
| 413 LARp_to_rp(LARp); | |
| 414 FILTER(S, LARp, 13, wt + 27, s + 27); | |
| 415 | |
| 416 Coefficients_40_159(LARpp_j, LARp); | |
| 417 LARp_to_rp(LARp); | |
| 418 FILTER(S, LARp, 120, wt + 40, s + 40); | |
| 419 } |
