Mercurial > hg > audiostuff
comparison spandsp-0.0.6pre17/src/gsm0610_preprocess.c @ 4:26cd8f1ef0b1
import spandsp-0.0.6pre17
author | Peter Meerwald <pmeerw@cosy.sbg.ac.at> |
---|---|
date | Fri, 25 Jun 2010 15:50:58 +0200 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
3:c6c5a16ce2f2 | 4:26cd8f1ef0b1 |
---|---|
1 /* | |
2 * SpanDSP - a series of DSP components for telephony | |
3 * | |
4 * gsm0610_preprocess.c - GSM 06.10 full rate speech codec. | |
5 * | |
6 * Written by Steve Underwood <steveu@coppice.org> | |
7 * | |
8 * Copyright (C) 2006 Steve Underwood | |
9 * | |
10 * All rights reserved. | |
11 * | |
12 * This program is free software; you can redistribute it and/or modify | |
13 * it under the terms of the GNU Lesser General Public License version 2.1, | |
14 * as published by the Free Software Foundation. | |
15 * | |
16 * This program is distributed in the hope that it will be useful, | |
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
19 * GNU Lesser General Public License for more details. | |
20 * | |
21 * You should have received a copy of the GNU Lesser General Public | |
22 * License along with this program; if not, write to the Free Software | |
23 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |
24 * | |
25 * This code is based on the widely used GSM 06.10 code available from | |
26 * http://kbs.cs.tu-berlin.de/~jutta/toast.html | |
27 * | |
28 * $Id: gsm0610_preprocess.c,v 1.17 2009/02/03 16:28:39 steveu Exp $ | |
29 */ | |
30 | |
31 /*! \file */ | |
32 | |
33 #if defined(HAVE_CONFIG_H) | |
34 #include "config.h" | |
35 #endif | |
36 | |
37 #include <assert.h> | |
38 #include <inttypes.h> | |
39 #if defined(HAVE_TGMATH_H) | |
40 #include <tgmath.h> | |
41 #endif | |
42 #if defined(HAVE_MATH_H) | |
43 #include <math.h> | |
44 #endif | |
45 #include "floating_fudge.h" | |
46 #include <stdlib.h> | |
47 | |
48 #include "spandsp/telephony.h" | |
49 #include "spandsp/fast_convert.h" | |
50 #include "spandsp/bitstream.h" | |
51 #include "spandsp/saturated.h" | |
52 #include "spandsp/gsm0610.h" | |
53 | |
54 #include "gsm0610_local.h" | |
55 | |
56 /* | |
57 4.2.0 .. 4.2.3 PREPROCESSING SECTION | |
58 | |
59 After A-law to linear conversion (or directly from the | |
60 A to D converter) the following scaling is assumed for | |
61 input to the RPE-LTP algorithm: | |
62 | |
63 in: 0.1.....................12 | |
64 S.v.v.v.v.v.v.v.v.v.v.v.v.*.*.* | |
65 | |
66 Where S is the sign bit, v a valid bit, and * a "don't care" bit. | |
67 The original signal is called sop[..] | |
68 | |
69 out: 0.1................... 12 | |
70 S.S.v.v.v.v.v.v.v.v.v.v.v.v.0.0 | |
71 */ | |
72 | |
73 void gsm0610_preprocess(gsm0610_state_t *s, const int16_t amp[GSM0610_FRAME_LEN], int16_t so[GSM0610_FRAME_LEN]) | |
74 { | |
75 int16_t z1; | |
76 int16_t mp; | |
77 int16_t s1; | |
78 int16_t msp; | |
79 int16_t SO; | |
80 int32_t L_z2; | |
81 int32_t L_s2; | |
82 int32_t L_temp; | |
83 #if !defined(__GNUC__) | |
84 int16_t lsp; | |
85 #endif | |
86 int k; | |
87 | |
88 z1 = s->z1; | |
89 L_z2 = s->L_z2; | |
90 mp = s->mp; | |
91 for (k = 0; k < GSM0610_FRAME_LEN; k++) | |
92 { | |
93 /* 4.2.1 Downscaling of the input signal */ | |
94 SO = (amp[k] >> 1) & ~3; | |
95 | |
96 assert(SO >= -0x4000); // downscaled by | |
97 assert(SO <= 0x3FFC); // previous routine. | |
98 | |
99 /* 4.2.2 Offset compensation */ | |
100 | |
101 /* This part implements a high-pass filter and requires extended | |
102 arithmetic precision for the recursive part of this filter. | |
103 The input of this procedure is the array so[0...159] and the | |
104 output the array sof[ 0...159 ]. | |
105 */ | |
106 /* Compute the non-recursive part */ | |
107 s1 = SO - z1; | |
108 z1 = SO; | |
109 | |
110 assert(s1 != INT16_MIN); | |
111 | |
112 /* Compute the recursive part */ | |
113 L_s2 = s1; | |
114 L_s2 <<= 15; | |
115 | |
116 /* Perform a 31 by 16 bits multiplication */ | |
117 #if defined(__GNUC__) | |
118 L_z2 = ((int64_t) L_z2*32735 + 0x4000) >> 15; | |
119 /* Alternate (ANSI) version of below line does slightly different rounding: | |
120 * L_temp = L_z2 >> 9; | |
121 * L_temp += L_temp >> 5; | |
122 * L_temp = (++L_temp) >> 1; | |
123 * L_z2 = L_z2 - L_temp; | |
124 */ | |
125 L_z2 = saturated_add32(L_z2, L_s2); | |
126 #else | |
127 /* This does L_z2 = L_z2 * 0x7FD5/0x8000 + L_s2 */ | |
128 msp = (int16_t) (L_z2 >> 15); | |
129 lsp = (int16_t) (L_z2 - ((int32_t) msp << 15)); | |
130 | |
131 L_s2 += gsm_mult_r(lsp, 32735); | |
132 L_temp = (int32_t) msp*32735; | |
133 L_z2 = saturated_add32(L_temp, L_s2); | |
134 #endif | |
135 | |
136 /* Compute sof[k] with rounding */ | |
137 L_temp = saturated_add32(L_z2, 16384); | |
138 | |
139 /* 4.2.3 Preemphasis */ | |
140 msp = gsm_mult_r(mp, -28180); | |
141 mp = (int16_t) (L_temp >> 15); | |
142 so[k] = saturated_add16(mp, msp); | |
143 } | |
144 /*endfor*/ | |
145 | |
146 s->z1 = z1; | |
147 s->L_z2 = L_z2; | |
148 s->mp = mp; | |
149 } | |
150 /*- End of function --------------------------------------------------------*/ | |
151 /*- End of file ------------------------------------------------------------*/ |