Add internal api for file recognition 34/140634/4
authorWonnam Jang <wn.jang@samsung.com>
Tue, 25 Jul 2017 23:59:17 +0000 (08:59 +0900)
committerWonnam Jang <wn.jang@samsung.com>
Thu, 27 Jul 2017 00:26:35 +0000 (09:26 +0900)
Change-Id: Ic51ab61631b9f0023a8005e2c7496309b76d1bb9
Signed-off-by: Wonnam Jang <wn.jang@samsung.com>
15 files changed:
client/stt.c
client/stt_dbus.c
client/stt_dbus.h
client/stt_file_client.c
common/stt_defs.h
include/stt_internal.h
server/sttd_dbus.c
server/sttd_dbus_server.c
server/sttd_dbus_server.h
server/sttd_engine_agent.c
server/sttd_engine_agent.h
server/sttd_recorder.c
server/sttd_recorder.h
server/sttd_server.c [changed mode: 0755->0644]
server/sttd_server.h

index fe24360..f4fe7a6 100644 (file)
@@ -1998,9 +1998,9 @@ static void __stt_notify_state_changed(void *data)
                client->state_changed_cb(client->stt, client->before_state,
                        client->current_state, client->state_changed_user_data);
                stt_client_not_use_callback(client);
-               SLOG(LOG_DEBUG, TAG_STTC, "State changed callback is called");
+               SLOG(LOG_DEBUG, TAG_STTC, "State changed callback is called, State(%d)", client->current_state);
        } else {
-               SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
+               SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null, State(%d)", client->current_state);
        }
 
        return;
@@ -2490,3 +2490,120 @@ int stt_unset_speech_status_cb(stt_h stt)
 
        return 0;
 }
+
+int stt_start_file(stt_h stt, const char* language, const char* type, const char* filepath, stt_audio_type_e audio_type, int sample_rate)
+{
+       stt_client_s* client = NULL;
+       if (0 != __stt_get_feature_enabled()) {
+               return STT_ERROR_NOT_SUPPORTED;
+       }
+       if (0 != __stt_check_privilege()) {
+               return STT_ERROR_PERMISSION_DENIED;
+       }
+       if (0 != __stt_check_handle(stt, &client)) {
+               return STT_ERROR_INVALID_PARAMETER;
+       }
+       if (NULL == filepath) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
+               return STT_ERROR_INVALID_PARAMETER;
+       }
+
+       SLOG(LOG_DEBUG, TAG_STTC, "===== STT START FILE");
+
+       /* check state */
+       if (client->current_state != STT_STATE_READY) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state(%d) is not READY", client->current_state);
+               return STT_ERROR_INVALID_STATE;
+       }
+
+       if (STT_INTERNAL_STATE_NONE != client->internal_state) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Internal state is NOT none : %d", client->internal_state);
+               return STT_ERROR_IN_PROGRESS_TO_RECORDING;
+       }
+
+       int ret = -1;
+       char appid[128] = {0, };
+       ret = aul_app_get_appid_bypid(getpid(), appid, sizeof(appid));
+
+       if ((AUL_R_OK != ret) || (0 == strlen(appid))) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get application ID");
+       } else {
+               SLOG(LOG_DEBUG, TAG_STTC, "[DEBUG] Current app id is %s", appid);
+       }
+
+       char* temp = NULL;
+       if (NULL == language) {
+               temp = strdup("default");
+       } else {
+               temp = strdup(language);
+       }
+
+       if (true == client->credential_needed && NULL == client->credential) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Do not have app credential for this engine(%s)", client->current_engine_id);
+               return STT_ERROR_PERMISSION_DENIED;
+       }
+
+       client->internal_state = STT_INTERNAL_STATE_STARTING;
+       ret = stt_dbus_request_start_file(client->uid, temp, type, client->silence, appid, client->credential, filepath, audio_type, sample_rate);
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to start file : %s", __stt_get_error_code(ret));
+               client->internal_state = STT_INTERNAL_STATE_NONE;
+       } else {
+               SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Start is successful but not done");
+       }
+
+       if (NULL != temp)       free(temp);
+
+       SLOG(LOG_DEBUG, TAG_STTC, "=====");
+       SLOG(LOG_DEBUG, TAG_STTC, " ");
+
+       return ret;
+}
+
+int stt_cancel_file(stt_h stt)
+{
+       stt_client_s* client = NULL;
+       if (0 != __stt_get_feature_enabled()) {
+               return STT_ERROR_NOT_SUPPORTED;
+       }
+       if (0 != __stt_check_privilege()) {
+               return STT_ERROR_PERMISSION_DENIED;
+       }
+       if (0 != __stt_check_handle(stt, &client)) {
+               return STT_ERROR_INVALID_PARAMETER;
+       }
+
+       SLOG(LOG_DEBUG, TAG_STTC, "===== STT CANCEL FILE");
+
+       /* check state */
+       if (STT_STATE_RECORDING != client->current_state && STT_STATE_PROCESSING != client->current_state) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid state : Current state(%d) is 'Ready'", client->current_state);
+               return STT_ERROR_INVALID_STATE;
+       }
+
+       if (STT_INTERNAL_STATE_STARTING == client->internal_state) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Internal state is STARTING : %d", client->internal_state);
+               return STT_ERROR_IN_PROGRESS_TO_RECORDING;
+       } else if (STT_INTERNAL_STATE_STOPPING == client->internal_state) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Internal state is STOPPING : %d", client->internal_state);
+               return STT_ERROR_IN_PROGRESS_TO_PROCESSING;
+       } else if (STT_INTERNAL_STATE_CANCELING == client->internal_state) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Internal state is CANCELING : %d", client->internal_state);
+               return STT_ERROR_IN_PROGRESS_TO_READY;
+       }
+
+       client->internal_state = STT_INTERNAL_STATE_CANCELING;
+       int ret = stt_dbus_request_cancel_file(client->uid);
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to cancel file : %s", __stt_get_error_code(ret));
+               client->internal_state = STT_INTERNAL_STATE_NONE;
+       } else {
+               SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Cancel file is successful but not done");
+       }
+
+       SLOG(LOG_DEBUG, TAG_STTC, "=====");
+       SLOG(LOG_DEBUG, TAG_STTC, " ");
+
+       return ret;
+}
+
index e5da100..f62b0a4 100644 (file)
@@ -2139,3 +2139,118 @@ int stt_dbus_request_cancel(int uid)
        return result;
 #endif
 }
