summaryrefslogtreecommitdiff
path: root/main
diff options
context:
space:
mode:
authorMatthew Jordan <mjordan@digium.com>2014-05-30 12:42:57 +0000
committerMatthew Jordan <mjordan@digium.com>2014-05-30 12:42:57 +0000
commit53968c00b34a913e0467200b95add483f79dd3b6 (patch)
tree3e04113a3c4eda1884205df78e9527b2c72cee6a /main
parente9f09ab2bce1e1aa1b619507b45d228bbc49f12c (diff)
TALK_DETECT: A channel function that raises events when talking is detected
This patch adds a new channel function TALK_DETECT that, when set on a channel, causes events indicating the start/stop of talking on a channel to be emitted to both AMI and ARI clients. The function allows setting both the silence threshold (the length of silence after which we decide no one is talking) as well as the talking threshold (the amount of energy that counts as talking). Parameters can be updated on a channel after talk detection has been enabled, and talk detection can be removed at any time. The events raised by the function use a nomenclature similar to existing AMI/ARI events. For AMI: ChannelTalkingStart/ChannelTalkingStop For ARI: ChannelTalkingStarted/ChannelTalkingFinished Review: https://reviewboard.asterisk.org/r/3563/ #ASTERISK-23786 #close Reported by: Matt Jordan ........ Merged revisions 414934 from http://svn.asterisk.org/svn/asterisk/branches/12 git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@414935 65c4cc65-6c06-0410-ace0-fbb531ad65f3
Diffstat (limited to 'main')
-rw-r--r--main/audiohook.c6
-rw-r--r--main/stasis_channels.c92
2 files changed, 94 insertions, 4 deletions
diff --git a/main/audiohook.c b/main/audiohook.c
index 90802b6cd..4dc7c136b 100644
--- a/main/audiohook.c
+++ b/main/audiohook.c
@@ -874,17 +874,15 @@ static struct ast_frame *audio_audiohook_write_list(struct ast_channel *chan, st
}
audiohook_set_internal_rate(audiohook, audiohook_list->list_internal_samp_rate, 1);
/* Feed in frame to manipulation. */
- if (audiohook->manipulate_callback(audiohook, chan, middle_frame, direction)) {
- /* XXX IGNORE FAILURE */
-
+ if (!audiohook->manipulate_callback(audiohook, chan, middle_frame, direction)) {
/* If the manipulation fails then the frame will be returned in its original state.
* Since there are potentially more manipulator callbacks in the list, no action should
* be taken here to exit early. */
+ middle_frame_manipulated = 1;
}
ast_audiohook_unlock(audiohook);
}
AST_LIST_TRAVERSE_SAFE_END;
- middle_frame_manipulated = 1;
}
/* ---Part_3: Decide what to do with the end_frame (whether to transcode or not) */
diff --git a/main/stasis_channels.c b/main/stasis_channels.c
index 49fd3f995..f38edb0e1 100644
--- a/main/stasis_channels.c
+++ b/main/stasis_channels.c
@@ -85,6 +85,34 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
</see-also>
</managerEventInstance>
</managerEvent>
+ <managerEvent language="en_US" name="ChannelTalkingStart">
+ <managerEventInstance class="EVENT_FLAG_CLASS">
+ <synopsis>Raised when talking is detected on a channel.</synopsis>
+ <syntax>
+ <channel_snapshot/>
+ </syntax>
+ <see-also>
+ <ref type="function">TALK_DETECT</ref>
+ <ref type="managerEvent">ChannelTalkingStop</ref>
+ </see-also>
+ </managerEventInstance>
+ </managerEvent>
+ <managerEvent language="en_US" name="ChannelTalkingStop">
+ <managerEventInstance class="EVENT_FLAG_CLASS">
+ <synopsis>Raised when talking is no longer detected on a channel.</synopsis>
+ <syntax>
+ <channel_snapshot/>
+ <parameter name="Duration">
+ <para>The length in time, in milliseconds, that talking was
+ detected on the channel.</para>
+ </parameter>
+ </syntax>
+ <see-also>
+ <ref type="function">TALK_DETECT</ref>
+ <ref type="managerEvent">ChannelTalkingStart</ref>
+ </see-also>
+ </managerEventInstance>
+ </managerEvent>
***/
#define NUM_MULTI_CHANNEL_BLOB_BUCKETS 7
@@ -974,6 +1002,58 @@ static struct ast_json *dial_to_json(
return json;
}
+static struct ast_manager_event_blob *talking_start_to_ami(struct stasis_message *msg)
+{
+ struct ast_str *channel_string;
+ struct ast_channel_blob *obj = stasis_message_data(msg);
+ struct ast_manager_event_blob *blob;
+
+ channel_string = ast_manager_build_channel_state_string(obj->snapshot);
+ if (!channel_string) {
+ return NULL;
+ }
+
+ blob = ast_manager_event_blob_create(EVENT_FLAG_CALL, "ChannelTalkingStart",
+ "%s", ast_str_buffer(channel_string));
+ ast_free(channel_string);
+
+ return blob;
+}
+
+static struct ast_json *talking_start_to_json(struct stasis_message *message,
+ const struct stasis_message_sanitizer *sanitize)
+{
+ return channel_blob_to_json(message, "ChannelTalkingStarted", sanitize);
+}
+
+static struct ast_manager_event_blob *talking_stop_to_ami(struct stasis_message *msg)
+{
+ struct ast_str *channel_string;
+ struct ast_channel_blob *obj = stasis_message_data(msg);
+ int duration = ast_json_integer_get(ast_json_object_get(obj->blob, "duration"));
+ struct ast_manager_event_blob *blob;
+
+ channel_string = ast_manager_build_channel_state_string(obj->snapshot);
+ if (!channel_string) {
+ return NULL;
+ }
+
+ blob = ast_manager_event_blob_create(EVENT_FLAG_CALL, "ChannelTalkingStop",
+ "%s"
+ "Duration: %d\r\n",
+ ast_str_buffer(channel_string),
+ duration);
+ ast_free(channel_string);
+
+ return blob;
+}
+
+static struct ast_json *talking_stop_to_json(struct stasis_message *message,
+ const struct stasis_message_sanitizer *sanitize)
+{
+ return channel_blob_to_json(message, "ChannelTalkingFinished", sanitize);
+}
+
/*!
* @{ \brief Define channel message types.
*/
@@ -1008,6 +1088,14 @@ STASIS_MESSAGE_TYPE_DEFN(ast_channel_agent_login_type,
STASIS_MESSAGE_TYPE_DEFN(ast_channel_agent_logoff_type,
.to_ami = agent_logoff_to_ami,
);
+STASIS_MESSAGE_TYPE_DEFN(ast_channel_talking_start,
+ .to_ami = talking_start_to_ami,
+ .to_json = talking_start_to_json,
+ );
+STASIS_MESSAGE_TYPE_DEFN(ast_channel_talking_stop,
+ .to_ami = talking_stop_to_ami,
+ .to_json = talking_stop_to_json,
+ );
/*! @} */
@@ -1038,6 +1126,8 @@ static void stasis_channels_cleanup(void)
STASIS_MESSAGE_TYPE_CLEANUP(ast_channel_monitor_stop_type);
STASIS_MESSAGE_TYPE_CLEANUP(ast_channel_agent_login_type);
STASIS_MESSAGE_TYPE_CLEANUP(ast_channel_agent_logoff_type);
+ STASIS_MESSAGE_TYPE_CLEANUP(ast_channel_talking_start);
+ STASIS_MESSAGE_TYPE_CLEANUP(ast_channel_talking_stop);
}
int ast_stasis_channels_init(void)
@@ -1084,6 +1174,8 @@ int ast_stasis_channels_init(void)
res |= STASIS_MESSAGE_TYPE_INIT(ast_channel_moh_stop_type);
res |= STASIS_MESSAGE_TYPE_INIT(ast_channel_monitor_start_type);
res |= STASIS_MESSAGE_TYPE_INIT(ast_channel_monitor_stop_type);
+ res |= STASIS_MESSAGE_TYPE_INIT(ast_channel_talking_start);
+ res |= STASIS_MESSAGE_TYPE_INIT(ast_channel_talking_stop);
return res;
}