From ac5eeb865e60dac88187c77dfcb3719ab43707c8 Mon Sep 17 00:00:00 2001 From: Juho Hiltunen Date: Sat, 22 May 2021 11:21:46 +0300 Subject: [PATCH] code cleanup: new function CheckTranslator() When a language or voice file in espeak-ng-data is loaded the keyword "translator" must be set so that other language options can modify the values in struct Translator. CheckTranslator() provides standardized error for all switch cases that modify a value in struct Translator. --- src/libespeak-ng/voices.c | 186 +++++++++++++++++++++----------------- 1 file changed, 101 insertions(+), 85 deletions(-) diff --git a/src/libespeak-ng/voices.c b/src/libespeak-ng/voices.c index 99bef3e4..b198c547 100644 --- a/src/libespeak-ng/voices.c +++ b/src/libespeak-ng/voices.c @@ -471,6 +471,18 @@ static int Read8Numbers(char *data_in, int *data) &data[0], &data[1], &data[2], &data[3], &data[4], &data[5], &data[6], &data[7]); } +static int CheckTranslator(Translator *tr, MNEM_TAB *keyword_tab, int key) +{ + // Return 0 if translator is set. + // Return 1 and print an error message for specified key if not + // used for parsing language options + if (tr) + return 0; + + fprintf(stderr, "Cannot set %s: language not set, or is invalid.\n", LookupMnemName(keyword_tab, key)); + return 1; +} + voice_t *LoadVoice(const char *vname, int control) { // control, bit 0 1= no_default @@ -652,10 +664,10 @@ voice_t *LoadVoice(const char *vname, int control) VoiceFormant(p); break; case V_LOWERCASE_SENTENCE: { - if (translator) - translator->langopts.lowercase_sentence = true; - else - fprintf(stderr, "Cannot set lowercaseSentence: language not set, or is invalid.\n"); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + + translator->langopts.lowercase_sentence = true; break; } @@ -669,96 +681,100 @@ voice_t *LoadVoice(const char *vname, int control) } break; case V_STRESSLENGTH: {// stressLength - if (translator) { - int stress_lengths_set = 0; - int stress_lengths[8]; - stress_lengths_set = Read8Numbers(p, stress_lengths); - for (ix = 0; ix < stress_lengths_set; ix++) { - translator->stress_lengths[ix] = stress_lengths[ix]; - } - } else - fprintf(stderr, "Cannot set stressLength: language not set, or is invalid.\n"); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + + int stress_lengths_set = 0; + int stress_lengths[8]; + stress_lengths_set = Read8Numbers(p, stress_lengths); + + for (ix = 0; ix < stress_lengths_set; ix++) { + translator->stress_lengths[ix] = stress_lengths[ix]; + } break; } case V_STRESSAMP: { // stressAmp - if (translator) { - int stress_amps_set = 0; - int stress_amps[8]; - stress_amps_set = Read8Numbers(p, stress_amps); - for (ix = 0; ix < stress_amps_set; ix++) { - translator->stress_amps[ix] = stress_amps[ix]; - } - } else - fprintf(stderr, "Cannot set stressAmp: language not set, or is invalid.\n"); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + + int stress_amps_set = 0; + int stress_amps[8]; + stress_amps_set = Read8Numbers(p, stress_amps); + for (ix = 0; ix < stress_amps_set; ix++) { + translator->stress_amps[ix] = stress_amps[ix]; + } + break; } case V_STRESSADD: { // stressAdd - if (translator) { - int stress_add_set = 0; - stress_add_set = Read8Numbers(p, stress_add); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; - for (ix = 0; ix < stress_add_set; ix++) { - translator->stress_lengths[ix] += stress_add[ix]; - } - } else - fprintf(stderr, "Cannot set stressAdd: language not set, or is invalid.\n"); + int stress_add_set = 0; + stress_add_set = Read8Numbers(p, stress_add); + + for (ix = 0; ix < stress_add_set; ix++) { + translator->stress_lengths[ix] += stress_add[ix]; + } break; } case V_INTONATION: // intonation sscanf(p, "%d", &option_tone_flags); if ((option_tone_flags & 0xff) != 0) { - if (translator) - translator->langopts.intonation_group = option_tone_flags & 0xff; - else - fprintf(stderr, "Cannot set intonation: language not set, or is invalid.\n"); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + + translator->langopts.intonation_group = option_tone_flags & 0xff; } break; case V_TUNES: - n = sscanf(p, "%s %s %s %s %s %s", names[0], names[1], names[2], names[3], names[4], names[5]); - if (translator) { - translator->langopts.intonation_group = 0; - for (ix = 0; ix < n; ix++) { - if (strcmp(names[ix], "NULL") == 0) - continue; + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; - if ((value = LookupTune(names[ix])) < 0) - fprintf(stderr, "Unknown tune '%s'\n", names[ix]); - else - translator->langopts.tunes[ix] = value; - } - } else - fprintf(stderr, "Cannot set tunes: language not set, or is invalid.\n"); + n = sscanf(p, "%s %s %s %s %s %s", names[0], names[1], names[2], names[3], names[4], names[5]); + translator->langopts.intonation_group = 0; + + for (ix = 0; ix < n; ix++) { + if (strcmp(names[ix], "NULL") == 0) + continue; + + if ((value = LookupTune(names[ix])) < 0) + fprintf(stderr, "Unknown tune '%s'\n", names[ix]); + else + translator->langopts.tunes[ix] = value; + } break; case V_DICTRULES: // conditional dictionary rules and list entries case V_NUMBERS: case V_STRESSOPT: - if (translator) { - // expect a list of numbers - while (*p != 0) { - while (isspace(*p)) p++; - if ((n = atoi(p)) > 0) { - p++; - if (n < 32) { - if (key == V_DICTRULES) - conditional_rules |= (1 << n); - else if (key == V_NUMBERS) - translator->langopts.numbers |= (1 << n); - else if (key == V_STRESSOPT) - translator->langopts.stress_flags |= (1 << n); - } else { - if ((key == V_NUMBERS) && (n < 64)) - translator->langopts.numbers2 |= (1 << (n-32)); - else - fprintf(stderr, "Bad option number %d\n", n); - } + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + + // expect a list of numbers + while (*p != 0) { + while (isspace(*p)) p++; + if ((n = atoi(p)) > 0) { + p++; + if (n < 32) { + if (key == V_DICTRULES) + conditional_rules |= (1 << n); + else if (key == V_NUMBERS) + translator->langopts.numbers |= (1 << n); + else if (key == V_STRESSOPT) + translator->langopts.stress_flags |= (1 << n); + } else { + if ((key == V_NUMBERS) && (n < 64)) + translator->langopts.numbers2 |= (1 << (n-32)); + else + fprintf(stderr, "Bad option number %d\n", n); } - while (isalnum(*p)) p++; } - ProcessLanguageOptions(&(translator->langopts)); - } else - fprintf(stderr, "Cannot set stressopt: language not set, or is invalid.\n"); + while (isalnum(*p)) p++; + } + ProcessLanguageOptions(&(translator->langopts)); + break; case V_REPLACE: if (phonemes_set == false) { @@ -769,19 +785,20 @@ voice_t *LoadVoice(const char *vname, int control) PhonemeReplacement(p); break; case V_WORDGAP: // words - if (translator) - sscanf(p, "%d %d", &translator->langopts.word_gap, &translator->langopts.vowel_pause); - else - fprintf(stderr, "Cannot set wordgap: language not set, or is invalid.\n"); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + + sscanf(p, "%d %d", &translator->langopts.word_gap, &translator->langopts.vowel_pause); break; case V_STRESSRULE: - if (translator) - sscanf(p, "%d %d %d %d", &translator->langopts.stress_rule, - &translator->langopts.stress_flags, - &translator->langopts.unstressed_wd1, - &translator->langopts.unstressed_wd2); - else - fprintf(stderr, "Cannot set stressrule: language not set, or is invalid.\n"); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + + sscanf(p, "%d %d %d %d", &translator->langopts.stress_rule, + &translator->langopts.stress_flags, + &translator->langopts.unstressed_wd1, + &translator->langopts.unstressed_wd2); + break; case V_ECHO: // echo. suggest: 135mS 11% @@ -863,10 +880,9 @@ voice_t *LoadVoice(const char *vname, int control) break; default: if ((key & 0xff00) == 0x100) { - if (translator) - sscanf(p, "%d", &translator->langopts.param[key &0xff]); - else - fprintf(stderr, "Cannot set voice attribute: language not set, or is invalid.\n"); + if (CheckTranslator(translator, keyword_tab, key) != 0) + break; + sscanf(p, "%d", &translator->langopts.param[key &0xff]); } else fprintf(stderr, "Bad voice attribute: %s\n", buf); break;