+
+int stt_dbus_request_start_file(int uid, const char* lang, const char* type, int silence, const char* appid, const char* credential, const char* filepath, stt_audio_type_e audio_type, int sample_rate)
+{
+       if (NULL == lang || NULL == type || NULL == appid) {
+               SLOG(LOG_ERROR, TAG_STTC, "Input parameter is NULL");
+               return STT_ERROR_INVALID_PARAMETER;
+       }
+
+       DBusMessage* msg;
+
+       /* create a signal & check for errors */
+       msg = dbus_message_new_method_call(
+               g_server_service_name,
+               g_server_service_object,
+               g_server_service_interface,
+               STT_METHOD_START_FILE);
+
+       if (NULL == msg) {
+               SLOG(LOG_ERROR, TAG_STTC, ">>>> stt start file : Fail to make message");
+               return STT_ERROR_OPERATION_FAILED;
+       } else {
+               SLOG(LOG_DEBUG, TAG_STTC, ">>>> stt start file : uid(%d), language(%s), type(%s), appid(%s), filepath(%s), audio_type(%d), sample_rate(%d)", uid, lang, type, appid, filepath, audio_type, sample_rate);
+       }
+
+       char *temp = NULL;
+       if (NULL == credential) {
+               temp = strdup("NULL");
+       } else {
+               temp = strdup(credential);
+       }
+
+       dbus_message_append_args(msg,
+               DBUS_TYPE_INT32, &uid,
+               DBUS_TYPE_STRING, &lang,
+               DBUS_TYPE_STRING, &type,
+               DBUS_TYPE_INT32, &silence,
+               DBUS_TYPE_STRING, &appid,
+               DBUS_TYPE_STRING, &temp,
+               DBUS_TYPE_STRING, &filepath,
+               DBUS_TYPE_INT32, &audio_type,
+               DBUS_TYPE_INT32, &sample_rate,
+               DBUS_TYPE_INVALID);
+       if (g_conn_sender) {
+               dbus_message_set_no_reply(msg, TRUE);
+
+               if (!dbus_connection_send(g_conn_sender, msg, NULL)) {
+                       SLOG(LOG_ERROR, TAG_STTC, "[Dbus ERROR] <<<< stt start message : Out Of Memory !");
+                       if (NULL != temp) {
+                               free(temp);
+                               temp = NULL;
+                       }
+                       return STT_ERROR_OUT_OF_MEMORY;
+               } else {
+                       dbus_connection_flush(g_conn_sender);
+               }
+
+               dbus_message_unref(msg);
+
+       } else {
+               SLOG(LOG_WARN, TAG_STTC, "[WARN] dbus connection handle is null (%p)", g_conn_sender);
+               if (NULL != temp) {
+                               free(temp);
+                               temp = NULL;
+               }
+               return STT_ERROR_OPERATION_FAILED;
+       }
+
+       if (NULL != temp) {
+                       free(temp);
+                       temp = NULL;
+       }
+       return 0;
+}
+
+int stt_dbus_request_cancel_file(int uid)
+{
+       DBusMessage* msg;
+
+       /* create a signal & check for errors */
+       msg = dbus_message_new_method_call(
+               g_server_service_name,
+               g_server_service_object,
+               g_server_service_interface,
+               STT_METHOD_CANCEL_FILE);
+
+       if (NULL == msg) {
+               SLOG(LOG_ERROR, TAG_STTC, ">>>> stt cancel file : Fail to make message");
+               return STT_ERROR_OPERATION_FAILED;
+       } else {
+               SLOG(LOG_DEBUG, TAG_STTC, ">>>> stt cancel file : uid(%d)", uid);
+       }
+
+       dbus_message_append_args(msg,
+               DBUS_TYPE_INT32, &uid,
+               DBUS_TYPE_INVALID);
+
+       if (g_conn_sender) {
+               dbus_message_set_no_reply(msg, TRUE);
+
+               if (!dbus_connection_send(g_conn_sender, msg, NULL)) {
+                       SLOG(LOG_ERROR, TAG_STTC, "[Dbus ERROR] <<<< stt stop message : Out Of Memory !");
+                       return STT_ERROR_OUT_OF_MEMORY;
+               } else {
+                       dbus_connection_flush(g_conn_sender);
+               }
+
+               dbus_message_unref(msg);
+       } else {
+               SLOG(LOG_WARN, TAG_STTC, "[WARN] dbus connection handle is null (%p)", g_conn_sender);
+               return STT_ERROR_OPERATION_FAILED;
+       }
+
+       return 0;
+}
+
index 4564d41..6c7e059 100644 (file)
@@ -17,6 +17,7 @@
 
 #include "stt.h"
 #include "stt_main.h"
