1/*---------------------------------------------------------------------------* 2 * ca_wave.c * 3 * * 4 * Copyright 2007, 2008 Nuance Communciations, Inc. * 5 * * 6 * Licensed under the Apache License, Version 2.0 (the 'License'); * 7 * you may not use this file except in compliance with the License. * 8 * * 9 * You may obtain a copy of the License at * 10 * http://www.apache.org/licenses/LICENSE-2.0 * 11 * * 12 * Unless required by applicable law or agreed to in writing, software * 13 * distributed under the License is distributed on an 'AS IS' BASIS, * 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * 15 * See the License for the specific language governing permissions and * 16 * limitations under the License. * 17 * * 18 *---------------------------------------------------------------------------*/ 19 20/************************************************************************ 21 * CA_Wave Methods 22 ************************************************************************/ 23 24#ifndef _RTT 25#include <stdio.h> 26#endif 27#include <stdlib.h> 28#include <string.h> 29#include <limits.h> 30 31#ifdef unix 32#include <unistd.h> 33#endif 34#include <assert.h> 35 36 37#include "frontapi.h" 38#include "portable.h" 39 40/* CA_Wave functions. See simpars.c for frontend params */ 41 42CA_Wave *CA_AllocateWave(char type) 43{ 44 CA_Wave *hWave = NULL; 45 TRY_CA_EXCEPT 46 hWave = (CA_Wave *) CALLOC_CLR(1, sizeof(CA_Wave), "cfront.hWave"); 47#ifndef _RTT 48 hWave->data.device.file.typ = type; 49#endif 50 hWave->data.channel = create_channel_object(); 51 hWave->is_configured = False; 52 hWave->is_configuredForVoicing = False; 53 hWave->ca_rtti = CA_WAVE_SIGNATURE; 54 return (hWave); 55 56 BEG_CATCH_CA_EXCEPT; 57 END_CATCH_CA_EXCEPT(hWave); 58} 59 60void CA_ConfigureWave(CA_Wave *hWave, CA_Frontend *hFrontend) 61{ 62 TRY_CA_EXCEPT 63 ASSERT(hWave); 64 ASSERT(hFrontend); 65 ASSERT(FRAMERATE > 0); 66 67 if (hFrontend->is_configured == False) 68 SERVICE_ERROR(UNCONFIGURED_FRONTEND); 69 if (hWave->is_configured == True) 70 SERVICE_ERROR(CONFIGURED_WAVE); 71 72 ASSERT(hFrontend->config->waveobj->samplerate); 73 74 hWave->data.scale = hFrontend->src_scale; 75 hWave->data.offset = hFrontend->offset; 76 setup_channel_object(hWave->data.channel, hFrontend->config->waveobj, 77 hFrontend->config->freqobj, 78 hFrontend->config->cepobj); 79 80 hWave->data.samplerate = hFrontend->config->waveobj->samplerate; 81 82 /* Buffer size is set to one frame's worth of data */ 83 create_sample_buffer(&hWave->data, 84 hFrontend->config->waveobj->samplerate / FRAMERATE, 85 hFrontend->config->freqobj->window_length); 86 87 hWave->data.stats.highclip_level = hFrontend->config->waveobj->high_clip; 88 hWave->data.stats.lowclip_level = hFrontend->config->waveobj->low_clip; 89 hWave->data.stats.max_per10000_clip = 90 hFrontend->config->waveobj->max_per10000_clip; 91 hWave->data.stats.max_dc_offset = 92 hFrontend->config->waveobj->max_dc_offset; 93 hWave->data.stats.high_noise_level_bit = 94 hFrontend->config->waveobj->high_noise_level_bit; 95 hWave->data.stats.low_speech_level_bit = 96 hFrontend->config->waveobj->low_speech_level_bit; 97 hWave->data.stats.min_samples = 98 hFrontend->config->waveobj->min_samples; 99 100 hWave->is_configured = True; 101 return; 102 103 BEG_CATCH_CA_EXCEPT; 104 END_CATCH_CA_EXCEPT(hWave); 105} 106 107void CA_ConfigureVoicingAnalysis(CA_Wave *hWave, CA_FrontendInputParams *hFrontPar) 108{ 109 TRY_CA_EXCEPT 110 111 hWave->voice.margin = hFrontPar->voice_margin; 112 hWave->voice.fast_margin = hFrontPar->fast_voice_margin; 113 hWave->voice.quiet_margin = hFrontPar->tracker_margin; 114 hWave->voice.voice_duration = hFrontPar->voice_duration; 115 hWave->voice.quiet_duration = hFrontPar->quiet_duration; 116 hWave->is_configuredForVoicing = True; 117 return; 118 119 BEG_CATCH_CA_EXCEPT 120 END_CATCH_CA_EXCEPT(hWave) 121} 122 123void CA_UnconfigureWave(CA_Wave *hWave) 124{ 125 TRY_CA_EXCEPT 126 ASSERT(hWave); 127 if (hWave->is_configured == False) 128 SERVICE_ERROR(UNCONFIGURED_WAVE); 129 130 clear_channel_object(hWave->data.channel); 131 free_sample_buffer(&hWave->data); 132 hWave->data.samplerate = 0; 133 134 hWave->is_configured = False; 135 136/* The following is not correct in this place as it does not match where it is set to TRUE. 137 * This is needed for the sample rate change function. 138 * hWave->is_configuredForVoicing = False; 139 */ 140 BEG_CATCH_CA_EXCEPT; 141 END_CATCH_CA_EXCEPT(hWave); 142} 143 144void CA_FreeWave(CA_Wave *hWave) 145{ 146 TRY_CA_EXCEPT 147 ASSERT(hWave); 148 149 if (hWave->is_configured == True) 150 SERVICE_ERROR(CONFIGURED_WAVE); 151 152 delete_channel_object(hWave->data.channel); 153 FREE((char *) hWave); 154 return; 155 BEG_CATCH_CA_EXCEPT; 156 END_CATCH_CA_EXCEPT(hWave); 157} 158 159int CA_OpenWaveFromDevice(CA_Wave *hWave, 160 int wave_type, 161 int samplerate, 162 int device_id, 163 int device_type) 164{ 165 TRY_CA_EXCEPT 166 ASSERT(hWave); 167 ASSERT(device_id >= 0); 168 ASSERT(device_type == WAVE_DEVICE_RAW); 169 170 if (hWave->is_configured == False) 171 SERVICE_ERROR(UNCONFIGURED_WAVE); 172 if (hWave->is_configuredForVoicing == False) 173 SERVICE_ERROR(UNCONFIGURED_WAVE); 174 175 reset_channel_object(hWave->data.channel); 176 hWave->data.wave_type = wave_type; 177 hWave->data.device_type = device_type; 178 hWave->data.device.ext.op = WAVE_DEVICE_INPUT; 179 hWave->data.samplerate = samplerate; 180 init_voicing_analysis(&hWave->voice); 181 182 reset_sig_check(&hWave->data.stats); 183 hWave->data.do_stats = ESR_TRUE; 184 185 return (True); 186 BEG_CATCH_CA_EXCEPT; 187 END_CATCH_CA_EXCEPT(hWave); 188} 189 190 191ESR_BOOL CA_DoSignalCheck(CA_Wave *hWave, 192 ESR_BOOL *clipping, 193 ESR_BOOL *dcoffset, 194 ESR_BOOL *highnoise, 195 ESR_BOOL *quietspeech, 196 ESR_BOOL *too_few_samples, 197 ESR_BOOL *too_many_samples) 198{ 199 TRY_CA_EXCEPT 200 201 int nsam; 202 int pclowclip; 203 int pchighclip; 204 int dc_offset; 205 int amp; 206 int pc5; 207 int pc95; 208 int overflow; 209 ESR_BOOL error; 210 wave_stats *ws; 211 212 ASSERT(hWave); 213 214 ws = &hWave->data.stats; 215 get_sig_check(ws, &nsam, &pclowclip, &pchighclip, &dc_offset, &, 216 &pc5, &pc95, &overflow); 217 218 if ((pclowclip + pchighclip) > ws->max_per10000_clip) 219 *clipping = ESR_TRUE; 220 else *clipping = ESR_FALSE; 221 if (abs(dc_offset) > ws->max_dc_offset) *dcoffset = ESR_TRUE; 222 else *dcoffset = ESR_FALSE; 223 if (pc5 >= ws->high_noise_level_bit) *highnoise = ESR_TRUE; 224 else *highnoise = ESR_FALSE; 225 if (pc95 < ws->low_speech_level_bit) *quietspeech = ESR_TRUE; 226 else *quietspeech = ESR_FALSE; 227 if (nsam < ws->min_samples) *too_few_samples = ESR_TRUE; 228 else *too_few_samples = ESR_FALSE; 229 if (overflow) *too_many_samples = ESR_TRUE; 230 else *too_many_samples = ESR_FALSE; 231 232 /* This is better than casting the logical expression to ESR_BOOL */ 233 if (*clipping || *dcoffset || *highnoise || *quietspeech || *too_few_samples || *too_many_samples) 234 error = ESR_TRUE; 235 else 236 error = ESR_FALSE; 237 238 return(error); 239 240 BEG_CATCH_CA_EXCEPT 241 END_CATCH_CA_EXCEPT(hWave) 242} 243 244void CA_CloseDevice(CA_Wave *hWave) 245{ 246 TRY_CA_EXCEPT 247 if (hWave->is_configured == False) 248 SERVICE_ERROR(UNCONFIGURED_WAVE); 249 250 ASSERT(hWave->data.device.ext.op == WAVE_DEVICE_INPUT); /* because I don't have output yet! */ 251 252 return; 253 BEG_CATCH_CA_EXCEPT; 254 END_CATCH_CA_EXCEPT(hWave); 255} 256 257 258int CA_LoadSamples(CA_Wave *hWave, 259 samdata *pPCMData, 260 int sampleCount) 261{ 262 ASSERT(hWave); 263 ASSERT(pPCMData); 264 265 TRY_CA_EXCEPT 266 if (hWave->is_configured == False) 267 SERVICE_ERROR(UNCONFIGURED_WAVE); 268 if (hWave->data.device_type != WAVE_DEVICE_RAW) 269 SERVICE_ERROR(BAD_WAV_DEVICE); 270 if (hWave->data.window_size < sampleCount) 271 SERVICE_ERROR(INCORRECT_SAMPLERATE); 272 273 memcpy(hWave->data.income, 274 pPCMData, 275 sampleCount * sizeof(samdata)); 276 277 hWave->data.num_samples = sampleCount; 278 279 if (hWave->data.do_stats) 280 acc_wave_stats(&hWave->data); 281 282 return (True); 283 BEG_CATCH_CA_EXCEPT; 284 END_CATCH_CA_EXCEPT(hWave); 285} 286 287void CA_ConditionSamples(CA_Wave *hWave) 288{ 289 TRY_CA_EXCEPT 290 int ii; 291 292 if (hWave->is_configured == False) 293 SERVICE_ERROR(UNCONFIGURED_WAVE); 294 295 if (hWave->data.offset != 0) 296 for (ii = 0; ii < hWave->data.num_samples; ii++) 297 hWave->data.income[ii] = RANGE(hWave->data.income[ii] + 298 hWave->data.offset, SHRT_MIN, SHRT_MAX); 299 if (hWave->data.scale != 1.0) 300 for (ii = 0; ii < hWave->data.num_samples; ii++) 301 hWave->data.income[ii] = (short) RANGE(hWave->data.income[ii] * 302 hWave->data.scale, SHRT_MIN, SHRT_MAX); 303 return; 304 BEG_CATCH_CA_EXCEPT; 305 END_CATCH_CA_EXCEPT(hWave); 306} 307