1 /*---------------------------------------------------------------------------*
2 * SessionTypeImpl.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 #include "ESR_SessionType.h"
22 #include "ESR_SessionTypeImpl.h"
23 #include "HashMap.h"
24 #include "IntArrayList.h"
25 #include "LCHAR.h"
26 #include "lstring.h"
27 #include "passert.h"
28 #include "pendian.h"
29 #include "PFile.h"
30 #include "PFileSystem.h"
31 #include "plog.h"
32 #include "pmemory.h"
33 #include "pstdio.h"
34 #include "string.h"
35 #include "ESR_SessionTypeListener.h"
36
37 #define MTAG NULL
38
ESR_SessionTypeCreate(ESR_SessionType ** self)39 ESR_ReturnCode ESR_SessionTypeCreate(ESR_SessionType** self)
40 {
41 ESR_SessionType* Interface;
42 ESR_SessionTypeData* data;
43 ESR_ReturnCode rc;
44
45 if (self == NULL)
46 {
47 PLogError(L("ESR_OUT_OF_MEMORY"));
48 return ESR_OUT_OF_MEMORY;
49 }
50 Interface = NEW(ESR_SessionType, MTAG);
51 if (Interface == NULL)
52 {
53 PLogError(L("ESR_OUT_OF_MEMORY"));
54 return ESR_OUT_OF_MEMORY;
55 }
56 data = NEW(ESR_SessionTypeData, MTAG);
57 if (data == NULL)
58 {
59 rc = ESR_OUT_OF_MEMORY;
60 goto CLEANUP;
61 }
62
63
64 Interface->addListener = &ESR_SessionTypeAddListenerImpl;
65 Interface->contains = &ESR_SessionTypeContainsImpl;
66 Interface->convertToBool = &ESR_SessionTypeConvertToBoolImpl;
67 Interface->convertToFloat = &ESR_SessionTypeConvertToFloatImpl;
68 Interface->convertToInt = &ESR_SessionTypeConvertToIntImpl;
69 Interface->convertToUint16_t = &ESR_SessionTypeConvertToUint16_tImpl;
70 Interface->convertToSize_t = &ESR_SessionTypeConvertToSize_tImpl;
71 Interface->destroy = &ESR_SessionTypeDestroyImpl;
72 Interface->getBool = &ESR_SessionTypeGetBoolImpl;
73 Interface->getFloat = &ESR_SessionTypeGetFloatImpl;
74 Interface->getInt = &ESR_SessionTypeGetIntImpl;
75 Interface->getUint16_t = &ESR_SessionTypeGetUint16_tImpl;
76 Interface->getKeyAtIndex = &ESR_SessionTypeGetKeyAtIndexImpl;
77 Interface->getLCHAR = &ESR_SessionTypeGetLCHARImpl;
78 Interface->getProperty = &ESR_SessionTypeGetPropertyImpl;
79 Interface->getPropertyType = &ESR_SessionTypeGetPropertyTypeImpl;
80 Interface->getSize = &ESR_SessionTypeGetSizeImpl;
81 Interface->getSize_t = &ESR_SessionTypeGetSize_tImpl;
82 Interface->importCommandLine = &ESR_SessionTypeImportCommandLineImpl;
83 Interface->importParFile = &ESR_SessionTypeImportParFileImpl;
84 Interface->removeProperty = &ESR_SessionTypeRemovePropertyImpl;
85 Interface->removeAndFreeProperty = &ESR_SessionTypeRemoveAndFreePropertyImpl;
86 Interface->setBool = &ESR_SessionTypeSetBoolImpl;
87 Interface->setBoolIfEmpty = &ESR_SessionTypeSetBoolIfEmptyImpl;
88 Interface->setFloat = &ESR_SessionTypeSetFloatImpl;
89 Interface->setFloatIfEmpty = &ESR_SessionTypeSetFloatIfEmptyImpl;
90 Interface->setInt = &ESR_SessionTypeSetIntImpl;
91 Interface->setIntIfEmpty = &ESR_SessionTypeSetIntIfEmptyImpl;
92 Interface->setUint16_t = &ESR_SessionTypeSetUint16_tImpl;
93 Interface->setUint16_tIfEmpty = &ESR_SessionTypeSetUint16_tIfEmptyImpl;
94 Interface->setLCHAR = &ESR_SessionTypeSetLCHARImpl;
95 Interface->setLCHARIfEmpty = &ESR_SessionTypeSetLCHARIfEmptyImpl;
96 Interface->setProperty = &ESR_SessionTypeSetPropertyImpl;
97 Interface->setSize_t = &ESR_SessionTypeSetSize_tImpl;
98 Interface->setSize_tIfEmpty = &ESR_SessionTypeSetSize_tIfEmptyImpl;
99 Interface->removeListener = &ESR_SessionTypeRemoveListenerImpl;
100
101 Interface->data = data;
102 data->value = NULL;
103 data->listeners = NULL;
104
105 CHK(rc, HashMapCreate(&data->value));
106 CHK(rc, ArrayListCreate(&data->listeners));
107 *self = Interface;
108 return ESR_SUCCESS;
109 CLEANUP:
110 Interface->destroy(Interface);
111 return rc;
112 }
113
114 /*
115 * Because there are no functions to set and get int size_t parameters and because most if not
116 * all int parameters should be size_t anyway, I am adding code to allow size_t and int parameters
117 * to be considered equal. Besides, this check is kind of overkill anyway. SteveR
118 */
119
ESR_SessionTypeGetPropertyImpl(ESR_SessionType * self,const LCHAR * name,void ** value,VariableTypes type)120 ESR_ReturnCode ESR_SessionTypeGetPropertyImpl(ESR_SessionType* self,
121 const LCHAR* name, void** value,
122 VariableTypes type)
123 {
124 ESR_SessionTypeData* data = self->data;
125 ESR_SessionPair* pair;
126 ESR_ReturnCode rc;
127
128 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
129 if ( ( pair->type != type) && ( ( ( pair->type != TYPES_INT ) && ( type != TYPES_SIZE_T ) ) ||
130 ( ( type != TYPES_INT ) && ( pair->type != TYPES_SIZE_T ) ) ) )
131 {
132 PLogError(L("ESR_INVALID_RESULT_TYPE: [got=%d, expected=%d]"), type, pair->type);
133 return ESR_INVALID_RESULT_TYPE;
134 }
135 *value = pair->value;
136 return ESR_SUCCESS;
137 CLEANUP:
138 return rc;
139 }
140
ESR_SessionTypeGetIntImpl(ESR_SessionType * self,const LCHAR * name,int * value)141 ESR_ReturnCode ESR_SessionTypeGetIntImpl(ESR_SessionType* self,
142 const LCHAR* name, int* value)
143 {
144 ESR_ReturnCode rc;
145 ESR_SessionTypeData* data;
146 ESR_SessionPair* pair;
147
148 data = self->data;
149 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
150 if ( ( pair->type != TYPES_INT ) && ( pair->type != TYPES_SIZE_T ) )
151 {
152 PLogError(L("ESR_INVALID_RESULT_TYPE: [got=%d, expected=%d]"), TYPES_INT, pair->type);
153 return ESR_INVALID_RESULT_TYPE;
154 }
155 *value = *((int*) pair->value);
156 return ESR_SUCCESS;
157 CLEANUP:
158 return rc;
159 }
160
ESR_SessionTypeGetUint16_tImpl(ESR_SessionType * self,const LCHAR * name,asr_uint16_t * value)161 ESR_ReturnCode ESR_SessionTypeGetUint16_tImpl(ESR_SessionType* self,
162 const LCHAR* name, asr_uint16_t* value)
163 {
164 ESR_ReturnCode rc;
165 ESR_SessionTypeData* data;
166 ESR_SessionPair* pair;
167
168 data = self->data;
169 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
170 if (pair->type != TYPES_UINT16_T)
171 {
172 PLogError(L("ESR_INVALID_RESULT_TYPE: [got=%d, expected=%d]"), TYPES_UINT16_T, pair->type);
173 return ESR_INVALID_RESULT_TYPE;
174 }
175 *value = *((asr_uint16_t*) pair->value);
176 return ESR_SUCCESS;
177 CLEANUP:
178 return rc;
179 }
180
ESR_SessionTypeGetSize_tImpl(ESR_SessionType * self,const LCHAR * name,size_t * value)181 ESR_ReturnCode ESR_SessionTypeGetSize_tImpl(ESR_SessionType* self,
182 const LCHAR* name,
183 size_t* value)
184 {
185 ESR_ReturnCode rc;
186 ESR_SessionTypeData* data;
187 ESR_SessionPair* pair;
188
189 data = self->data;
190 CHKLOG(rc, HashMapGet(data->value, name, (void **)&pair));
191 if ( ( pair->type != TYPES_INT ) && ( pair->type != TYPES_SIZE_T ) )
192 {
193 PLogError(L("ESR_INVALID_RESULT_TYPE: [got=%d, expected=%d]"), TYPES_SIZE_T, pair->type);
194 return ESR_INVALID_RESULT_TYPE;
195 }
196 *value = *((size_t*) pair->value);
197 return ESR_SUCCESS;
198 CLEANUP:
199 return rc;
200 }
201
ESR_SessionTypeGetFloatImpl(ESR_SessionType * self,const LCHAR * name,float * value)202 ESR_ReturnCode ESR_SessionTypeGetFloatImpl(ESR_SessionType* self,
203 const LCHAR* name, float* value)
204 {
205 ESR_ReturnCode rc;
206 ESR_SessionTypeData* data;
207 ESR_SessionPair* pair;
208
209 data = self->data;
210 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
211 if (pair->type != TYPES_FLOAT)
212 {
213 PLogError(L("ESR_INVALID_RESULT_TYPE: [got=%d, expected=%d]"), TYPES_FLOAT, pair->type);
214 return ESR_INVALID_RESULT_TYPE;
215 }
216 *value = *((float*) pair->value);
217 return ESR_SUCCESS;
218 CLEANUP:
219 return rc;
220 }
221
ESR_SessionTypeGetBoolImpl(ESR_SessionType * self,const LCHAR * name,ESR_BOOL * value)222 ESR_ReturnCode ESR_SessionTypeGetBoolImpl(ESR_SessionType* self,
223 const LCHAR* name, ESR_BOOL* value)
224 {
225 ESR_ReturnCode rc;
226 ESR_SessionTypeData* data;
227 ESR_SessionPair* pair;
228
229 data = self->data;
230 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
231 if (pair->type != TYPES_BOOL)
232 {
233 PLogError(L("ESR_INVALID_RESULT_TYPE: [got=%d, expected=%d]"), TYPES_BOOL, pair->type);
234 return ESR_INVALID_RESULT_TYPE;
235 }
236 *value = *((ESR_BOOL*) pair->value);
237 return ESR_SUCCESS;
238 CLEANUP:
239 return rc;
240 }
241
ESR_SessionTypeGetLCHARImpl(ESR_SessionType * self,const LCHAR * name,LCHAR * value,size_t * len)242 ESR_ReturnCode ESR_SessionTypeGetLCHARImpl(ESR_SessionType* self,
243 const LCHAR* name,
244 LCHAR* value, size_t* len)
245 {
246 LCHAR* lValue;
247 ESR_ReturnCode rc;
248 ESR_SessionTypeData* data;
249 ESR_SessionPair* pair;
250
251 if (name == NULL || value == NULL || len == NULL)
252 return ESR_INVALID_ARGUMENT;
253 data = self->data;
254
255 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
256 if (pair->type != TYPES_PLCHAR)
257 {
258 PLogError(L("ESR_INVALID_RESULT_TYPE: [got=%d, expected=%d]"), TYPES_PLCHAR, pair->type);
259 return ESR_INVALID_RESULT_TYPE;
260 }
261 lValue = (LCHAR*) pair->value;
262 if (LSTRLEN(pair->value) + 1 > *len)
263 {
264 *len = LSTRLEN(lValue) + 1;
265 return ESR_BUFFER_OVERFLOW;
266 }
267 LSTRCPY(value, lValue);
268 return ESR_SUCCESS;
269 CLEANUP:
270 return rc;
271 }
272
ESR_SessionTypeContainsImpl(ESR_SessionType * self,const LCHAR * name,ESR_BOOL * exists)273 ESR_ReturnCode ESR_SessionTypeContainsImpl(ESR_SessionType* self,
274 const LCHAR* name, ESR_BOOL* exists)
275 {
276 ESR_SessionTypeData* data = self->data;
277
278 return HashMapContainsKey(data->value, name, exists);
279 }
280
firePropertyChanged(ESR_SessionType * self,const LCHAR * name,const void * oldValue,const void * newValue,enum VariableTypes_t type)281 static ESR_ReturnCode firePropertyChanged(ESR_SessionType* self, const LCHAR* name,
282 const void* oldValue, const void* newValue,
283 enum VariableTypes_t type)
284 {
285 ESR_SessionTypeData* data = self->data;
286 ArrayList* list = data->listeners;
287 size_t size, i;
288 ESR_SessionTypeListenerPair* listener;
289 ESR_ReturnCode rc;
290
291 CHKLOG(rc, list->getSize(list, &size));
292 for (i = 0; i < size; ++i)
293 {
294 CHKLOG(rc, list->get(list, i, (void **)&listener));
295 CHKLOG(rc, listener->listener->propertyChanged(listener->listener, name, oldValue, newValue, type, listener->data));
296 }
297 return ESR_SUCCESS;
298 CLEANUP:
299 return rc;
300 }
301
ESR_SessionTypeSetPropertyImpl(ESR_SessionType * self,const LCHAR * name,void * value,VariableTypes type)302 ESR_ReturnCode ESR_SessionTypeSetPropertyImpl(ESR_SessionType* self,
303 const LCHAR* name, void* value,
304 VariableTypes type)
305 {
306 ESR_SessionTypeData* data = self->data;
307 ESR_SessionPair* pair = NULL;
308 ESR_BOOL exists;
309 ESR_ReturnCode rc;
310
311 CHKLOG(rc, HashMapContainsKey(data->value, name, &exists));
312 if ( exists )
313 {
314 /* We allow change of parameters through the recognizer and we rely on the recognizer to do
315 * all of the needed validation. SteveR
316 */
317 /* Deleting the old entry seems stupid, but it's the only way to prevent a memory leak,
318 * since the old data is not returned when you add the new data. SteveR
319 */
320 CHKLOG ( rc, ESR_SessionTypeRemoveAndFreePropertyImpl ( self, name ) );
321 }
322 pair = NEW(ESR_SessionPair, MTAG);
323 if (pair == NULL)
324 {
325 PLogError(L("ESR_OUT_OF_MEMORY"));
326 return ESR_OUT_OF_MEMORY;
327 }
328 pair->value = value;
329 pair->type = type;
330
331 CHKLOG(rc, firePropertyChanged(self, name, NULL, value, type));
332 CHKLOG(rc, HashMapPut(data->value, name, pair));
333 return ESR_SUCCESS;
334 CLEANUP:
335 /* The cleanup potentially leaks memory which could be cleard up with FREE ( pair->value );
336 * but you can't guarantee that the value was allocated. A leak is better than a crash. SteveR
337 */
338 FREE(pair);
339 return rc;
340 }
341
ESR_SessionTypeSetIntImpl(ESR_SessionType * self,const LCHAR * name,int value)342 ESR_ReturnCode ESR_SessionTypeSetIntImpl(ESR_SessionType* self,
343 const LCHAR* name, int value)
344 {
345 ESR_SessionTypeData* data;
346 int* clone;
347
348 data = self->data;
349 clone = MALLOC(sizeof(int), MTAG);
350 if (clone == NULL)
351 {
352 PLogError(L("ESR_OUT_OF_MEMORY"));
353 return ESR_OUT_OF_MEMORY;
354 }
355
356 *clone = value;
357 return self->setProperty(self, name, clone, TYPES_INT);
358 }
359
ESR_SessionTypeSetUint16_tImpl(ESR_SessionType * self,const LCHAR * name,asr_uint16_t value)360 ESR_ReturnCode ESR_SessionTypeSetUint16_tImpl(ESR_SessionType* self,
361 const LCHAR* name, asr_uint16_t value)
362 {
363 ESR_SessionTypeData* data;
364 asr_uint16_t* clone;
365
366 data = self->data;
367 clone = MALLOC(sizeof(asr_uint16_t), MTAG);
368 if (clone == NULL)
369 {
370 PLogError(L("ESR_OUT_OF_MEMORY"));
371 return ESR_OUT_OF_MEMORY;
372 }
373
374 *clone = value;
375 return self->setProperty(self, name, clone, TYPES_UINT16_T);
376 }
377
ESR_SessionTypeSetSize_tImpl(ESR_SessionType * self,const LCHAR * name,size_t value)378 ESR_ReturnCode ESR_SessionTypeSetSize_tImpl(ESR_SessionType* self,
379 const LCHAR* name, size_t value)
380 {
381 ESR_SessionTypeData* data;
382 int* clone;
383
384 data = self->data;
385 clone = MALLOC(sizeof(size_t), MTAG);
386 if (clone == NULL)
387 {
388 PLogError(L("ESR_OUT_OF_MEMORY"));
389 return ESR_OUT_OF_MEMORY;
390 }
391
392 *clone = value;
393 return self->setProperty(self, name, clone, TYPES_SIZE_T);
394 }
395
ESR_SessionTypeSetFloatImpl(ESR_SessionType * self,const LCHAR * name,float value)396 ESR_ReturnCode ESR_SessionTypeSetFloatImpl(ESR_SessionType* self,
397 const LCHAR* name, float value)
398 {
399 ESR_SessionTypeData* data;
400 float* clone;
401
402 data = self->data;
403 clone = MALLOC(sizeof(float), MTAG);
404 if (clone == NULL)
405 {
406 PLogError(L("ESR_OUT_OF_MEMORY"));
407 return ESR_OUT_OF_MEMORY;
408 }
409
410 *clone = value;
411 return self->setProperty(self, name, clone, TYPES_FLOAT);
412 }
413
ESR_SessionTypeSetBoolImpl(ESR_SessionType * self,const LCHAR * name,ESR_BOOL value)414 ESR_ReturnCode ESR_SessionTypeSetBoolImpl(ESR_SessionType* self,
415 const LCHAR* name, ESR_BOOL value)
416 {
417 ESR_SessionTypeData* data;
418 ESR_BOOL* clone;
419
420 data = self->data;
421 clone = MALLOC(sizeof(ESR_BOOL), MTAG);
422 if (clone == NULL)
423 {
424 PLogError(L("ESR_OUT_OF_MEMORY"));
425 return ESR_OUT_OF_MEMORY;
426 }
427
428 *clone = value;
429 return self->setProperty(self, name, clone, TYPES_BOOL);
430 }
431
ESR_SessionTypeSetLCHARImpl(ESR_SessionType * self,const LCHAR * name,LCHAR * value)432 ESR_ReturnCode ESR_SessionTypeSetLCHARImpl(ESR_SessionType* self,
433 const LCHAR* name, LCHAR* value)
434 {
435 ESR_SessionTypeData* data;
436 LCHAR* clone;
437
438 data = self->data;
439 clone = MALLOC(sizeof(LCHAR) * (LSTRLEN(value) + 1), MTAG);
440 if (clone == NULL)
441 {
442 PLogError(L("ESR_OUT_OF_MEMORY"));
443 return ESR_OUT_OF_MEMORY;
444 }
445
446 LSTRCPY(clone, value);
447 return self->setProperty(self, name, clone, TYPES_PLCHAR);
448 }
449
ESR_SessionTypeSetIntIfEmptyImpl(ESR_SessionType * self,const LCHAR * name,int value)450 ESR_ReturnCode ESR_SessionTypeSetIntIfEmptyImpl(ESR_SessionType* self,
451 const LCHAR* name, int value)
452 {
453 ESR_BOOL exists;
454 ESR_ReturnCode rc;
455
456 CHK(rc, self->contains(self, name, &exists));
457 if (exists)
458 return ESR_SUCCESS;
459 return self->setInt(self, name, value);
460 CLEANUP:
461 return rc;
462 }
463
ESR_SessionTypeSetUint16_tIfEmptyImpl(ESR_SessionType * self,const LCHAR * name,asr_uint16_t value)464 ESR_ReturnCode ESR_SessionTypeSetUint16_tIfEmptyImpl(ESR_SessionType* self,
465 const LCHAR* name, asr_uint16_t value)
466 {
467 ESR_BOOL exists;
468 ESR_ReturnCode rc;
469
470 CHK(rc, self->contains(self, name, &exists));
471 if (exists)
472 return ESR_SUCCESS;
473 return self->setInt(self, name, value);
474 CLEANUP:
475 return rc;
476 }
477
ESR_SessionTypeSetSize_tIfEmptyImpl(ESR_SessionType * self,const LCHAR * name,size_t value)478 ESR_ReturnCode ESR_SessionTypeSetSize_tIfEmptyImpl(ESR_SessionType* self,
479 const LCHAR* name, size_t value)
480 {
481 ESR_BOOL exists;
482 ESR_ReturnCode rc;
483
484 CHK(rc, self->contains(self, name, &exists));
485 if (exists)
486 return ESR_SUCCESS;
487 return self->setSize_t(self, name, value);
488 CLEANUP:
489 return rc;
490 }
491
ESR_SessionTypeSetFloatIfEmptyImpl(ESR_SessionType * self,const LCHAR * name,float value)492 ESR_ReturnCode ESR_SessionTypeSetFloatIfEmptyImpl(ESR_SessionType* self,
493 const LCHAR* name, float value)
494 {
495 ESR_BOOL exists;
496 ESR_ReturnCode rc;
497
498 CHK(rc, self->contains(self, name, &exists));
499 if (exists)
500 return ESR_SUCCESS;
501 return self->setFloat(self, name, value);
502 CLEANUP:
503 return rc;
504 }
505
ESR_SessionTypeSetBoolIfEmptyImpl(ESR_SessionType * self,const LCHAR * name,ESR_BOOL value)506 ESR_ReturnCode ESR_SessionTypeSetBoolIfEmptyImpl(ESR_SessionType* self,
507 const LCHAR* name, ESR_BOOL value)
508 {
509 ESR_BOOL exists;
510 ESR_ReturnCode rc;
511
512 CHK(rc, self->contains(self, name, &exists));
513 if (exists)
514 return ESR_SUCCESS;
515 return self->setBool(self, name, value);
516 CLEANUP:
517 return rc;
518 }
519
ESR_SessionTypeSetLCHARIfEmptyImpl(ESR_SessionType * self,const LCHAR * name,LCHAR * value)520 ESR_ReturnCode ESR_SessionTypeSetLCHARIfEmptyImpl(ESR_SessionType* self,
521 const LCHAR* name, LCHAR* value)
522 {
523 ESR_BOOL exists;
524 ESR_ReturnCode rc;
525
526 CHK(rc, self->contains(self, name, &exists));
527 if (exists)
528 return ESR_SUCCESS;
529 return self->setLCHAR(self, name, value);
530 CLEANUP:
531 return rc;
532 }
533
ESR_SessionTypeRemovePropertyImpl(ESR_SessionType * self,const LCHAR * name)534 ESR_ReturnCode ESR_SessionTypeRemovePropertyImpl(ESR_SessionType* self,
535 const LCHAR* name)
536 {
537 ESR_ReturnCode rc;
538 ESR_SessionTypeData* data = self->data;
539 ESR_SessionPair* pair;
540
541 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
542 CHKLOG(rc, firePropertyChanged(self, name, pair->value, NULL, pair->type));
543 CHK(rc, HashMapRemove(data->value, name));
544 FREE(pair);
545 return ESR_SUCCESS;
546 CLEANUP:
547 return rc;
548 }
549
ESR_SessionTypeRemoveAndFreePropertyImpl(ESR_SessionType * self,const LCHAR * name)550 ESR_ReturnCode ESR_SessionTypeRemoveAndFreePropertyImpl(ESR_SessionType* self,
551 const LCHAR* name)
552 {
553 ESR_ReturnCode rc;
554 ESR_SessionTypeData* data = self->data;
555 ESR_SessionPair* pair;
556 ESR_SessionPair temp;
557 IntArrayList* intList;
558
559 CHK(rc, data->value->get(data->value, name, (void **)&pair));
560 temp = *pair;
561 CHK(rc, self->removeProperty(self, name));
562 if (temp.value)
563 {
564 if (temp.type == TYPES_INTARRAYLIST)
565 {
566 intList = temp.value;
567 intList->destroy(intList);
568 }
569 else
570 FREE(temp.value);
571 }
572 return ESR_SUCCESS;
573 CLEANUP:
574 return rc;
575 }
576
ESR_SessionTypeImportCommandLineImpl(ESR_SessionType * self,int argc,LCHAR * argv[])577 ESR_ReturnCode ESR_SessionTypeImportCommandLineImpl(ESR_SessionType* self,
578 int argc, LCHAR* argv[])
579 {
580 char* key = NULL;
581 char* value = NULL;
582 VariableTypes type;
583 ESR_ReturnCode rc;
584
585 while (--argc > 0 && **++argv)
586 {
587 if (**argv != '-')
588 {
589 /* got value */
590 if (key == NULL)
591 {
592 /* but we don't have any key to associate it with */
593 pfprintf(PSTDERR, "Options must be prefixed by '-'%s\n", *argv);
594 }
595 else
596 {
597 rc = self->getPropertyType(self, key, &type);
598 if (rc == ESR_SUCCESS)
599 {
600 CHKLOG(rc, self->getProperty(self, key, (void **)&value, type));
601 CHKLOG(rc, self->removeProperty(self, key));
602 FREE(value);
603 value = NULL;
604 }
605 else if (rc != ESR_NO_MATCH_ERROR)
606 {
607 PLogError(ESR_rc2str(rc));
608 goto CLEANUP;
609 }
610 value = MALLOC(sizeof(LCHAR) * (strlen(*argv) + 1), MTAG);
611 if (value == NULL)
612 {
613 rc = ESR_OUT_OF_MEMORY;
614 PLogError(L("ESR_OUT_OF_MEMORY"));
615 goto CLEANUP;
616 }
617 LSTRCPY(value, *argv);
618 CHKLOG(rc, self->setProperty(self, key, value, TYPES_PLCHAR));
619 FREE(key);
620 key = NULL;
621 value = NULL;
622 }
623 }
624 else
625 {
626 /* got key */
627 if (key != NULL)
628 {
629 /* But we already have a key without a value, so set the old key's value to "" */
630 rc = self->getPropertyType(self, key, &type);
631 if (rc == ESR_SUCCESS)
632 {
633 CHKLOG(rc, self->getProperty(self, key, (void **)&value, type));
634 CHKLOG(rc, self->removeProperty(self, key));
635 FREE(value);
636 value = NULL;
637 }
638 else if (rc != ESR_NO_MATCH_ERROR)
639 {
640 PLogError(ESR_rc2str(rc));
641 goto CLEANUP;
642 }
643 value = MALLOC(sizeof(LCHAR) + 1, MTAG);
644 strcpy(value, "");
645 CHKLOG(rc, self->setProperty(self, key, value, TYPES_PLCHAR));
646 FREE(key);
647 value = NULL;
648 }
649 key = MALLOC(sizeof(LCHAR) * (LSTRLEN("cmdline.") + LSTRLEN(*argv) + 1), MTAG);
650 if (key == NULL)
651 {
652 rc = ESR_OUT_OF_MEMORY;
653 PLogError(L("ESR_OUT_OF_MEMORY"));
654 goto CLEANUP;
655 }
656 LSTRCPY(key, "cmdline.");
657 LSTRCAT(key, *argv + 1);
658 }
659 }
660 return ESR_SUCCESS;
661 CLEANUP:
662 if (key != NULL)
663 FREE(key);
664 if (value != NULL)
665 FREE(value);
666 return rc;
667 }
668
ESR_SessionTypeGetSizeImpl(ESR_SessionType * self,size_t * size)669 ESR_ReturnCode ESR_SessionTypeGetSizeImpl(ESR_SessionType* self, size_t* size)
670 {
671 ESR_SessionTypeData* data = self->data;
672 ESR_ReturnCode rc;
673
674 CHK(rc, HashMapGetSize(data->value, size));
675 return ESR_SUCCESS;
676 CLEANUP:
677 return rc;
678 }
679
ESR_SessionTypeGetKeyAtIndexImpl(ESR_SessionType * self,size_t index,LCHAR ** key)680 ESR_ReturnCode ESR_SessionTypeGetKeyAtIndexImpl(ESR_SessionType* self,
681 size_t index, LCHAR** key)
682 {
683 ESR_SessionTypeData* data = self->data;
684 ESR_ReturnCode rc;
685
686 CHK(rc, HashMapGetKeyAtIndex(data->value, index, key));
687 return ESR_SUCCESS;
688 CLEANUP:
689 return rc;
690 }
691
ESR_SessionTypeConvertToIntImpl(ESR_SessionType * self,const LCHAR * key)692 ESR_ReturnCode ESR_SessionTypeConvertToIntImpl(ESR_SessionType* self,
693 const LCHAR* key)
694 {
695 LCHAR* value;
696 int *newValue = NULL;
697 ESR_ReturnCode rc;
698
699 CHK(rc, self->getProperty(self, key, (void **)&value, TYPES_PLCHAR));
700 if (value == NULL)
701 return ESR_SUCCESS;
702 newValue = MALLOC(sizeof(long), MTAG);
703 if (newValue == NULL)
704 {
705 rc = ESR_OUT_OF_MEMORY;
706 goto CLEANUP;
707 }
708 CHKLOG(rc, lstrtoi(value, newValue, 10));
709 CHKLOG(rc, self->setProperty(self, key, newValue, TYPES_INT));
710 FREE(value);
711 return ESR_SUCCESS;
712 CLEANUP:
713 if (newValue != NULL)
714 FREE(newValue);
715 return rc;
716 }
717
ESR_SessionTypeConvertToUint16_tImpl(ESR_SessionType * self,const LCHAR * key)718 ESR_ReturnCode ESR_SessionTypeConvertToUint16_tImpl(ESR_SessionType* self,
719 const LCHAR* key)
720 {
721 LCHAR* value;
722 int *newValue = NULL;
723 ESR_ReturnCode rc;
724
725 CHK(rc, self->getProperty(self, key, (void **)&value, TYPES_PLCHAR));
726 if (value == NULL)
727 return ESR_SUCCESS;
728 newValue = MALLOC(sizeof(long), MTAG);
729 if (newValue == NULL)
730 {
731 rc = ESR_OUT_OF_MEMORY;
732 goto CLEANUP;
733 }
734 CHKLOG(rc, lstrtoi(value, newValue, 10));
735 CHKLOG(rc, self->setProperty(self, key, newValue, TYPES_UINT16_T));
736 FREE(value);
737 return ESR_SUCCESS;
738 CLEANUP:
739 if (newValue != NULL)
740 FREE(newValue);
741 return rc;
742 }
743
ESR_SessionTypeConvertToSize_tImpl(ESR_SessionType * self,const LCHAR * key)744 ESR_ReturnCode ESR_SessionTypeConvertToSize_tImpl(ESR_SessionType* self,
745 const LCHAR* key)
746 {
747 LCHAR* value;
748 size_t* newValue = NULL;
749 ESR_ReturnCode rc;
750
751 CHK(rc, self->getProperty(self, key, (void **)&value, TYPES_PLCHAR));
752 if (value == NULL)
753 return ESR_SUCCESS;
754 newValue = MALLOC(sizeof(size_t), MTAG);
755 if (newValue == NULL)
756 {
757 rc = ESR_OUT_OF_MEMORY;
758 goto CLEANUP;
759 }
760 CHKLOG(rc, lstrtoui(value, (unsigned int *)newValue, 10));
761 CHKLOG(rc, self->setProperty(self, key, newValue, TYPES_SIZE_T));
762 FREE(value);
763 return ESR_SUCCESS;
764 CLEANUP:
765 if (newValue != NULL)
766 FREE(newValue);
767 return rc;
768 }
769
ESR_SessionTypeConvertToFloatImpl(ESR_SessionType * self,const LCHAR * key)770 ESR_ReturnCode ESR_SessionTypeConvertToFloatImpl(ESR_SessionType* self,
771 const LCHAR* key)
772 {
773 LCHAR* value;
774 float *newValue = NULL;
775 ESR_ReturnCode rc;
776
777 CHK(rc, self->getProperty(self, key, (void **)&value, TYPES_PLCHAR));
778 if (value == NULL)
779 return ESR_SUCCESS;
780 newValue = MALLOC(sizeof(double), MTAG);
781 if (newValue == NULL)
782 {
783 rc = ESR_OUT_OF_MEMORY;
784 goto CLEANUP;
785 }
786 CHKLOG(rc, lstrtof(value, newValue));
787 CHKLOG(rc, self->setProperty(self, key, newValue, TYPES_FLOAT));
788 FREE(value);
789 return ESR_SUCCESS;
790 CLEANUP:
791 if (newValue != NULL)
792 FREE(newValue);
793 return rc;
794 }
795
ESR_SessionTypeConvertToBoolImpl(ESR_SessionType * self,const LCHAR * key)796 ESR_ReturnCode ESR_SessionTypeConvertToBoolImpl(ESR_SessionType* self,
797 const LCHAR* key)
798 {
799 LCHAR* value;
800 ESR_BOOL *newValue = NULL;
801 ESR_ReturnCode rc;
802
803 CHK(rc, self->getProperty(self, key, (void **)&value, TYPES_PLCHAR));
804 if (value == NULL)
805 return ESR_SUCCESS;
806 newValue = MALLOC(sizeof(ESR_BOOL), MTAG);
807 if (newValue == NULL)
808 {
809 rc = ESR_OUT_OF_MEMORY;
810 goto CLEANUP;
811 }
812 rc = lstrtob(value, newValue);
813 if (rc != ESR_SUCCESS)
814 {
815 FREE(newValue);
816 return rc;
817 }
818 rc = self->setProperty(self, key, newValue, TYPES_BOOL);
819 if (rc != ESR_SUCCESS)
820 {
821 FREE(newValue);
822 return rc;
823 }
824 FREE(value);
825 return ESR_SUCCESS;
826 CLEANUP:
827 if (newValue != NULL)
828 FREE(newValue);
829 return rc;
830 }
831
832 /**
833 * Imports file containing [key, value] pairs into session.
834 *
835 * @param self ESR_SessionType handle
836 * @param filename File to read session from
837 * @param addMapping Function used to map keys to their type and add them to the session
838 * @param data Data used by the mapping function
839 */
importKeyValueFile(ESR_SessionType * self,const LCHAR * filename,ESR_ReturnCode (* addMapping)(ESR_SessionType * self,const LCHAR * key,LCHAR * value,void * data),void * data)840 static ESR_ReturnCode importKeyValueFile(ESR_SessionType* self,
841 const LCHAR* filename,
842 ESR_ReturnCode(*addMapping)(ESR_SessionType* self, const LCHAR* key, LCHAR* value, void* data),
843 void* data)
844 {
845 const size_t LINE_SIZE = 512;
846 LCHAR key[512];
847 LCHAR buffer[512];
848 LCHAR* value;
849 LCHAR* ending;
850 LCHAR* line;
851 PFile* file = NULL;
852 ESR_BOOL lineSpan = ESR_FALSE;
853 LString* valueBuffer = NULL;
854 ESR_ReturnCode rc = ESR_SUCCESS;
855
856 if (filename == NULL)
857 return ESR_INVALID_ARGUMENT;
858
859 file = pfopen ( filename, L("r") );
860 /* CHKLOG(rc, PFileSystemCreatePFile(filename, ESR_TRUE, &file));
861 CHKLOG(rc, PFileOpen(file, L("r")));*/
862
863 if (file == NULL)
864 {
865 LCHAR msg[P_PATH_MAX + 30];
866 LCHAR cwd[P_PATH_MAX];
867 size_t len;
868
869 len = P_PATH_MAX;
870 CHKLOG(rc, pf_get_cwd (cwd, &len));
871 psprintf(msg, L("ESR_OPEN_FILE_ERROR(filename=%s, cwd=%s)"), filename, cwd);
872 rc = ESR_OPEN_ERROR;
873 PLogError(msg);
874 goto CLEANUP;
875 }
876
877 rc = LStringCreate(&valueBuffer);
878 if (rc != ESR_SUCCESS)
879 goto CLEANUP;
880
881 line = buffer;
882 while (ESR_TRUE)
883 {
884 line = pfgets(line, LINE_SIZE, file);
885 if (line == NULL)
886 {
887 if (pfeof(file))
888 break;
889 rc = ESR_READ_ERROR;
890 PLogError(ESR_rc2str(rc));
891 goto CLEANUP;
892 }
893 if (LSTRLEN(line) == LINE_SIZE)
894 {
895 PLogError(L("%s: line surpasses %d character limit: '%s'"), filename, line);
896 continue;
897 }
898 lstrtrim(line);
899 if (LSTRLEN(line) == 0 || line[0] == '#')
900 continue;
901
902 if (!lineSpan)
903 {
904 if (rc != ESR_SUCCESS) goto CLEANUP;
905
906 /* locate the key and value pair */
907 ending = LSTRCHR(line, '=');
908 if (ending == NULL)
909 {
910 fprintf(stderr, "Missing equal sign on line '%s'\n", line);
911 continue;
912 }
913 *ending = L('\0');
914 value = ending + 1;
915 }
916 else
917 value = line;
918
919 /* Optionally use ';' to denote end of value */
920 ending = LSTRCHR(value, L(';'));
921 if (ending != NULL)
922 *ending = L('\0');
923 else
924 {
925 ending = LSTRCHR(value, L('\n'));
926 if (ending != NULL)
927 *ending = L('\0');
928 }
929 if (!lineSpan)
930 {
931 LSTRCPY(key, line);
932 lstrtrim(key);
933 }
934 if (LSTRLEN(value) == 0)
935 {
936 pfprintf(PSTDERR, L("Missing value for '%s'\n"), key);
937 continue;
938 }
939 lstrtrim(value);
940 if ((ending = LSTRCHR(value, '\\')) == (value + LSTRLEN(value) - 1))
941 {
942 /* found '\\' at end of line which means data will span to the next line */
943 lineSpan = ESR_TRUE;
944 *ending = L('\0');
945 }
946 else
947 lineSpan = ESR_FALSE;
948 rc = LStringAppend(valueBuffer, value);
949 if (rc != ESR_SUCCESS)
950 {
951 PLogError(ESR_rc2str(rc));
952 goto CLEANUP;
953 }
954 if (!lineSpan)
955 {
956 rc = LStringToLCHAR(valueBuffer, &value);
957 valueBuffer = NULL;
958 if (rc != ESR_SUCCESS)
959 {
960 PLogError(ESR_rc2str(rc));
961 goto CLEANUP;
962 }
963 rc = addMapping(self, key, value, data);
964 if (value != NULL)
965 {
966 FREE(value);
967 value = NULL;
968 }
969 if (rc != ESR_SUCCESS)
970 {
971 PLogError(ESR_rc2str(rc));
972 goto CLEANUP;
973 }
974 rc = LStringCreate(&valueBuffer);
975 if (rc != ESR_SUCCESS)
976 {
977 PLogError(ESR_rc2str(rc));
978 goto CLEANUP;
979 }
980 }
981 }
982
983 if (pferror(file))
984 {
985 rc = ESR_READ_ERROR;
986 PLogError(ESR_rc2str(rc));
987 goto CLEANUP;
988 }
989 if (pfclose(file) != 0)
990 {
991 rc = ESR_CLOSE_ERROR;
992 PLogError(ESR_rc2str(rc));
993 goto CLEANUP;
994 }
995 if (valueBuffer != NULL)
996 LStringDestroy(valueBuffer);
997 return ESR_SUCCESS;
998 CLEANUP:
999 if (file != NULL)
1000 pfclose(file);
1001 if (valueBuffer != NULL)
1002 LStringDestroy(valueBuffer);
1003 return rc;
1004 }
1005
1006 /**
1007 * Appends a collection of integers stored in string format to an IntArrayList.
1008 *
1009 * @param self ESR_SessionType handle
1010 * @param text Text containing integers
1011 * @param list List to be populated
1012 */
parseIntList(ESR_SessionType * self,LCHAR * text,IntArrayList * list)1013 static ESR_ReturnCode parseIntList(ESR_SessionType* self,
1014 LCHAR* text, IntArrayList* list)
1015 {
1016 size_t size, pos, beginning;
1017 int value;
1018 ESR_ReturnCode rc;
1019
1020 size = LSTRLEN(text);
1021 pos = 0;
1022 while (ESR_TRUE)
1023 {
1024 /* Scan for beginning of next token */
1025 for (; pos < size && LISSPACE(text[pos]); ++pos);
1026
1027 if (pos >= size)
1028 {
1029 /* Reached end of string while looking for beginning of next token */
1030 break;
1031 }
1032 beginning = pos;
1033
1034 /* Scan for ending of current token */
1035 for (; pos < size && !LISSPACE(text[pos]); ++pos);
1036 text[pos] = L('\0');
1037 CHKLOG(rc, lstrtoi(text + beginning, &value, 10));
1038 CHKLOG(rc, IntArrayListAdd(list, value));
1039 ++pos;
1040 }
1041 return ESR_SUCCESS;
1042 CLEANUP:
1043 return rc;
1044 }
1045
ESR_SessionTypeGetPropertyTypeImpl(ESR_SessionType * self,const LCHAR * name,VariableTypes * type)1046 ESR_ReturnCode ESR_SessionTypeGetPropertyTypeImpl(ESR_SessionType* self,
1047 const LCHAR* name, VariableTypes* type)
1048 {
1049 ESR_SessionTypeData* data = self->data;
1050 ESR_SessionPair* pair;
1051 ESR_ReturnCode rc;
1052
1053 CHK(rc, HashMapGet(data->value, name, (void **)&pair));
1054 *type = pair->type;
1055 return ESR_SUCCESS;
1056 CLEANUP:
1057 return rc;
1058 }
1059
1060 /**
1061 * Maps key -> type for PAR files.
1062 *
1063 * @param self ESR_Session handle
1064 * @param key Key name
1065 * @param value The value
1066 */
addParMapping(ESR_SessionType * self,const LCHAR * key,LCHAR * value,void * data)1067 static ESR_ReturnCode addParMapping(ESR_SessionType* self,
1068 const LCHAR* key, LCHAR* value, void* data)
1069 {
1070 IntArrayList* iList;
1071 ESR_ReturnCode rc;
1072 HashMap* map;
1073 VariableTypes* type;
1074 int iValue;
1075 size_t size_tValue;
1076 float fValue;
1077 ESR_BOOL bValue;
1078 ESR_BOOL exists;
1079
1080 map = (HashMap*) data;
1081 rc = HashMapGet(data, key, (void **)&type);
1082 if (rc == ESR_NO_MATCH_ERROR)
1083 {
1084 /* If type is unknown, assume LCHAR* */
1085 PLogMessage(L("Unknown parfile key '%s'"), key);
1086 CHKLOG(rc, self->setLCHAR(self, key, value));
1087 }
1088 else if (rc == ESR_SUCCESS)
1089 {
1090 switch (*type)
1091 {
1092 case TYPES_INT:
1093 CHKLOG(rc, lstrtoi(value, &iValue, 10));
1094 CHKLOG(rc, self->contains(self, key, &exists));
1095 if (exists)
1096 CHKLOG(rc, self->removeAndFreeProperty(self, key));
1097 CHKLOG(rc, self->setInt(self, key, iValue));
1098 break;
1099 case TYPES_UINT16_T:
1100 CHKLOG(rc, lstrtoui(value, (unsigned int *)&size_tValue, 10));
1101 passert(size_tValue >= UINT16_TMIN && size_tValue <= UINT16_TMAX);
1102 CHKLOG(rc, self->contains(self, key, &exists));
1103 if (exists)
1104 CHKLOG(rc, self->removeAndFreeProperty(self, key));
1105 CHKLOG(rc, self->setUint16_t(self, key, (asr_uint16_t) size_tValue));
1106 break;
1107 case TYPES_SIZE_T:
1108 CHKLOG(rc, lstrtoui(value, (unsigned int *)&size_tValue, 10));
1109 CHKLOG(rc, self->contains(self, key, &exists));
1110 if (exists)
1111 CHKLOG(rc, self->removeAndFreeProperty(self, key));
1112 CHKLOG(rc, self->setSize_t(self, key, size_tValue));
1113 break;
1114 case TYPES_FLOAT:
1115 CHKLOG(rc, lstrtof(value, &fValue));
1116 CHKLOG(rc, self->contains(self, key, &exists));
1117 if (exists)
1118 CHKLOG(rc, self->removeAndFreeProperty(self, key));
1119 CHKLOG(rc, self->setFloat(self, key, fValue));
1120 break;
1121 case TYPES_BOOL:
1122 CHKLOG(rc, lstrtob(value, &bValue));
1123 CHKLOG(rc, self->contains(self, key, &exists));
1124 if (exists)
1125 CHKLOG(rc, self->removeAndFreeProperty(self, key));
1126 CHKLOG(rc, self->setBool(self, key, bValue));
1127 break;
1128 case TYPES_INTARRAYLIST:
1129 CHKLOG(rc, self->contains(self, key, &exists));
1130 if (exists)
1131 {
1132 CHKLOG(rc, self->getProperty(self, key, (void **)&iList, TYPES_INTARRAYLIST));
1133 CHKLOG(rc, self->removeProperty(self, key));
1134 CHKLOG(rc, iList->destroy(iList));
1135 }
1136 CHKLOG(rc, IntArrayListCreate(&iList));
1137 CHKLOG(rc, parseIntList(self, value, iList));
1138 CHKLOG(rc, self->setProperty(self, key, iList, TYPES_INTARRAYLIST));
1139 break;
1140 default:
1141 passert(0); /* Unknown variable type. Assuming LCHAR* */
1142 case TYPES_PLCHAR:
1143 CHKLOG(rc, self->contains(self, key, &exists));
1144 if (exists)
1145 CHKLOG(rc, self->removeAndFreeProperty(self, key));
1146 CHKLOG(rc, self->setLCHAR(self, key, value));
1147 break;
1148 }
1149 }
1150 return rc;
1151 CLEANUP:
1152 return rc;
1153 }
1154
ESR_SessionTypeImportParFileImpl(ESR_SessionType * self,const LCHAR * filename)1155 ESR_ReturnCode ESR_SessionTypeImportParFileImpl(ESR_SessionType* self,
1156 const LCHAR* filename)
1157 {
1158 ESR_ReturnCode rc;
1159 HashMap* parameterList;
1160 VariableTypes Int = TYPES_INT;
1161 VariableTypes UInt16_t = TYPES_UINT16_T;
1162 VariableTypes Float = TYPES_FLOAT;
1163 VariableTypes Bool = TYPES_BOOL;
1164 VariableTypes IntArrayList = TYPES_INTARRAYLIST;
1165 VariableTypes PLChar = TYPES_PLCHAR;
1166 VariableTypes Size_t = TYPES_SIZE_T;
1167
1168 /* Create [key, type] lookup table */
1169 CHKLOG(rc, HashMapCreate(¶meterList));
1170
1171 CHKLOG(rc, parameterList->put(parameterList, "cmdline.arbfile", &PLChar));
1172 CHKLOG(rc, parameterList->put(parameterList, "cmdline.bgsniff", &Size_t));
1173 CHKLOG(rc, parameterList->put(parameterList, "cmdline.channel", &PLChar));
1174 CHKLOG(rc, parameterList->put(parameterList, "cmdline.datapath", &PLChar));
1175 CHKLOG(rc, parameterList->put(parameterList, "cmdline.DataCaptureDirectory", &PLChar));
1176 CHKLOG(rc, parameterList->put(parameterList, "cmdline.detail_res", &PLChar));
1177 CHKLOG(rc, parameterList->put(parameterList, "cmdline.lda", &PLChar));
1178 CHKLOG(rc, parameterList->put(parameterList, "cmdline.modelfiles", &PLChar));
1179 CHKLOG(rc, parameterList->put(parameterList, "cmdline.modelfiles11", &PLChar));
1180 CHKLOG(rc, parameterList->put(parameterList, "cmdline.modelfiles8", &PLChar));
1181 CHKLOG(rc, parameterList->put(parameterList, "cmdline.lda11", &PLChar));
1182 CHKLOG(rc, parameterList->put(parameterList, "cmdline.lda8", &PLChar));
1183 CHKLOG(rc, parameterList->put(parameterList, "cmdline.results", &PLChar));
1184 CHKLOG(rc, parameterList->put(parameterList, "cmdline.rules", &PLChar));
1185 CHKLOG(rc, parameterList->put(parameterList, "cmdline.tcp", &PLChar));
1186 CHKLOG(rc, parameterList->put(parameterList, "cmdline.multable", &PLChar));
1187 CHKLOG(rc, parameterList->put(parameterList, "cmdline.parfile", &PLChar));
1188 CHKLOG(rc, parameterList->put(parameterList, "cmdline.vocabulary", &PLChar));
1189 CHKLOG(rc, parameterList->put(parameterList, "cmdline.use_image", &Int));
1190 CHKLOG(rc, parameterList->put(parameterList, "cmdline.semproc_verbose", &Bool));
1191 CHKLOG(rc, parameterList->put(parameterList, "cmdline.nametagPath", &PLChar));
1192
1193 /* Beginning of speech detection stuff */
1194 CHKLOG(rc, parameterList->put(parameterList, "cmdline.bgsniff_min", &Size_t));
1195 CHKLOG(rc, parameterList->put(parameterList, "cmdline.silence_duration_in_frames", &Size_t));
1196 CHKLOG(rc, parameterList->put(parameterList, "cmdline.end_of_utterance_hold_off_in_frames", &Size_t));
1197 CHKLOG(rc, parameterList->put(parameterList, "cmdline.gatedmode", &Bool));
1198
1199 /* new param from SREC that did not exist in CREC */
1200 CHKLOG(rc, parameterList->put(parameterList, "SREC.Recognizer.utterance_timeout", &Size_t));
1201 CHKLOG(rc, parameterList->put(parameterList, "SREC.Recognizer.osi_log_level", &Size_t));
1202 CHKLOG(rc, parameterList->put(parameterList, "SREC.voice_enroll.bufsz_kB", &Size_t));
1203 CHKLOG(rc, parameterList->put(parameterList, "SREC.voice_enroll.eos_comfort_frames", &Size_t));
1204 CHKLOG(rc, parameterList->put(parameterList, "SREC.voice_enroll.bos_comfort_frames", &Size_t));
1205
1206 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.gdiff.one_nbest", &PLChar));
1207 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.gdiff.many_nbest", &PLChar));
1208 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.sd.one_nbest", &PLChar));
1209 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.sd.many_nbest", &PLChar));
1210 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.sd13.one_nbest", &PLChar));
1211 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.sd13.many_nbest", &PLChar));
1212 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.spf.one_nbest", &PLChar));
1213 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.spf.many_nbest", &PLChar));
1214 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.abs.one_nbest", &PLChar));
1215 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.abs.many_nbest", &PLChar));
1216 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.gdiffpf.one_nbest", &PLChar));
1217 CHKLOG(rc, parameterList->put(parameterList, "SREC.Confidence.sigmoid_param.gdiffpf.many_nbest", &PLChar));
1218
1219 CHKLOG(rc, parameterList->put(parameterList, "CREC.ParVersion", &Float));
1220 CHKLOG(rc, parameterList->put(parameterList, "CREC.useCREClogger", &Int));
1221 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.dimen", &Int));
1222 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.skip", &Int));
1223 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.stay", &Int));
1224 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.durscale", &Int));
1225 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.minvar", &Int));
1226 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.maxvar", &Int));
1227 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.frame_period", &Int));
1228 CHKLOG(rc, parameterList->put(parameterList, "CREC.Acoustic.load_models", &PLChar));
1229 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.mel_dim", &Int));
1230 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.samplerate", &Size_t));
1231 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.premel", &Float));
1232 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.lowcut", &Int));
1233 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.highcut", &Int));
1234 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.window_factor", &Float));
1235 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.offset", &Float));
1236 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.ddmel", &Bool));
1237 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.peakdecayup", &Float));
1238 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.peakdecaydown", &Float));
1239 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.do_skip_even_frames", &Bool));
1240 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.do_smooth_c0", &Bool));
1241 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.melA", &IntArrayList));
1242 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.melB", &IntArrayList));
1243 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.dmelA", &IntArrayList));
1244 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.dmelB", &IntArrayList));
1245 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.ddmelA", &IntArrayList));
1246 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.ddmelB", &IntArrayList));
1247
1248 /* new for S2G 3 (read from parfile instead of hardcoding) */
1249 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.cmn", &IntArrayList));
1250 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.cmn8", &IntArrayList));
1251 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.cmn11", &IntArrayList));
1252 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.tmn", &IntArrayList));
1253 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.adjust", &IntArrayList));
1254 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.debug", &Bool));
1255 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.sbindex", &IntArrayList));
1256 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.forget_factor", &IntArrayList));
1257 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.cache_resolution", &IntArrayList));
1258 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.inutt.forget_factor2", &IntArrayList));
1259 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.inutt.disable_after", &IntArrayList));
1260 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.inutt.enable_after", &IntArrayList));
1261
1262
1263 /* zwz */
1264 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.swicms.do_VN", &Bool));
1265
1266 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.speech_detect", &Int));
1267 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.ambient_within", &Int));
1268 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.speech_above", &Int));
1269 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.start_windback", &Int));
1270 CHKLOG(rc, parameterList->put(parameterList, "CREC.Frontend.utterance_allowance", &Int));
1271
1272
1273 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.dimen", &Int));
1274 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.whole_dimen", &Int));
1275 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.mix_score_scale", &Float));
1276 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.start", &Int));
1277 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.chelt_imelda", &Bool));
1278 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.vfrlimit", &Bool));
1279 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.vfrthresh", &Bool));
1280 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.mix_score_scale", &Float));
1281 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.imelda_scale", &Float));
1282 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.uni_score_scale", &Float));
1283 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.uni_score_offset", &Float));
1284 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.forget_speech", &Int));
1285 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.forget_background", &Int));
1286 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.rel_low", &Int));
1287 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.rel_high", &Int));
1288 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.gap_period", &Int));
1289 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.click_period", &Int));
1290 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.breath_period", &Int));
1291 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.extend_annotation", &Int));
1292 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.min_initial_quiet_frames", &Int));
1293 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.min_annotation_frames", &Int));
1294 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.min_initial_quiet_frames", &Int));
1295 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.max_annotation_frames", &Int));
1296 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.delete_leading_segments", &Int));
1297 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.leading_segment_min_frames", &Int));
1298 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.leading_segment_max_frames", &Int));
1299 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.leading_segment_min_silence_gap_frames", &Int));
1300 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.leading_segment_accept_if_not_found", &Int));
1301 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.snr_holdoff", &Int));
1302 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.min_acceptable_snr", &Int));
1303 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.param", &Int));
1304 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.beep_size", &Int));
1305 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.beep_threshold", &Int));
1306 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.partial_distance_dim", &Int));
1307 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.partial_distance_threshold", &Int));
1308 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.partial_distance_offset", &Int));
1309 CHKLOG(rc, parameterList->put(parameterList, "CREC.Pattern.global_model_means", &IntArrayList));
1310
1311 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.NBest", &Int));
1312 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.reject", &Int));
1313 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.often", &Int));
1314 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.partial_results", &Bool));
1315 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.wordpen", &Int));
1316 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.viterbi_prune_thresh", &Int));
1317 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_hmm_tokens", &Int));
1318 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_fsmnode_tokens", &Int));
1319 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_word_tokens", &Int));
1320 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_altword_tokens", &Int));
1321 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.num_wordends_per_frame", &Int));
1322 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_fsm_nodes", &Int));
1323 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_fsm_arcs", &Int));
1324 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_searches", &Int));
1325 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.terminal_timeout", &Int));
1326 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.optional_terminal_timeout", &Int));
1327 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.non_terminal_timeout", &Int));
1328 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.eou_threshold", &Int));
1329 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_frames", &Int));
1330 CHKLOG(rc, parameterList->put(parameterList, "CREC.Recognizer.max_model_states", &Int));
1331 CHKLOG(rc, parameterList->put(parameterList, "thread.priority", &UInt16_t));
1332 /* for G2P */
1333 CHKLOG(rc, parameterList->put(parameterList, "G2P.Available", &Bool));
1334 CHKLOG(rc, parameterList->put(parameterList, "G2P.Data", &PLChar));
1335 CHKLOG(rc, parameterList->put(parameterList, "G2P.Dictionary", &PLChar));
1336 /* Enable Get Waveform */
1337 CHKLOG(rc, parameterList->put(parameterList, "enableGetWaveform", &Bool));
1338
1339 rc = importKeyValueFile(self, filename, addParMapping, parameterList);
1340 if (rc != ESR_SUCCESS)
1341 goto CLEANUP;
1342 CHKLOG(rc, HashMapDestroy(parameterList));
1343 return ESR_SUCCESS;
1344 CLEANUP:
1345 HashMapDestroy(parameterList);
1346 return rc;
1347 }
1348
ESR_SessionTypeAddListenerImpl(ESR_SessionType * self,ESR_SessionTypeListenerPair * listener)1349 ESR_ReturnCode ESR_SessionTypeAddListenerImpl(ESR_SessionType* self, ESR_SessionTypeListenerPair* listener)
1350 {
1351 ESR_SessionTypeData* data = self->data;
1352 ArrayList* listeners = data->listeners;
1353 ESR_ReturnCode rc;
1354
1355 CHKLOG(rc, listeners->add(listeners, listener));
1356 return ESR_SUCCESS;
1357 CLEANUP:
1358 return rc;
1359 }
1360
ESR_SessionTypeRemoveListenerImpl(ESR_SessionType * self,ESR_SessionTypeListenerPair * listener)1361 ESR_ReturnCode ESR_SessionTypeRemoveListenerImpl(ESR_SessionType* self, ESR_SessionTypeListenerPair* listener)
1362 {
1363 ESR_SessionTypeData* data = self->data;
1364 ArrayList* listeners = data->listeners;
1365 ESR_ReturnCode rc;
1366
1367 CHKLOG(rc, listeners->remove(listeners, listener));
1368 return ESR_SUCCESS;
1369 CLEANUP:
1370 return rc;
1371 }
1372
ESR_SessionTypeDestroyImpl(ESR_SessionType * self)1373 ESR_ReturnCode ESR_SessionTypeDestroyImpl(ESR_SessionType* self)
1374 {
1375 ESR_SessionTypeData* data = self->data;
1376 size_t hashSize;
1377 ESR_SessionPair* pair;
1378 ESR_ReturnCode rc;
1379
1380 if (data != NULL)
1381 {
1382 if (data->value != NULL)
1383 {
1384 CHKLOG(rc, HashMapGetSize(data->value, &hashSize));
1385 while (hashSize > 0)
1386 {
1387 CHKLOG(rc, HashMapGetValueAtIndex(data->value, 0, (void **)&pair));
1388
1389 if (pair->value)
1390 {
1391 if (pair->type == TYPES_INTARRAYLIST)
1392 CHKLOG(rc, IntArrayListDestroy((IntArrayList*) pair->value));
1393 else
1394 FREE(pair->value);
1395 }
1396 CHKLOG(rc, HashMapRemoveAtIndex(data->value, 0));
1397 --hashSize;
1398 FREE(pair);
1399 }
1400
1401 CHKLOG(rc, HashMapDestroy(data->value));
1402 data->value = NULL;
1403 }
1404 if (data->listeners != NULL)
1405 {
1406 CHKLOG(rc, data->listeners->destroy(data->listeners));
1407 data->listeners = NULL;
1408 }
1409 FREE(data);
1410 }
1411
1412 FREE(self);
1413 return ESR_SUCCESS;
1414 CLEANUP:
1415 return rc;
1416 }
1417