+#include "stt_internal.h"
 
 #ifdef __cplusplus
 extern "C" {
@@ -62,6 +63,9 @@ int stt_dbus_request_stop(int uid);
 
 int stt_dbus_request_cancel(int uid);
 
+int stt_dbus_request_start_file(int uid, const char* lang, const char* type, int silence, const char* appid, const char* credential, const char* filepath, stt_audio_type_e audio_type, int sample_rate);
+
+int stt_dbus_request_cancel_file(int uid);
 
 #ifdef __cplusplus
 }
index 40f722e..a5303e4 100644 (file)
@@ -28,6 +28,10 @@ int stt_file_client_new()
        }
 
        g_client_info = (stt_file_client_s*)calloc(1, sizeof(stt_file_client_s));
+       if (!g_client_info) {
+               SLOG(LOG_ERROR, TAG_STTFC, "[ERROR] Fail to allocate memory");
+               return STT_FILE_ERROR_OUT_OF_MEMORY;
+       }
 
        /* initialize client data */
        g_client_info->recognition_result_cb = NULL;
index 465e22c..2fd8fd6 100644 (file)
@@ -76,6 +76,9 @@ extern "C" {
 #define STTD_METHOD_SET_VOLUME         "sttd_method_set_volume"
 #define STTD_METHOD_SPEECH_STATUS      "sttd_method_speech_status"
 
+#define STT_METHOD_START_FILE          "stt_method_start_file"
+#define STT_METHOD_CANCEL_FILE         "stt_method_cancel_file"
+
 
 /******************************************************************************************
 * Defines for configuration
index 5b0cc70..bebf85b 100644 (file)
@@ -32,6 +32,14 @@ extern "C"
 #define STT_SPEECH_STATUS_BEGINNING_POINT_DETECTED     0
 
 /**
+* @brief Enumerations of audio type.
+*/
+typedef enum {
+       STT_AUDIO_TYPE_RAW_S16 = 0,     /**< Signed 16-bit audio sample */
+       STT_AUDIO_TYPE_RAW_U8,          /**< Unsigned 8-bit audio sample */
+} stt_audio_type_e;
+
+/**
  * @brief Called when user speaking is detected.
  *
  * @param[in] stt The STT handle
@@ -124,6 +132,62 @@ int stt_unset_speech_status_cb(stt_h stt);
  */
 int stt_set_server_stt(stt_h stt, const char* key, char* user_data);
 
+/**
+ * @brief Starts file recognition asynchronously.
+ * @privlevel public
+ * @privilege %http://tizen.org/privilege/recorder
+ * @remarks This function starts sending recorded data from file to engine.
+ * @param[in] stt The STT handle
+ * @param[in] language The language selected from stt_foreach_supported_languages()
+ * @param[in] type The type for recognition (e.g. #STT_RECOGNITION_TYPE_FREE, #STT_RECOGNITION_TYPE_FREE_PARTIAL)
+ * @param[in] filepath PCM filepath for recognition
+ * @param[in] audio_type audio type of file
+ * @param[in] sample_rate sample rate of file
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #STT_ERROR_NONE Successful
+ * @retval #STT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #STT_ERROR_INVALID_STATE Invalid state
+ * @retval #STT_ERROR_OPERATION_FAILED Operation failure
+ * @retval #STT_ERROR_NOT_SUPPORTED STT NOT supported
+ * @retval #STT_ERROR_PERMISSION_DENIED Permission denied
+ * @retval #STT_ERROR_IN_PROGRESS_TO_RECORDING Progress to recording is not finished
+ * @pre The state should be #STT_STATE_READY.
+ * @post It will invoke stt_state_changed_cb(), if you register a callback with stt_state_changed_cb().
+ *       If this function succeeds, the STT state will be #STT_STATE_RECORDING.
+ *       If you call this function again before state changes, you will receive STT_ERROR_IN_PROGRESS_TO_RECORDING.
+ * @see stt_cancel_file()
+ * @see stt_state_changed_cb()
+*/
+int stt_start_file(stt_h stt, const char* language, const char* type, const char* filepath, stt_audio_type_e audio_type, int sample_rate);
+
+/**
+ * @brief Cancels processing file recognition asynchronously.
+ * @privlevel public
+ * @privilege %http://tizen.org/privilege/recorder
+ * @remarks This function cancels recording and engine cancels recognition processing.
+ *         After successful cancel, stt_state_changed_cb() is called otherwise if error is occurred, stt_error_cb() is called.
+ * @param[in] stt The STT handle
+ * @return @c 0 on success,
+ *        otherwise a negative error value
+ * @retval #STT_ERROR_NONE Successful
+ * @retval #STT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #STT_ERROR_INVALID_STATE Invalid state
+ * @retval #STT_ERROR_OPERATION_FAILED Operation failure
+ * @retval #STT_ERROR_NOT_SUPPORTED STT NOT supported
+ * @retval #STT_ERROR_PERMISSION_DENIED Permission denied
+ * @retval #STT_ERROR_IN_PROGRESS_TO_READY Progress to ready is not finished
+ * @retval #STT_ERROR_IN_PROGRESS_TO_RECORDING Progress to recording is not finished
+ * @retval #STT_ERROR_IN_PROGRESS_TO_PROCESSING Progress to processing is not finished
+ * @pre The state should be #STT_STATE_RECORDING or #STT_STATE_PROCESSING.
+ * @post It will invoke stt_state_changed_cb(), if you register a callback with stt_state_changed_cb().
+ *      If this function succeeds, the STT state will be #STT_STATE_READY.
+ *      If you call this function again before state changes, you will receive STT_ERROR_IN_PROGRESS_TO_READY.
+ * @see stt_start_file()
+ * @see stt_state_changed_cb()
+*/
+int stt_cancel_file(stt_h stt);
+
 #ifdef __cplusplus
 }
 #endif
