Update to latest UniMRCP version. MRCP requests can no timeout if there is no server response.

This commit is contained in:
Christopher Rienzo committed 2011-06-16 16:25:00 +00:00
1 parent 0555b702db
commit 17099473a3
441 files changed
+17430 -17071

No files matched your search

@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: dtmfscenario.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include <stdlib.h>
+9 -13
View File
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: dtmfsession.cpp 1780 2010-09-01 05:59:32Z achaloyan $
*/
#include "dtmfsession.h"
@@ -30,8 +32,6 @@ struct RecogChannel
mrcp_channel_t* m_pMrcpChannel;
/** DTMF generator */
mpf_dtmf_generator_t* m_pDtmfGenerator;
/** Audio stream */
mpf_audio_stream_t* m_pStream;
/** Streaming is in-progress */
bool m_Streaming;
};
@@ -79,13 +79,6 @@ bool DtmfSession::OnSessionTerminate(mrcp_sig_status_code_e status)
return UmcSession::OnSessionTerminate(status);
}
static apt_bool_t OpenStream(mpf_audio_stream_t* pStream, mpf_codec_t *codec)
{
RecogChannel* pRecogChannel = (RecogChannel*) pStream->obj;
pRecogChannel->m_pStream = pStream;
return TRUE;
}
static apt_bool_t ReadStream(mpf_audio_stream_t* pStream, mpf_frame_t* pFrame)
{
RecogChannel* pRecogChannel = (RecogChannel*) pStream->obj;
@@ -110,7 +103,6 @@ RecogChannel* DtmfSession::CreateRecogChannel()
RecogChannel *pRecogChannel = new RecogChannel;
pRecogChannel->m_pMrcpChannel = NULL;
pRecogChannel->m_pDtmfGenerator = NULL;
pRecogChannel->m_pStream = NULL;
pRecogChannel->m_Streaming = false;
/* create source stream capabilities */
@@ -120,7 +112,7 @@ RecogChannel* DtmfSession::CreateRecogChannel()
static const mpf_audio_stream_vtable_t audio_stream_vtable =
{
NULL,
OpenStream,
NULL,
NULL,
ReadStream,
NULL,
@@ -162,7 +154,11 @@ bool DtmfSession::OnChannelAdd(mrcp_channel_t* pMrcpChannel, mrcp_sig_status_cod
RecogChannel* pRecogChannel = (RecogChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pRecogChannel)
{
pRecogChannel->m_pDtmfGenerator = mpf_dtmf_generator_create(pRecogChannel->m_pStream,GetSessionPool());
const mpf_audio_stream_t* pStream = mrcp_application_audio_stream_get(pMrcpChannel);
if(pStream)
{
pRecogChannel->m_pDtmfGenerator = mpf_dtmf_generator_create(pStream,GetSessionPool());
}
}
return StartRecognition(pMrcpChannel);
+3 -1
View File
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: main.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include "umcconsole.h"
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: recogscenario.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include <stdlib.h>
+53 -10
View File
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: recogsession.cpp 1587 2010-03-12 19:40:02Z achaloyan $
*/
#include "recogsession.h"
@@ -27,12 +29,21 @@ struct RecogChannel
{
/** MRCP control channel */
mrcp_channel_t* m_pMrcpChannel;
/** IN-PROGRESS RECOGNIZE request */
mrcp_message_t* m_pRecogRequest;
/** Streaming is in-progress */
bool m_Streaming;
/** File to read audio stream from */
FILE* m_pAudioIn;
/** Estimated time to complete (used if no audio_in available) */
apr_size_t m_TimeToComplete;
RecogChannel() :
m_pMrcpChannel(NULL),
m_pRecogRequest(NULL),
m_Streaming(false),
m_pAudioIn(NULL),
m_TimeToComplete(0) {}
};
RecogSession::RecogSession(const RecogScenario* pScenario) :
@@ -67,6 +78,37 @@ bool RecogSession::Start()
return true;
}
bool RecogSession::Stop()
{
if(!UmcSession::Stop())
return false;
if(!m_pRecogChannel)
return false;
mrcp_message_t* pStopMessage = CreateMrcpMessage(m_pRecogChannel->m_pMrcpChannel,RECOGNIZER_STOP);
if(!pStopMessage)
return false;
if(m_pRecogChannel->m_pRecogRequest)
{
mrcp_generic_header_t* pGenericHeader;
/* get/allocate generic header */
pGenericHeader = (mrcp_generic_header_t*) mrcp_generic_header_prepare(pStopMessage);
if(pGenericHeader)
{
pGenericHeader->active_request_id_list.count = 1;
pGenericHeader->active_request_id_list.ids[0] =
m_pRecogChannel->m_pRecogRequest->start_line.request_id;
mrcp_generic_header_property_add(pStopMessage,GENERIC_HEADER_ACTIVE_REQUEST_ID_LIST);
}
m_pRecogChannel->m_pRecogRequest = NULL;
}
return SendMrcpRequest(m_pRecogChannel->m_pMrcpChannel,pStopMessage);
}
bool RecogSession::OnSessionTerminate(mrcp_sig_status_code_e status)
{
if(m_pRecogChannel)
@@ -128,11 +170,7 @@ RecogChannel* RecogSession::CreateRecogChannel()
apr_pool_t* pool = GetSessionPool();
/* create channel */
RecogChannel *pRecogChannel = new RecogChannel;
pRecogChannel->m_pMrcpChannel = NULL;
pRecogChannel->m_Streaming = false;
pRecogChannel->m_pAudioIn = NULL;
pRecogChannel->m_TimeToComplete = 0;
RecogChannel* pRecogChannel = new RecogChannel;
/* create source stream capabilities */
pCapabilities = mpf_source_stream_capabilities_create(pool);
@@ -218,11 +256,13 @@ bool RecogSession::OnMessageReceive(mrcp_channel_t* pMrcpChannel, mrcp_message_t
/* received the response to RECOGNIZE request */
if(pMrcpMessage->start_line.request_state == MRCP_REQUEST_STATE_INPROGRESS)
{
RecogChannel* pRecogChannel = (RecogChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pRecogChannel)
pRecogChannel->m_pRecogRequest = GetMrcpMessage();
/* start to stream the speech to recognize */
if(pRecogChannel)
{
pRecogChannel->m_Streaming = true;
}
}
else
{
@@ -241,9 +281,12 @@ bool RecogSession::OnMessageReceive(mrcp_channel_t* pMrcpChannel, mrcp_message_t
{
ParseNLSMLResult(pMrcpMessage);
if(pRecogChannel)
{
pRecogChannel->m_Streaming = false;
}
RecogChannel* pRecogChannel = (RecogChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pRecogChannel)
pRecogChannel->m_pRecogRequest = NULL;
Terminate();
}
else if(pMrcpMessage->start_line.method_id == RECOGNIZER_START_OF_INPUT)
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: recorderscenario.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include <stdlib.h>
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: recordersession.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include "recordersession.h"
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: setparamscenario.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include "setparamscenario.h"
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: setparamsession.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include "setparamsession.h"
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: synthscenario.cpp 1474 2010-02-07 20:51:47Z achaloyan $
*/
#include <stdlib.h>
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: synthsession.cpp 1586 2010-03-12 19:39:02Z achaloyan $
*/
#include "synthsession.h"
@@ -23,9 +25,14 @@
struct SynthChannel
{
/** MRCP channel */
mrcp_channel_t* m_pMrcpChannel;
/** IN-PROGRESS SPEAK request */
mrcp_message_t* m_pSpeakRequest;
/** File to write audio stream to */
FILE* m_pAudioOut;
SynthChannel() : m_pMrcpChannel(NULL), m_pSpeakRequest(NULL), m_pAudioOut(NULL) {}
};
SynthSession::SynthSession(const SynthScenario* pScenario) :
@@ -58,6 +65,37 @@ bool SynthSession::Start()
return true;
}
bool SynthSession::Stop()
{
if(!UmcSession::Stop())
return false;
if(!m_pSynthChannel)
return false;
mrcp_message_t* pStopMessage = CreateMrcpMessage(m_pSynthChannel->m_pMrcpChannel,SYNTHESIZER_STOP);
if(!pStopMessage)
return false;
if(m_pSynthChannel->m_pSpeakRequest)
{
mrcp_generic_header_t* pGenericHeader;
/* get/allocate generic header */
pGenericHeader = (mrcp_generic_header_t*) mrcp_generic_header_prepare(pStopMessage);
if(pGenericHeader)
{
pGenericHeader->active_request_id_list.count = 1;
pGenericHeader->active_request_id_list.ids[0] =
m_pSynthChannel->m_pSpeakRequest->start_line.request_id;
mrcp_generic_header_property_add(pStopMessage,GENERIC_HEADER_ACTIVE_REQUEST_ID_LIST);
}
m_pSynthChannel->m_pSpeakRequest = NULL;
}
return SendMrcpRequest(m_pSynthChannel->m_pMrcpChannel,pStopMessage);
}
bool SynthSession::OnSessionTerminate(mrcp_sig_status_code_e status)
{
if(m_pSynthChannel)
@@ -93,8 +131,7 @@ SynthChannel* SynthSession::CreateSynthChannel()
apr_pool_t* pool = GetSessionPool();
/* create channel */
SynthChannel *pSynthChannel = new SynthChannel;
pSynthChannel->m_pMrcpChannel = NULL;
SynthChannel* pSynthChannel = new SynthChannel;
/* create sink stream capabilities */
pCapabilities = mpf_sink_stream_capabilities_create(pool);
@@ -128,7 +165,6 @@ SynthChannel* SynthSession::CreateSynthChannel()
}
pSynthChannel->m_pMrcpChannel = pChannel;
pSynthChannel->m_pAudioOut = NULL;
return pSynthChannel;
}
@@ -169,6 +205,10 @@ bool SynthSession::OnMessageReceive(mrcp_channel_t* pMrcpChannel, mrcp_message_t
/* received the response to SPEAK request */
if(pMrcpMessage->start_line.request_state == MRCP_REQUEST_STATE_INPROGRESS)
{
SynthChannel* pSynthChannel = (SynthChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pSynthChannel)
pSynthChannel->m_pSpeakRequest = GetMrcpMessage();
/* waiting for SPEAK-COMPLETE event */
}
else
@@ -187,6 +227,9 @@ bool SynthSession::OnMessageReceive(mrcp_channel_t* pMrcpChannel, mrcp_message_t
/* received MRCP event */
if(pMrcpMessage->start_line.method_id == SYNTHESIZER_SPEAK_COMPLETE)
{
SynthChannel* pSynthChannel = (SynthChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pSynthChannel)
pSynthChannel->m_pSpeakRequest = NULL;
/* received SPEAK-COMPLETE event, terminate the session */
Terminate();
}
+38 -17
View File
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: umcconsole.cpp 1785 2010-09-22 06:14:29Z achaloyan $
*/
#include <stdio.h>
@@ -37,6 +39,7 @@ bool UmcConsole::Run(int argc, const char * const *argv)
{
apr_pool_t* pool = NULL;
apt_dir_layout_t* pDirLayout = NULL;
const char *logConfPath;
/* APR global initialization */
if(apr_initialize() != APR_SUCCESS)
@@ -63,13 +66,27 @@ bool UmcConsole::Run(int argc, const char * const *argv)
/* create the structure of default directories layout */
pDirLayout = apt_default_dir_layout_create(m_Options.m_RootDirPath,pool);
/* create singleton logger */
apt_log_instance_create(m_Options.m_LogOutput,m_Options.m_LogPriority,pool);
if((m_Options.m_LogOutput & APT_LOG_OUTPUT_FILE) == APT_LOG_OUTPUT_FILE)
/* get path to logger configuration file */
logConfPath = apt_confdir_filepath_get(pDirLayout,"logger.xml",pool);
/* create and load singleton logger */
apt_log_instance_load(logConfPath,pool);
if(m_Options.m_LogPriority)
{
/* override the log priority, if specified in command line */
apt_log_priority_set((apt_log_priority_e)atoi(m_Options.m_LogPriority));
}
if(m_Options.m_LogOutput)
{
/* override the log output mode, if specified in command line */
apt_log_output_mode_set((apt_log_output_e)atoi(m_Options.m_LogOutput));
}
if(apt_log_output_mode_check(APT_LOG_OUTPUT_FILE) == TRUE)
{
/* open the log file */
apt_log_file_open(pDirLayout->log_dir_path,"unimrcpclient",MAX_LOG_FILE_SIZE,MAX_LOG_FILE_COUNT,pool);
apt_log_file_open(pDirLayout->log_dir_path,"unimrcpclient",MAX_LOG_FILE_SIZE,MAX_LOG_FILE_COUNT,FALSE,pool);
}
/* create demo framework */
@@ -105,7 +122,7 @@ bool UmcConsole::ProcessCmdLine(char* pCmdLine)
const char* pProfileName = apr_strtok(NULL, " ", &last);
if(!pProfileName)
{
pProfileName = "MRCPv2-Default";
pProfileName = "uni2";
}
m_pFramework->RunSession(pScenarioName,pProfileName);
}
@@ -118,6 +135,14 @@ bool UmcConsole::ProcessCmdLine(char* pCmdLine)
m_pFramework->KillSession(pID);
}
}
else if(strcasecmp(name,"stop") == 0)
{
char* pID = apr_strtok(NULL, " ", &last);
if(pID)
{
m_pFramework->StopSession(pID);
}
}
else if(strcasecmp(name,"show") == 0)
{
char* pWhat = apr_strtok(NULL, " ", &last);
@@ -146,12 +171,12 @@ bool UmcConsole::ProcessCmdLine(char* pCmdLine)
printf("usage:\n"
"\n- run [scenario] [profile] (run new session)\n"
" scenario is one of 'synth', 'recog', ... (use 'show scenarios')\n"
" profile is one of 'MRCPv2-Default', 'MRCPv1-Default', ... (see unimrcpclient.xml)\n"
" profile is one of 'uni2', 'uni1', ... (see unimrcpclient.xml)\n"
"\n examples: \n"
" run synth\n"
" run recog\n"
" run synth MRCPv1-Default\n"
" run recog MRCPv1-Default\n"
" run synth uni1\n"
" run recog uni1\n"
"\n- kill [id] (kill session)\n"
" id is a session identifier: 1, 2, ... (use 'show sessions')\n"
"\n example: \n"
@@ -238,8 +263,8 @@ bool UmcConsole::LoadOptions(int argc, const char * const *argv, apr_pool_t *poo
/* set the default options */
m_Options.m_RootDirPath = "../";
m_Options.m_LogPriority = APT_PRIO_INFO;
m_Options.m_LogOutput = APT_LOG_OUTPUT_CONSOLE;
m_Options.m_LogPriority = NULL;
m_Options.m_LogOutput = NULL;
rv = apr_getopt_init(&opt, pool , argc, argv);
if(rv != APR_SUCCESS)
@@ -254,15 +279,11 @@ bool UmcConsole::LoadOptions(int argc, const char * const *argv, apr_pool_t *poo
break;
case 'l':
if(optarg)
{
m_Options.m_LogPriority = (apt_log_priority_e) atoi(optarg);
}
m_Options.m_LogPriority = optarg;
break;
case 'o':
if(optarg)
{
m_Options.m_LogOutput = (apt_log_output_e) atoi(optarg);
}
m_Options.m_LogOutput = optarg;
break;
case 'h':
Usage();
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,6 +12,8 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: umcframework.cpp 1767 2010-08-23 19:10:22Z achaloyan $
*/
#include "umcframework.h"
@@ -21,6 +23,7 @@
#include "recorderscenario.h"
#include "dtmfscenario.h"
#include "setparamscenario.h"
#include "verifierscenario.h"
#include "unimrcp_client.h"
#include "apt_log.h"
@@ -36,6 +39,7 @@ enum UmcTaskMsgType
{
UMC_TASK_CLIENT_MSG,
UMC_TASK_RUN_SESSION_MSG,
UMC_TASK_STOP_SESSION_MSG,
UMC_TASK_KILL_SESSION_MSG,
UMC_TASK_SHOW_SCENARIOS_MSG,
UMC_TASK_SHOW_SESSIONS_MSG
@@ -134,7 +138,7 @@ bool UmcFramework::CreateTask()
return false;
pTask = apt_consumer_task_base_get(m_pTask);
apt_task_name_set(pTask,"Framework Task");
apt_task_name_set(pTask,"Framework Agent");
pVtable = apt_consumer_task_vtable_get(m_pTask);
if(pVtable)
{
@@ -175,6 +179,8 @@ UmcScenario* UmcFramework::CreateScenario(const char* pType)
return new DtmfScenario();
else if(strcasecmp(pType,"Params") == 0)
return new SetParamScenario();
else if(strcasecmp(pType,"Verifier") == 0)
return new VerifierScenario();
}
return NULL;
}
@@ -335,6 +341,24 @@ bool UmcFramework::ProcessRunRequest(const char* pScenarioName, const char* pPro
return true;
}
void UmcFramework::ProcessStopRequest(const char* id)
{
UmcSession* pSession;
void* pVal;
apr_hash_index_t* it = apr_hash_first(m_pPool,m_pSessionTable);
for(; it; it = apr_hash_next(it))
{
apr_hash_this(it,NULL,NULL,&pVal);
pSession = (UmcSession*) pVal;
if(pSession && strcasecmp(pSession->GetId(),id) == 0)
{
/* stop in-progress request */
pSession->Stop();
return;
}
}
}
void UmcFramework::ProcessKillRequest(const char* id)
{
UmcSession* pSession;
@@ -346,7 +370,7 @@ void UmcFramework::ProcessKillRequest(const char* id)
pSession = (UmcSession*) pVal;
if(pSession && strcasecmp(pSession->GetId(),id) == 0)
{
/* first, terminate session */
/* terminate session */
pSession->Terminate();
return;
}
@@ -403,6 +427,22 @@ void UmcFramework::RunSession(const char* pScenarioName, const char* pProfileNam
apt_task_msg_signal(pTask,pTaskMsg);
}
void UmcFramework::StopSession(const char* id)
{
apt_task_t* pTask = apt_consumer_task_base_get(m_pTask);
apt_task_msg_t* pTaskMsg = apt_task_msg_get(pTask);
if(!pTaskMsg)
return;
pTaskMsg->type = TASK_MSG_USER;
pTaskMsg->sub_type = UMC_TASK_STOP_SESSION_MSG;
UmcTaskMsg* pUmcMsg = (UmcTaskMsg*) pTaskMsg->data;
strncpy(pUmcMsg->m_SessionId,id,sizeof(pUmcMsg->m_SessionId)-1);
pUmcMsg->m_pAppMessage = NULL;
apt_task_msg_signal(pTask,pTaskMsg);
}
void UmcFramework::KillSession(const char* id)
{
apt_task_t* pTask = apt_consumer_task_base_get(m_pTask);
@@ -562,6 +602,11 @@ apt_bool_t UmcProcessMsg(apt_task_t *pTask, apt_task_msg_t *pMsg)
pFramework->ProcessRunRequest(pUmcMsg->m_ScenarioName,pUmcMsg->m_ProfileName);
break;
}
case UMC_TASK_STOP_SESSION_MSG:
{
pFramework->ProcessStopRequest(pUmcMsg->m_SessionId);
break;
}
case UMC_TASK_KILL_SESSION_MSG:
{
pFramework->ProcessKillRequest(pUmcMsg->m_SessionId);
+30 -10
View File
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,14 +12,17 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: umcscenario.cpp 1571 2010-03-07 20:33:39Z achaloyan $
*/
#include <stdlib.h>
#include "umcscenario.h"
#include "apt_log.h"
UmcScenario::UmcScenario() :
m_pName(NULL),
m_pMrcpProfile("MRCPv2-Default"),
m_pMrcpProfile("uni2"),
m_pDirLayout(NULL),
m_ResourceDiscovery(false),
m_pCapabilities(NULL),
@@ -200,14 +203,31 @@ const char* UmcScenario::LoadFileContent(const char* pFileName, apr_pool_t* pool
if(!pFilePath)
return NULL;
FILE* pFile = fopen(pFilePath,"r");
if(!pFile)
apr_file_t *pFile;
if(apr_file_open(&pFile,pFilePath,APR_FOPEN_READ|APR_FOPEN_BINARY,0,pool) != APR_SUCCESS)
{
apt_log(APT_LOG_MARK,APT_PRIO_WARNING,"Failed to Open File %s",pFilePath);
return NULL;
}
char text[1024];
apr_size_t size;
size = fread(text,1,sizeof(text)-1,pFile);
text[size] = '\0';
fclose(pFile);
return apr_pstrdup(pool,text);
apr_finfo_t finfo;
if(apr_file_info_get(&finfo,APR_FINFO_SIZE,pFile) != APR_SUCCESS)
{
apt_log(APT_LOG_MARK,APT_PRIO_WARNING,"Failed to Get File Info %s",pFilePath);
apr_file_close(pFile);
return NULL;
}
apr_size_t size = (apr_size_t)finfo.size;
char* pContent = (char*) apr_palloc(pool,size+1);
apt_log(APT_LOG_MARK,APT_PRIO_DEBUG,"Load File Content size [%"APR_SIZE_T_FMT" bytes] %s",size,pFilePath);
if(apr_file_read(pFile,pContent,&size) != APR_SUCCESS)
{
apt_log(APT_LOG_MARK,APT_PRIO_WARNING,"Failed to Read Content %s",pFilePath);
apr_file_close(pFile);
return NULL;
}
pContent[size] = '\0';
apr_file_close(pFile);
return pContent;
}
+28 -2
View File
@@ -1,5 +1,5 @@
/*
* Copyright 2008 Arsen Chaloyan
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -12,16 +12,20 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: umcsession.cpp 1695 2010-05-19 18:56:15Z achaloyan $
*/
#include "umcsession.h"
#include "umcscenario.h"
#include "mrcp_message.h"
UmcSession::UmcSession(const UmcScenario* pScenario) :
m_pScenario(pScenario),
m_pMrcpProfile(NULL),
m_pMrcpApplication(NULL),
m_pMrcpSession(NULL),
m_pMrcpMessage(NULL),
m_Running(false),
m_Terminating(false)
{
@@ -69,6 +73,14 @@ bool UmcSession::Run()
return ret;
}
bool UmcSession::Stop()
{
if(m_Terminating)
return false;
return true;
}
bool UmcSession::Terminate()
{
if(m_Terminating)
@@ -105,7 +117,17 @@ bool UmcSession::OnChannelRemove(mrcp_channel_t *channel, mrcp_sig_status_code_e
bool UmcSession::OnMessageReceive(mrcp_channel_t *channel, mrcp_message_t *message)
{
return m_Running;
if(!m_Running)
return false;
if(!m_pMrcpMessage)
return false;
/* match request identifiers */
if(m_pMrcpMessage->start_line.request_id != message->start_line.request_id)
return false;
return true;
}
bool UmcSession::OnTerminateEvent(mrcp_channel_t *channel)
@@ -129,6 +151,9 @@ bool UmcSession::OnResourceDiscover(mrcp_session_descriptor_t* descriptor, mrcp_
bool UmcSession::CreateMrcpSession(const char* pProfileName)
{
m_pMrcpSession = mrcp_application_session_create(m_pMrcpApplication,pProfileName,this);
char name[32];
apr_snprintf(name,sizeof(name),"umc-%s",m_Id);
mrcp_application_session_name_set(m_pMrcpSession,name);
return (m_pMrcpSession != NULL);
}
@@ -163,6 +188,7 @@ bool UmcSession::SendMrcpRequest(mrcp_channel_t* pMrcpChannel, mrcp_message_t* p
if(!m_Running)
return false;
m_pMrcpMessage = pMrcpMessage;
return (mrcp_application_message_send(m_pMrcpSession,pMrcpChannel,pMrcpMessage) == TRUE);
}
@@ -0,0 +1,82 @@
/*
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: verifierscenario.cpp 1775 2010-08-26 18:23:38Z achaloyan $
*/
#include <stdlib.h>
#include "verifierscenario.h"
#include "verifiersession.h"
#include "mrcp_message.h"
#include "mrcp_generic_header.h"
#include "mrcp_recog_header.h"
#include "mrcp_recog_resource.h"
#include "apt_log.h"
VerifierScenario::VerifierScenario() :
m_RepositoryURI(NULL),
m_VerificationMode(NULL),
m_VoiceprintIdentifier(NULL)
{
}
VerifierScenario::~VerifierScenario()
{
}
void VerifierScenario::Destroy()
{
}
bool VerifierScenario::LoadElement(const apr_xml_elem* pElem, apr_pool_t* pool)
{
if(UmcScenario::LoadElement(pElem,pool))
return true;
if(strcasecmp(pElem->name,"verify") == 0)
{
LoadVerify(pElem,pool);
return true;
}
return false;
}
bool VerifierScenario::LoadVerify(const apr_xml_elem* pElem, apr_pool_t* pool)
{
const apr_xml_attr* pAttr;
for(pAttr = pElem->attr; pAttr; pAttr = pAttr->next)
{
if(strcasecmp(pAttr->name,"repository-uri") == 0)
{
m_RepositoryURI = pAttr->value;
}
else if(strcasecmp(pAttr->name,"verification-mode") == 0)
{
m_VerificationMode = pAttr->value;
}
else if(strcasecmp(pAttr->name,"voiceprint-identifier") == 0)
{
m_VoiceprintIdentifier = pAttr->value;
}
}
return true;
}
UmcSession* VerifierScenario::CreateSession()
{
return new VerifierSession(this);
}
@@ -0,0 +1,389 @@
/*
* Copyright 2008-2010 Arsen Chaloyan
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: verifiersession.cpp 1778 2010-08-27 17:34:52Z achaloyan $
*/
#include "verifiersession.h"
#include "verifierscenario.h"
#include "mrcp_message.h"
#include "mrcp_generic_header.h"
#include "mrcp_verifier_header.h"
#include "mrcp_verifier_resource.h"
#include "apt_nlsml_doc.h"
#include "apt_log.h"
struct VerifierChannel
{
/** MRCP control channel */
mrcp_channel_t* m_pMrcpChannel;
/** IN-PROGRESS VERIFY request */
mrcp_message_t* m_pVerificationRequest;
/** Streaming is in-progress */
bool m_Streaming;
/** File to read audio stream from */
FILE* m_pAudioIn;
/** Estimated time to complete (used if no audio_in available) */
apr_size_t m_TimeToComplete;
VerifierChannel() :
m_pMrcpChannel(NULL),
m_pVerificationRequest(NULL),
m_Streaming(false),
m_pAudioIn(NULL),
m_TimeToComplete(0) {}
};
VerifierSession::VerifierSession(const VerifierScenario* pScenario) :
UmcSession(pScenario),
m_pVerifierChannel(NULL),
m_ContentId("request1@form-level")
{
}
VerifierSession::~VerifierSession()
{
}
bool VerifierSession::Start()
{
/* create channel and associate all the required data */
m_pVerifierChannel = CreateVerifierChannel();
if(!m_pVerifierChannel)
return false;
/* add channel to session (send asynchronous request) */
if(!AddMrcpChannel(m_pVerifierChannel->m_pMrcpChannel))
{
delete m_pVerifierChannel;
m_pVerifierChannel = NULL;
return false;
}
return true;
}
bool VerifierSession::Stop()
{
if(!UmcSession::Stop())
return false;
if(!m_pVerifierChannel)
return false;
mrcp_message_t* pStopMessage = CreateMrcpMessage(m_pVerifierChannel->m_pMrcpChannel,VERIFIER_STOP);
if(!pStopMessage)
return false;
return SendMrcpRequest(m_pVerifierChannel->m_pMrcpChannel,pStopMessage);
}
bool VerifierSession::OnSessionTerminate(mrcp_sig_status_code_e status)
{
if(m_pVerifierChannel)
{
FILE* pAudioIn = m_pVerifierChannel->m_pAudioIn;
if(pAudioIn)
{
m_pVerifierChannel->m_pAudioIn = NULL;
fclose(pAudioIn);
}
delete m_pVerifierChannel;
m_pVerifierChannel = NULL;
}
return UmcSession::OnSessionTerminate(status);
}
static apt_bool_t ReadStream(mpf_audio_stream_t* pStream, mpf_frame_t* pFrame)
{
VerifierChannel* pVerifierChannel = (VerifierChannel*) pStream->obj;
if(pVerifierChannel && pVerifierChannel->m_Streaming)
{
if(pVerifierChannel->m_pAudioIn)
{
if(fread(pFrame->codec_frame.buffer,1,pFrame->codec_frame.size,pVerifierChannel->m_pAudioIn) == pFrame->codec_frame.size)
{
/* normal read */
pFrame->type |= MEDIA_FRAME_TYPE_AUDIO;
}
else
{
/* file is over */
pVerifierChannel->m_Streaming = false;
}
}
else
{
/* fill with silence in case no file available */
if(pVerifierChannel->m_TimeToComplete >= CODEC_FRAME_TIME_BASE)
{
pFrame->type |= MEDIA_FRAME_TYPE_AUDIO;
memset(pFrame->codec_frame.buffer,0,pFrame->codec_frame.size);
pVerifierChannel->m_TimeToComplete -= CODEC_FRAME_TIME_BASE;
}
else
{
pVerifierChannel->m_Streaming = false;
}
}
}
return TRUE;
}
VerifierChannel* VerifierSession::CreateVerifierChannel()
{
mrcp_channel_t* pChannel;
mpf_termination_t* pTermination;
mpf_stream_capabilities_t* pCapabilities;
apr_pool_t* pool = GetSessionPool();
/* create channel */
VerifierChannel* pVerifierChannel = new VerifierChannel;
/* create source stream capabilities */
pCapabilities = mpf_source_stream_capabilities_create(pool);
GetScenario()->InitCapabilities(pCapabilities);
static const mpf_audio_stream_vtable_t audio_stream_vtable =
{
NULL,
NULL,
NULL,
ReadStream,
NULL,
NULL,
NULL
};
pTermination = CreateAudioTermination(
&audio_stream_vtable, /* virtual methods table of audio stream */
pCapabilities, /* capabilities of audio stream */
pVerifierChannel); /* object to associate */
pChannel = CreateMrcpChannel(
MRCP_VERIFIER_RESOURCE, /* MRCP resource identifier */
pTermination, /* media termination, used to terminate audio stream */
NULL, /* RTP descriptor, used to create RTP termination (NULL by default) */
pVerifierChannel); /* object to associate */
if(!pChannel)
{
delete pVerifierChannel;
return NULL;
}
pVerifierChannel->m_pMrcpChannel = pChannel;
return pVerifierChannel;
}
bool VerifierSession::OnChannelAdd(mrcp_channel_t* pMrcpChannel, mrcp_sig_status_code_e status)
{
if(!UmcSession::OnChannelAdd(pMrcpChannel,status))
return false;
if(status != MRCP_SIG_STATUS_CODE_SUCCESS)
{
/* error case, just terminate the demo */
return Terminate();
}
return StartVerification(pMrcpChannel);
}
bool VerifierSession::OnMessageReceive(mrcp_channel_t* pMrcpChannel, mrcp_message_t* pMrcpMessage)
{
if(!UmcSession::OnMessageReceive(pMrcpChannel,pMrcpMessage))
return false;
VerifierChannel* pVerifierChannel = (VerifierChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pMrcpMessage->start_line.message_type == MRCP_MESSAGE_TYPE_RESPONSE)
{
/* received MRCP response */
if(pMrcpMessage->start_line.method_id == VERIFIER_START_SESSION)
{
/* received the response to START-SESSION request */
/* create and send VERIFY request */
mrcp_message_t* pMrcpMessage = CreateVerificationRequest(pMrcpChannel);
if(pMrcpMessage)
{
SendMrcpRequest(pVerifierChannel->m_pMrcpChannel,pMrcpMessage);
}
}
else if(pMrcpMessage->start_line.method_id == VERIFIER_END_SESSION)
{
/* received the response to END-SESSION request */
Terminate();
}
else if(pMrcpMessage->start_line.method_id == VERIFIER_VERIFY)
{
/* received the response to VERIFY request */
if(pMrcpMessage->start_line.request_state == MRCP_REQUEST_STATE_INPROGRESS)
{
VerifierChannel* pVerifierChannel = (VerifierChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pVerifierChannel)
pVerifierChannel->m_pVerificationRequest = GetMrcpMessage();
/* start to stream the speech to Verify */
if(pVerifierChannel)
pVerifierChannel->m_Streaming = true;
}
else
{
/* create and send END-SESSION request */
mrcp_message_t* pMrcpMessage = CreateEndSessionRequest(pMrcpChannel);
if(pMrcpMessage)
{
SendMrcpRequest(pVerifierChannel->m_pMrcpChannel,pMrcpMessage);
}
}
}
else
{
/* received unexpected response */
}
}
else if(pMrcpMessage->start_line.message_type == MRCP_MESSAGE_TYPE_EVENT)
{
if(pMrcpMessage->start_line.method_id == VERIFIER_VERIFICATION_COMPLETE)
{
if(pVerifierChannel)
pVerifierChannel->m_Streaming = false;
VerifierChannel* pVerifierChannel = (VerifierChannel*) mrcp_application_channel_object_get(pMrcpChannel);
if(pVerifierChannel)
pVerifierChannel->m_pVerificationRequest = NULL;
/* create and send END-SESSION request */
mrcp_message_t* pMrcpMessage = CreateEndSessionRequest(pMrcpChannel);
if(pMrcpMessage)
{
SendMrcpRequest(pVerifierChannel->m_pMrcpChannel,pMrcpMessage);
}
}
else if(pMrcpMessage->start_line.method_id == VERIFIER_START_OF_INPUT)
{
/* received start-of-input, do whatever you need here */
}
}
return true;
}
bool VerifierSession::StartVerification(mrcp_channel_t* pMrcpChannel)
{
VerifierChannel* pVerifierChannel = (VerifierChannel*) mrcp_application_channel_object_get(pMrcpChannel);
/* create and send Verification request */
mrcp_message_t* pMrcpMessage = CreateStartSessionRequest(pMrcpChannel);
if(pMrcpMessage)
{
SendMrcpRequest(pVerifierChannel->m_pMrcpChannel,pMrcpMessage);
}
const mpf_codec_descriptor_t* pDescriptor = mrcp_application_source_descriptor_get(pMrcpChannel);
pVerifierChannel->m_pAudioIn = GetAudioIn(pDescriptor,GetSessionPool());
if(!pVerifierChannel->m_pAudioIn)
{
/* no audio input availble, set some estimated time to complete instead */
pVerifierChannel->m_TimeToComplete = 5000; // 5 sec
}
return true;
}
mrcp_message_t* VerifierSession::CreateStartSessionRequest(mrcp_channel_t* pMrcpChannel)
{
mrcp_message_t* pMrcpMessage = CreateMrcpMessage(pMrcpChannel,VERIFIER_START_SESSION);
if(!pMrcpMessage)
return NULL;
mrcp_verifier_header_t* pVerifierHeader;
/* get/allocate verifier header */
pVerifierHeader = (mrcp_verifier_header_t*) mrcp_resource_header_prepare(pMrcpMessage);
if(pVerifierHeader)
{
const VerifierScenario* pScenario = GetScenario();
const char* pRepositoryURI = pScenario->GetRepositoryURI();
if(pRepositoryURI)
{
apt_string_set(&pVerifierHeader->repository_uri,pRepositoryURI);
mrcp_resource_header_property_add(pMrcpMessage,VERIFIER_HEADER_REPOSITORY_URI);
}
const char* pVoiceprintIdentifier = pScenario->GetVoiceprintIdentifier();
if(pVoiceprintIdentifier)
{
apt_string_set(&pVerifierHeader->voiceprint_identifier,pVoiceprintIdentifier);
mrcp_resource_header_property_add(pMrcpMessage,VERIFIER_HEADER_VOICEPRINT_IDENTIFIER);
}
const char* pVerificationMode = pScenario->GetVerificationMode();
if(pVerificationMode)
{
apt_string_set(&pVerifierHeader->verification_mode,pVerificationMode);
mrcp_resource_header_property_add(pMrcpMessage,VERIFIER_HEADER_VERIFICATION_MODE);
}
}
return pMrcpMessage;
}
mrcp_message_t* VerifierSession::CreateEndSessionRequest(mrcp_channel_t* pMrcpChannel)
{
return CreateMrcpMessage(pMrcpChannel,VERIFIER_END_SESSION);
}
mrcp_message_t* VerifierSession::CreateVerificationRequest(mrcp_channel_t* pMrcpChannel)
{
mrcp_message_t* pMrcpMessage = CreateMrcpMessage(pMrcpChannel,VERIFIER_VERIFY);
if(!pMrcpMessage)
return NULL;
mrcp_verifier_header_t* pVerifierHeader;
/* get/allocate verifier header */
pVerifierHeader = (mrcp_verifier_header_t*) mrcp_resource_header_prepare(pMrcpMessage);
if(pVerifierHeader)
{
pVerifierHeader->no_input_timeout = 5000;
mrcp_resource_header_property_add(pMrcpMessage,VERIFIER_HEADER_NO_INPUT_TIMEOUT);
pVerifierHeader->start_input_timers = TRUE;
mrcp_resource_header_property_add(pMrcpMessage,VERIFIER_HEADER_START_INPUT_TIMERS);
}
return pMrcpMessage;
}
FILE* VerifierSession::GetAudioIn(const mpf_codec_descriptor_t* pDescriptor, apr_pool_t* pool) const
{
const VerifierScenario* pScenario = GetScenario();
const char* pVoiceprintIdentifier = pScenario->GetVoiceprintIdentifier();
if(!pVoiceprintIdentifier)
{
apt_log(APT_LOG_MARK,APT_PRIO_WARNING,"No Voiceprint Specified");
return NULL;
}
const char* pFileName = apr_psprintf(pool,"%s-%dkHz.pcm",
pVoiceprintIdentifier,
pDescriptor ? pDescriptor->sampling_rate/1000 : 8);
apt_dir_layout_t* pDirLayout = pScenario->GetDirLayout();
const char* pFilePath = apt_datadir_filepath_get(pDirLayout,pFileName,pool);
if(!pFilePath)
return NULL;
FILE* pFile = fopen(pFilePath,"rb");
if(!pFile)
{
apt_log(APT_LOG_MARK,APT_PRIO_INFO,"Cannot Find [%s]",pFilePath);
return NULL;
}
apt_log(APT_LOG_MARK,APT_PRIO_INFO,"Set [%s] as Speech Source",pFilePath);
return pFile;
}