diff --git a/src/espeak-ng.c b/src/espeak-ng.c index c507e95b..f48a6b07 100644 --- a/src/espeak-ng.c +++ b/src/espeak-ng.c @@ -588,9 +588,11 @@ int main(int argc, char **argv) } espeak_ng_InitializePath(data_path); - espeak_ng_STATUS result = espeak_ng_Initialize(); + espeak_ng_ERROR_CONTEXT context = NULL; + espeak_ng_STATUS result = espeak_ng_Initialize(&context); if (result != ENS_OK) { espeak_ng_PrintStatusCodeMessage(result, stderr); + espeak_ng_ClearErrorContext(&context); exit(1); } diff --git a/src/include/espeak-ng/espeak_ng.h b/src/include/espeak-ng/espeak_ng.h index 2966cf36..48289057 100644 --- a/src/include/espeak-ng/espeak_ng.h +++ b/src/include/espeak-ng/espeak_ng.h @@ -75,7 +75,7 @@ ESPEAK_NG_API void espeak_ng_InitializePath(const char *path); ESPEAK_NG_API espeak_ng_STATUS -espeak_ng_Initialize(void); +espeak_ng_Initialize(espeak_ng_ERROR_CONTEXT *context); ESPEAK_NG_API espeak_ng_STATUS espeak_ng_InitializeOutput(espeak_ng_OUTPUT_MODE output_mode, diff --git a/src/libespeak-ng/compiledata.c b/src/libespeak-ng/compiledata.c index acb1ccf6..828df277 100644 --- a/src/libespeak-ng/compiledata.c +++ b/src/libespeak-ng/compiledata.c @@ -2725,7 +2725,7 @@ static espeak_ng_STATUS CompilePhonemeData2(const char *source, FILE *log) fclose(f_phtab); fclose(f_phcontents); - LoadPhData(NULL); + LoadPhData(NULL, NULL); CompileReport(); @@ -3029,7 +3029,7 @@ espeak_ng_STATUS espeak_ng_CompileIntonation(FILE *log) fprintf(log, "Compiled %d intonation tunes: %d errors.\n", n_tune_names, error_count); - LoadPhData(NULL); + LoadPhData(NULL, NULL); return error_count > 0 ? ENS_COMPILE_ERROR : ENS_OK; } diff --git a/src/libespeak-ng/error.c b/src/libespeak-ng/error.c index 1bfc4e15..124dcf8b 100644 --- a/src/libespeak-ng/error.c +++ b/src/libespeak-ng/error.c @@ -37,21 +37,38 @@ espeak_ng_STATUS create_file_error_context(espeak_ng_ERROR_CONTEXT *context, esp { if (context) { if (*context) { - free((*context)->filename); + free((*context)->path); } else { *context = malloc(sizeof(espeak_ng_ERROR_CONTEXT_)); } - (*context)->filename = strdup(filename); + (*context)->path = strdup(filename); + (*context)->version = 0; + (*context)->expected_version = 0; } return status; } +espeak_ng_STATUS create_version_mismatch_error_context(espeak_ng_ERROR_CONTEXT *context, const char *path_home, int version, int expected_version) +{ + if (context) { + if (*context) { + free((*context)->path); + } else { + *context = malloc(sizeof(espeak_ng_ERROR_CONTEXT_)); + } + (*context)->path = strdup(path_home); + (*context)->version = version; + (*context)->expected_version = expected_version; + } + return ENS_VERSION_MISMATCH; +} + #pragma GCC visibility push(default) ESPEAK_NG_API void espeak_ng_ClearErrorContext(espeak_ng_ERROR_CONTEXT *context) { if (context && *context) { - free((*context)->filename); + free((*context)->path); free(*context); *context = NULL; } diff --git a/src/libespeak-ng/error.h b/src/libespeak-ng/error.h index f5683d04..08e4ad1f 100644 --- a/src/libespeak-ng/error.h +++ b/src/libespeak-ng/error.h @@ -25,7 +25,9 @@ extern "C" typedef struct espeak_ng_ERROR_CONTEXT_ { - char *filename; + char *path; + int version; + int expected_version; } espeak_ng_ERROR_CONTEXT_; espeak_ng_STATUS @@ -33,6 +35,12 @@ create_file_error_context(espeak_ng_ERROR_CONTEXT *context, espeak_ng_STATUS status, const char *filename); +espeak_ng_STATUS +create_version_mismatch_error_context(espeak_ng_ERROR_CONTEXT *context, + const char *path, + int version, + int expected_version); + #ifdef __cplusplus } #endif diff --git a/src/libespeak-ng/espeak_api.c b/src/libespeak-ng/espeak_api.c index b913be5c..d6fe7fd2 100644 --- a/src/libespeak-ng/espeak_api.c +++ b/src/libespeak-ng/espeak_api.c @@ -53,9 +53,11 @@ static espeak_ERROR status_to_espeak_error(espeak_ng_STATUS status) ESPEAK_API int espeak_Initialize(espeak_AUDIO_OUTPUT output_type, int buf_length, const char *path, int options) { espeak_ng_InitializePath(path); - espeak_ng_STATUS result = espeak_ng_Initialize(); + espeak_ng_ERROR_CONTEXT context = NULL; + espeak_ng_STATUS result = espeak_ng_Initialize(&context); if (result != ENS_OK) { espeak_ng_PrintStatusCodeMessage(result, stderr); + espeak_ng_ClearErrorContext(&context); if ((options & espeakINITIALIZE_DONT_EXIT) == 0) exit(1); } diff --git a/src/libespeak-ng/speech.c b/src/libespeak-ng/speech.c index 1d5ddaf9..e23544c0 100644 --- a/src/libespeak-ng/speech.c +++ b/src/libespeak-ng/speech.c @@ -313,7 +313,7 @@ ESPEAK_NG_API void espeak_ng_InitializePath(const char *path) #endif } -ESPEAK_NG_API espeak_ng_STATUS espeak_ng_Initialize(void) +ESPEAK_NG_API espeak_ng_STATUS espeak_ng_Initialize(espeak_ng_ERROR_CONTEXT *context) { int param; int srate = 22050; // default sample rate 22050 Hz @@ -328,7 +328,7 @@ ESPEAK_NG_API espeak_ng_STATUS espeak_ng_Initialize(void) } } - espeak_ng_STATUS result = LoadPhData(&srate); + espeak_ng_STATUS result = LoadPhData(&srate, context); if (result != ENS_OK) return result; diff --git a/src/libespeak-ng/synthdata.c b/src/libespeak-ng/synthdata.c index e7bb9502..1ab8943f 100644 --- a/src/libespeak-ng/synthdata.c +++ b/src/libespeak-ng/synthdata.c @@ -33,6 +33,7 @@ #include "espeak_ng.h" #include "speak_lib.h" +#include "error.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" @@ -72,7 +73,7 @@ int vowel_transition1; int FormantTransition2(frameref_t *seq, int *n_frames, unsigned int data1, unsigned int data2, PHONEME_TAB *other_ph, int which); -static espeak_ng_STATUS ReadPhFile(void **ptr, const char *fname, int *size) +static espeak_ng_STATUS ReadPhFile(void **ptr, const char *fname, int *size, espeak_ng_ERROR_CONTEXT *context) { if (!ptr) return EINVAL; @@ -83,10 +84,8 @@ static espeak_ng_STATUS ReadPhFile(void **ptr, const char *fname, int *size) sprintf(buf, "%s%c%s", path_home, PATHSEP, fname); length = GetFileLength(buf); - if ((f_in = fopen(buf, "rb")) == NULL) { - fprintf(stderr, "Can't read data file: '%s'\n", buf); - return errno; - } + if ((f_in = fopen(buf, "rb")) == NULL) + return create_file_error_context(context, errno, buf); if (*ptr != NULL) Free(*ptr); @@ -99,7 +98,7 @@ static espeak_ng_STATUS ReadPhFile(void **ptr, const char *fname, int *size) int error = errno; fclose(f_in); Free(*ptr); - return error; + return create_file_error_context(context, error, buf); } fclose(f_in); @@ -108,7 +107,7 @@ static espeak_ng_STATUS ReadPhFile(void **ptr, const char *fname, int *size) return ENS_OK; } -espeak_ng_STATUS LoadPhData(int *srate) +espeak_ng_STATUS LoadPhData(int *srate, espeak_ng_ERROR_CONTEXT *context) { int ix; int n_phonemes; @@ -119,13 +118,13 @@ espeak_ng_STATUS LoadPhData(int *srate) int *pw; espeak_ng_STATUS status; - if ((status = ReadPhFile((void **)&phoneme_tab_data, "phontab", NULL)) != ENS_OK) + if ((status = ReadPhFile((void **)&phoneme_tab_data, "phontab", NULL, context)) != ENS_OK) return status; - if ((status = ReadPhFile((void **)&phoneme_index, "phonindex", NULL)) != ENS_OK) + if ((status = ReadPhFile((void **)&phoneme_index, "phonindex", NULL, context)) != ENS_OK) return status; - if ((status = ReadPhFile((void **)&phondata_ptr, "phondata", NULL)) != ENS_OK) + if ((status = ReadPhFile((void **)&phondata_ptr, "phondata", NULL, context)) != ENS_OK) return status; - if ((status = ReadPhFile((void **)&tunes, "intonations", &length)) != ENS_OK) + if ((status = ReadPhFile((void **)&tunes, "intonations", &length, context)) != ENS_OK) return status; wavefile_data = (unsigned char *)phondata_ptr; n_tunes = length / sizeof(TUNE); @@ -139,7 +138,7 @@ espeak_ng_STATUS LoadPhData(int *srate) } if (version != version_phdata) - return ENS_VERSION_MISMATCH; + return create_version_mismatch_error_context(context, path_home, version, version_phdata); // set up phoneme tables p = phoneme_tab_data; diff --git a/src/libespeak-ng/synthesize.h b/src/libespeak-ng/synthesize.h index b5c8099f..b5e55100 100644 --- a/src/libespeak-ng/synthesize.h +++ b/src/libespeak-ng/synthesize.h @@ -499,7 +499,7 @@ unsigned int LookupSound(PHONEME_TAB *ph1, PHONEME_TAB *ph2, int which, int *mat frameref_t *LookupSpect(PHONEME_TAB *this_ph, int which, FMT_PARAMS *fmt_params, int *n_frames, PHONEME_LIST *plist); unsigned char *LookupEnvelope(int ix); -espeak_ng_STATUS LoadPhData(int *srate); +espeak_ng_STATUS LoadPhData(int *srate, espeak_ng_ERROR_CONTEXT *context); void SynthesizeInit(void); int Generate(PHONEME_LIST *phoneme_list, int *n_ph, int resume); diff --git a/src/speak-ng.c b/src/speak-ng.c index b66abb8a..f5c9b74c 100644 --- a/src/speak-ng.c +++ b/src/speak-ng.c @@ -575,9 +575,11 @@ int main(int argc, char **argv) } espeak_ng_InitializePath(data_path); - espeak_ng_STATUS result = espeak_ng_Initialize(); + espeak_ng_ERROR_CONTEXT context = NULL; + espeak_ng_STATUS result = espeak_ng_Initialize(&context); if (result != ENS_OK) { espeak_ng_PrintStatusCodeMessage(result, stderr); + espeak_ng_ClearErrorContext(&context); exit(1); }