index 0f68473..99a29a2 100644 (file)
@@ -475,6 +475,11 @@ static Eina_Bool listener_event_callback(void* data, Ecore_Fd_Handler *fd_handle
        else if (dbus_message_is_method_call(msg, g_server_service_interface, STT_METHOD_CANCEL))
                sttd_dbus_server_cancel(g_conn_listener, msg);
 
+       else if (dbus_message_is_method_call(msg, g_server_service_interface, STT_METHOD_START_FILE))
+               sttd_dbus_server_start_file(g_conn_listener, msg);
+
+       else if (dbus_message_is_method_call(msg, g_server_service_interface, STT_METHOD_CANCEL_FILE))
+               sttd_dbus_server_cancel_file(g_conn_listener, msg);
 
        /* free the message */
        dbus_message_unref(msg);
@@ -585,18 +590,24 @@ int __sttd_get_buxtonkey()
 
        if (NULL == engine_appid || NULL == engine_default || 0 == strncmp(engine_appid, engine_default, strlen(engine_appid))) {
                g_server_service_name = (char*)calloc(strlen(STT_SERVER_SERVICE_NAME) + 1, sizeof(char));
-               snprintf(g_server_service_name, strlen(STT_SERVER_SERVICE_NAME) + 1, "%s", STT_SERVER_SERVICE_NAME);
+               if (g_server_service_name)
+                       snprintf(g_server_service_name, strlen(STT_SERVER_SERVICE_NAME) + 1, "%s", STT_SERVER_SERVICE_NAME);
                g_server_service_object = (char*)calloc(strlen(STT_SERVER_SERVICE_OBJECT_PATH) + 1, sizeof(char));
-               snprintf(g_server_service_object, strlen(STT_SERVER_SERVICE_OBJECT_PATH) + 1, "%s", STT_SERVER_SERVICE_OBJECT_PATH);
+               if (g_server_service_object)
+                       snprintf(g_server_service_object, strlen(STT_SERVER_SERVICE_OBJECT_PATH) + 1, "%s", STT_SERVER_SERVICE_OBJECT_PATH);
                g_server_service_interface = (char*)calloc(strlen(STT_SERVER_SERVICE_INTERFACE) + 1, sizeof(char));
-               snprintf(g_server_service_interface, strlen(STT_SERVER_SERVICE_INTERFACE) + 1, "%s", STT_SERVER_SERVICE_INTERFACE);
+               if (g_server_service_interface)
+                       snprintf(g_server_service_interface, strlen(STT_SERVER_SERVICE_INTERFACE) + 1, "%s", STT_SERVER_SERVICE_INTERFACE);
        } else {
                g_server_service_name = (char*)calloc(strlen(STT_SERVER_SERVICE_NAME) + strlen(engine_appid) - 8, sizeof(char));
-               snprintf(g_server_service_name, strlen(STT_SERVER_SERVICE_NAME) + strlen(engine_appid) - 8, "%s%s%s", STT_SERVER_SERVICE_NAME, ".", (engine_appid + 10));
+               if (g_server_service_name)
+                       snprintf(g_server_service_name, strlen(STT_SERVER_SERVICE_NAME) + strlen(engine_appid) - 8, "%s%s%s", STT_SERVER_SERVICE_NAME, ".", (engine_appid + 10));
                g_server_service_object = (char*)calloc(strlen(STT_SERVER_SERVICE_OBJECT_PATH) + strlen(engine_appid) - 8, sizeof(char));
-               snprintf(g_server_service_object, strlen(STT_SERVER_SERVICE_OBJECT_PATH) + strlen(engine_appid) - 8, "%s%s%s", STT_SERVER_SERVICE_OBJECT_PATH, "/", (engine_appid + 10));
+               if (g_server_service_object)
+                       snprintf(g_server_service_object, strlen(STT_SERVER_SERVICE_OBJECT_PATH) + strlen(engine_appid) - 8, "%s%s%s", STT_SERVER_SERVICE_OBJECT_PATH, "/", (engine_appid + 10));
                g_server_service_interface = (char*)calloc(strlen(STT_SERVER_SERVICE_INTERFACE) + strlen(engine_appid) - 8, sizeof(char));
-               snprintf(g_server_service_interface, strlen(STT_SERVER_SERVICE_INTERFACE) + strlen(engine_appid) - 8, "%s%s%s", STT_SERVER_SERVICE_INTERFACE, ".", (engine_appid + 10));
+               if (g_server_service_interface)
+                       snprintf(g_server_service_interface, strlen(STT_SERVER_SERVICE_INTERFACE) + strlen(engine_appid) - 8, "%s%s%s", STT_SERVER_SERVICE_INTERFACE, ".", (engine_appid + 10));
        }
 
        if (NULL == g_server_service_name || NULL == g_server_service_object || NULL == g_server_service_interface) {
index 2428cb0..b3ab460 100644 (file)
@@ -1147,3 +1147,93 @@ int sttd_dbus_server_cancel(DBusConnection* conn, DBusMessage* msg)
 
        return 0;
 }
+
+int sttd_dbus_server_start_file(DBusConnection* conn, DBusMessage* msg)
+{
+       DBusError err;
+       dbus_error_init(&err);
+
+       int uid;
+       char* lang;
+       char* type;
+       char* appid;
+       int silence;
+       char* credential;
+       char* filepath;
+       stte_audio_type_e audio_type;
+       int sample_rate;
+
+       int ret = STTD_ERROR_OPERATION_FAILED;
+
+       dbus_message_get_args(msg, &err,
+               DBUS_TYPE_INT32, &uid,
+               DBUS_TYPE_STRING, &lang,
+               DBUS_TYPE_STRING, &type,
+               DBUS_TYPE_INT32, &silence,
+               DBUS_TYPE_STRING, &appid,
+               DBUS_TYPE_STRING, &credential,
+               DBUS_TYPE_STRING, &filepath,
+               DBUS_TYPE_INT32, &audio_type,
+               DBUS_TYPE_INT32, &sample_rate,
+               DBUS_TYPE_INVALID);
+
+       SLOG(LOG_DEBUG, TAG_STTD, ">>>>> STT Start File");
+
+       if (dbus_error_is_set(&err)) {
+               SLOG(LOG_ERROR, TAG_STTD, "[IN ERROR] stt start file: get arguments error (%s)", err.message);
+               dbus_error_free(&err);
+               ret = STTD_ERROR_OPERATION_FAILED;
+       } else {
+               SLOG(LOG_DEBUG, TAG_STTD, "[IN] stt start file : uid(%d), lang(%s), type(%s), silence(%d) appid(%s) filepath(%s), audio_type(%d), sample_rate(%d)"
+                       , uid, lang, type, silence, appid, filepath, audio_type, sample_rate);
+               ret = sttd_server_start_file(uid, lang, type, silence, appid, credential, filepath, audio_type, sample_rate);
+       }
+
+       if (0 <= ret) {
+               SLOG(LOG_DEBUG, TAG_STTD, "[OUT SUCCESS] Result(%d)", ret);
+       } else {
+               SLOG(LOG_ERROR, TAG_STTD, "[OUT ERROR] Result(%d)", ret);
+               if (0 != sttdc_send_error_signal(uid, ret, "[ERROR] Fail to start file")) {
+                       SLOG(LOG_ERROR, TAG_STTD, "[ERROR] Fail to send error signal");
+               }
+       }
+
+       SLOG(LOG_DEBUG, TAG_STTD, "<<<<<");
+       SLOG(LOG_DEBUG, TAG_STTD, "  ");
+
+       return 0;
+}
+
+int sttd_dbus_server_cancel_file(DBusConnection* conn, DBusMessage* msg)
+{
+       DBusError err;
+       dbus_error_init(&err);
+
+       int uid;
+       int ret = STTD_ERROR_OPERATION_FAILED;
+       dbus_message_get_args(msg, &err, DBUS_TYPE_INT32, &uid, DBUS_TYPE_INVALID);
+
+       SLOG(LOG_DEBUG, TAG_STTD, ">>>>> STT Cancel File");
+
+       if (dbus_error_is_set(&err)) {
+               SLOG(LOG_ERROR, TAG_STTD, "[IN ERROR] stt cancel file : get arguments error (%s)", err.message);
+               dbus_error_free(&err);
+               ret = STTD_ERROR_OPERATION_FAILED;
+       } else {
+               SLOG(LOG_DEBUG, TAG_STTD, "[IN] stt cancel file : uid(%d)", uid);
+               ret = sttd_server_cancel_file(uid);
+       }
+
+       if (0 <= ret) {
+               SLOG(LOG_DEBUG, TAG_STTD, "[OUT SUCCESS] Result(%d)", ret);
+       } else {
+               SLOG(LOG_ERROR, TAG_STTD, "[OUT ERROR] Result(%d)", ret);
+               if (0 != sttdc_send_error_signal(uid, ret, "[ERROR] Fail to cancel")) {
+                       SLOG(LOG_ERROR, TAG_STTD, "[ERROR] Fail to send error signal");
+               }
+       }
+       SLOG(LOG_DEBUG, TAG_STTD, "<<<<<");
+       SLOG(LOG_DEBUG, TAG_STTD, "  ");
+
+       return 0;
+}
index 6e7c16d..da21771 100644 (file)
@@ -68,6 +68,9 @@ int sttd_dbus_server_stop(DBusConnection* conn, DBusMessage* msg);
 
 int sttd_dbus_server_cancel(DBusConnection* conn, DBusMessage* msg);
 
+int sttd_dbus_server_start_file(DBusConnection* conn, DBusMessage* msg);
+
+int sttd_dbus_server_cancel_file(DBusConnection* conn, DBusMessage* msg);
 
 
 #ifdef __cplusplus
index 5e39973..b0e7071 100644 (file)
@@ -837,6 +837,32 @@ int sttd_engine_agent_recognize_start_recorder(int uid)
        return 0;
 }
 
+int sttd_engine_agent_recognize_start_file(int uid, const char* filepath)
+{
+       if (NULL == g_engine_info) {
+               SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] The engine is not valid");
+               return STTD_ERROR_INVALID_PARAMETER;
+       }
+
+       if (false == g_engine_info->is_loaded) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Not loaded engine");
+               return STTD_ERROR_OPERATION_FAILED;
+       }
+
+       SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Start recorder");
+
+       int ret;
+       ret = sttd_recorder_start_file(uid, filepath);
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to start recorder : result(%d)", ret);
+               stt_engine_recognize_cancel();
+               sttd_recorder_stop_file();
+               return ret;
+       }
+
+       return 0;
+}
+
 int sttd_engine_agent_set_recording_data(const void* data, unsigned int length)
 {
        if (false == g_agent_init) {
@@ -867,6 +893,41 @@ int sttd_engine_agent_set_recording_data(const void* data, unsigned int length)
        return ret;
 }
 
+int sttd_engine_agent_recognize_stop_file()
+{
+       if (false == g_agent_init) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Not Initialized");
+               return STTD_ERROR_OPERATION_FAILED;
+       }
+
+       if (NULL == g_engine_info) {
+               SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] The engine is not valid");
+               return STTD_ERROR_INVALID_PARAMETER;
+       }
+
+       if (false == g_engine_info->is_loaded) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Not loaded engine");
+               return STTD_ERROR_OPERATION_FAILED;
+       }
+
+       SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Stop recorder");
+       int ret;
+       ret = sttd_recorder_stop_file();
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to stop recorder : result(%d)", ret);
+               return ret;
+       }
+
+#ifdef AUDIO_CREATE_ON_START
+       SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Destroy recorder");
+       if (0 != sttd_recorder_destroy())
+               SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to destroy recorder");
+#endif
+
+       SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent Success] Stop recorder");
+       return 0;
+}
+
 int sttd_engine_agent_recognize_stop_recorder()
 {
        if (false == g_agent_init) {
index f44723d..58058be 100644 (file)
@@ -98,10 +98,14 @@ int sttd_engine_agent_recognize_start_engine(int uid, const char* lang, const ch
 
 int sttd_engine_agent_recognize_start_recorder(int uid);
 
+int sttd_engine_agent_recognize_start_file(int uid, const char* filepath);
+
 int sttd_engine_agent_set_recording_data(const void* data, unsigned int length);
 
 int sttd_engine_agent_recognize_stop();
 
+int sttd_engine_agent_recognize_stop_file();
+
 int sttd_engine_agent_recognize_stop_recorder();
 
 int sttd_engine_agent_recognize_stop_engine();
index 52b66ef..2d9a037 100644 (file)
@@ -623,3 +623,70 @@ int sttd_recorder_stop()
 
        return 0;
 }
+
+int sttd_recorder_start_file(int uid, const char *filepath)
+{
+       if (STTD_RECORDER_STATE_RECORDING == g_recorder_state)
+               return 0;
+
+       /* Check engine id is valid */
+       if (NULL == g_recorder) {
+               SLOG(LOG_WARN, TAG_STTD, "[Recorder WARNING] Engine id is not valid");
+               return STTD_ERROR_INVALID_PARAMETER;
+       }
+       g_recorder_state = STTD_RECORDER_STATE_RECORDING;
+       g_recorder->uid = uid;
+
+       int cnt = 0;
+       int totalReadBytes = 0;
+
+       FILE *infile = fopen(filepath, "rb");
+
+       //process the file
+       if (infile != NULL) {
+               while (!feof(infile)) {
+                       static char pcm_buff[BUFFER_LENGTH];
+                       int read_byte = fread(pcm_buff, 1, BUFFER_LENGTH, infile);
+                       totalReadBytes += read_byte;
+                       if (0 != read_byte) {
+                               if (0 != g_audio_cb(pcm_buff, read_byte)) {
+                                       SLOG(LOG_ERROR, TAG_STTD, "[Recorder ERROR] Fail to call audio callback");
+                                       fclose(infile);
+                                       return -1;
+                               }
+                               if (0 == cnt % 30) {
+                                       float vol_db = get_volume_decibel(pcm_buff, BUFFER_LENGTH, g_recorder->audio_type);
+                                       if (0 != sttdc_send_set_volume(g_recorder->uid, vol_db)) {
+                                               SLOG(LOG_ERROR, TAG_STTD, "[Recorder] Fail to send recording volume(%f)", vol_db);
+                                       }
+                               }
+
+                               /* Audio read log */
+                               if (0 == cnt % 50)
+                                       SLOG(LOG_DEBUG, TAG_STTD, "[Recorder][%d] Recording... : read_size(%d)", cnt, read_byte);
+                               cnt++;
+                       }
+               }
+               fclose(infile);
+       }
+
+       SLOG(LOG_DEBUG, TAG_STTD, "[Recorder][%d] total bytes(%d)", cnt, totalReadBytes);
+       return 0;
+}
+
+int sttd_recorder_stop_file()
+{
+       if (STTD_RECORDER_STATE_READY == g_recorder_state)
+               return 0;
+
+       /* Check engine id is valid */
+       if (NULL == g_recorder) {
+               SLOG(LOG_WARN, TAG_STTD, "[Recorder WARNING] Engine id is not valid");
+               return STTD_ERROR_INVALID_PARAMETER;
+       }
+
+       g_recorder->uid = -1;
+       g_recorder_state = STTD_RECORDER_STATE_READY;
+
+       return 0;
+}
index 946a283..3c27c87 100644 (file)
@@ -42,6 +42,10 @@ int sttd_recorder_start(int uid);
 
 int sttd_recorder_stop();
 
+int sttd_recorder_start_file(int uid, const char *filepath);
+
+int sttd_recorder_stop_file();
+
 
 #ifdef __cplusplus
 }
old mode 100755 (executable)
new mode 100644 (file)
index f364cf3..8fcee24
@@ -341,8 +341,8 @@ int __server_speech_status_callback(stte_speech_status_e status, void *user_para
                        return STTD_ERROR_OPERATION_FAILED;
                }
 
-               if (APP_STATE_RECORDING != state) {
-                       SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Current state is not recording");
+               if (APP_STATE_RECORDING != state && APP_STATE_PROCESSING != state) {
+                       SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Current state is not recording, state(%d), status(%d)", state, status);
                        return STTD_ERROR_INVALID_STATE;
                }
 
@@ -1448,3 +1448,172 @@ int sttd_server_cancel(int uid)
 
        return STTD_ERROR_NONE;
 }
+
+int sttd_server_start_file(int uid, const char* lang, const char* recognition_type, int silence, const char* appid, const char* credential,
+                                                       const char* filepath, stte_audio_type_e audio_type, int sample_rate)
+{
+       if (NULL == lang || NULL == recognition_type || NULL == filepath) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Input parameter is NULL");
+               return STTD_ERROR_INVALID_PARAMETER;
+       }
+
+       /* check if uid is valid */
+       app_state_e state;
+       if (0 != sttd_client_get_state(uid, &state)) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] uid is NOT valid ");
+               return STTD_ERROR_INVALID_PARAMETER;
+       }
+
+       /* check uid state */
+       if (APP_STATE_READY != state) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] sttd_server_start : current state is not ready");
+               return STTD_ERROR_INVALID_STATE;
+       }
+
+       int ret = 0;
+       if (false == stt_client_get_app_agreed(uid)) {
+               bool temp = false;
+               ret = sttd_engine_agent_check_app_agreed(appid, &temp);
+               if (0 != ret) {
+                       SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to get engine available : %d", ret);
+                       return ret;
+               }
+
+               if (false == temp) {
+                       SLOG(LOG_ERROR, TAG_STTD, "[Server] App(%s) NOT confirmed that engine is available", appid);
+                       return STTD_ERROR_PERMISSION_DENIED;
+               }
+
+               stt_client_set_app_agreed(uid);
+       }
+
+       /* check if engine use network */
+       if (true == sttd_engine_agent_need_network()) {
+               if (false == stt_network_is_connected()) {
+                       SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Disconnect network. Current engine needs to network connection.");
+                       return STTD_ERROR_OUT_OF_NETWORK;
+               }
+       }
+
+       if (0 != stt_client_set_current_recognition(uid)) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Current STT is busy because of recording or processing");
+               return STTD_ERROR_RECORDER_BUSY;
+       }
+
+       /* engine start recognition */
+       SLOG(LOG_DEBUG, TAG_STTD, "[Server] start : uid(%d), lang(%s), recog_type(%s), appid(%s), file(%s), audio_type(%d), sample_rate(%d)", uid, lang, recognition_type, appid, filepath, audio_type, sample_rate);
+
+       /* 1. Set audio session */
+       ret = sttd_recorder_set_audio_session();
+       if (0 != ret) {
+               stt_client_unset_current_recognition();
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to set session : %d", ret);
+               return ret;
+       }
+
+       /* 2. Start engine to recognize */
+       ret = sttd_engine_agent_recognize_start_engine(uid, lang, recognition_type, silence, appid, credential, NULL);
+       if (0 != ret) {
+               stt_client_unset_current_recognition();
+               sttd_recorder_unset_audio_session();
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to start engine : result(%d)", ret);
+               return ret;
+       }
+
+       sttd_client_set_state(uid, APP_STATE_RECORDING);
+       sttdc_send_set_state(uid, APP_STATE_RECORDING);
+
+       /* 3. Start to send pcm from file to engine */
+       ret = sttd_engine_agent_recognize_start_file(uid, filepath);
+       if (0 != ret) {
+               stt_client_unset_current_recognition();
+               sttd_recorder_unset_audio_session();
+               sttd_engine_agent_recognize_cancel();
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to start file : result(%d)", ret);
+               return ret;
+       }
+
+       /* 4. Stop to send pcm from file  */
+       ret = sttd_engine_agent_recognize_stop_file();
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to stop recorder : result(%d)", ret);
+               stt_client_unset_current_recognition();
+               sttd_recorder_unset_audio_session();
+               sttd_engine_agent_recognize_cancel();
+               return ret;
+       }
+
+       /* 5. change & notify uid state */
+       sttd_client_set_state(uid, APP_STATE_PROCESSING);
+       sttdc_send_set_state(uid, APP_STATE_PROCESSING);
+
+       /* 6. Unset audio session */
+       ret = sttd_recorder_unset_audio_session();
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to unset session : %d", ret);
+               stt_client_unset_current_recognition();
+               return ret;
+       }
+
+       /* 7. Stop engine */
+       ret = sttd_engine_agent_recognize_stop_engine();
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to stop engine : result(%d)", ret);
+               stt_client_unset_current_recognition();
+               return ret;
+       }
+
+       return STTD_ERROR_NONE;
+}
+
+int sttd_server_cancel_file(int uid)
+{
+       /* check if uid is valid */
+       app_state_e state;
+       if (0 != sttd_client_get_state(uid, &state)) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] uid is NOT valid ");
+               return STTD_ERROR_INVALID_PARAMETER;
+       }
+
+       /* check uid state */
+       if (APP_STATE_READY == state) {
+               SLOG(LOG_WARN, TAG_STTD, "[Server WARNING] Current state is ready");
+               return STTD_ERROR_NONE;
+       }
+
+       stt_client_unset_current_recognition();
+
+       if (NULL != g_recording_timer) {
+               ecore_timer_del(g_recording_timer);
+               g_recording_timer = NULL;
+       }
+
+       if (NULL != g_processing_timer) {
+               ecore_timer_del(g_processing_timer);
+               g_processing_timer = NULL;
+       }
+
+       if (APP_STATE_RECORDING == state) {
+               /* Unset audio session */
+               int ret = sttd_recorder_unset_audio_session();
+               if (0 != ret) {
+                       SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to unset session : %d", ret);
+                       return ret;
+               }
+       }
+
+       /* change uid state */
+       sttd_client_set_state(uid, APP_STATE_READY);
+
+       /* cancel engine recognition */
+       int ret = sttd_engine_agent_recognize_cancel();
+       if (0 != ret) {
+               SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to cancel : result(%d)", ret);
+               return ret;
+       }
+
+       /* Notify uid state change */
+       sttdc_send_set_state(uid, APP_STATE_READY);
+
+       return STTD_ERROR_NONE;
+}
index 0fd6dd9..72c231b 100644 (file)
@@ -76,6 +76,9 @@ int sttd_server_stop(int uid);
 
 int sttd_server_cancel(int uid);
 
+int sttd_server_start_file(int uid, const char* lang, const char* recognition_type, int silence, const char* appid, const char* credential, const char* filepath, stte_audio_type_e audio_type, int sample_rate);
+
+int sttd_server_cancel_file(int uid);
 
 
 #ifdef __cplusplus