summaryrefslogtreecommitdiff
path: root/include
diff options
context:
space:
mode:
authorGeorge Joseph <gjoseph@digium.com>2017-09-27 10:44:53 -0600
committerGeorge Joseph <gjoseph@digium.com>2018-04-17 10:30:23 -0600
commit4fb7967c7327fd73a93c587f3eca0564201be049 (patch)
tree0fb763353f2152e6f524f259e8f517685f3e7a9e /include
parent38dae51b788cd7f9f69c88573d6ce769c80f07f0 (diff)
bridge_softmix: Forward TEXT frames
Core bridging and, more specifically, bridge_softmix have been enhanced to relay received frames of type TEXT or TEXT_DATA to all participants in a softmix bridge. res_pjsip_messaging and chan_pjsip have been enhanced to take advantage of this so when res_pjsip_messaging receives an in-dialog MESSAGE message from a user in a conference call, it's relayed to all other participants in the call. res_pjsip_messaging already queues TEXT frames to the channel when it receives an in-dialog MESSAGE from an endpoint and chan_pjsip will send an MESSAGE when it gets a TEXT frame. On a normal point-to-point call, the frames are forwarded between the two correctly. bridge_softmix was not though so messages weren't getting forwarded to conference bridge participants. Even if they were, the bridging code had no way to tell the participants who sent the message so it would look like it came from the bridge itself. * The TEXT frame type doesn't allow storage of any meta data, such as sender, on the frame so a new TEXT_DATA frame type was added that uses the new ast_msg_data structure as its payload. A channel driver can queue a frame of that type when it receives a message from outside. A channel driver can use it for sending messages by implementing the new send_text_data channel tech callback and setting the new AST_CHAN_TP_SEND_TEXT_DATA flag in its tech properties. If set, the bridging/channel core will use it instead of the original send_text callback and it will get the ast_msg_data structure. Channel drivers aren't required to implement this. Even if a TEXT_DATA enabled driver uses it for incoming messages, an outgoing channel driver that doesn't will still have it's send_text callback called with only the message text just as before. * res_pjsip_messaging now creates a TEXT_DATA frame for incoming in-dialog messages and sets the "from" to the display name in the "From" header, or if that's empty, the caller id name from the channel. This allows the chat client user to set a friendly name for the chat. * bridge_softmix now forwards TEXT and TEXT_DATA frames to all participants (except the sender). * A new function "ast_sendtext_data" was added to channel which takes an ast_msg_data structure and calls a channel's send_text_data callback, or if that's not defined, the original send_text callback. * bridge_channel now calls ast_sendtext_data for TEXT_DATA frame types and ast_sendtext for TEXT frame types. * chan_pjsip now uses the "from" name in the ast_msg_data structure (if it exists) to set the "From" header display name on outgoing text messages. Change-Id: Idacf5900bfd5f22ab8cd235aa56dfad090d18489
Diffstat (limited to 'include')
-rw-r--r--include/asterisk/channel.h32
-rw-r--r--include/asterisk/frame.h3
-rw-r--r--include/asterisk/message.h123
3 files changed, 158 insertions, 0 deletions
diff --git a/include/asterisk/channel.h b/include/asterisk/channel.h
index 16f9aa8ae..c865a8a32 100644
--- a/include/asterisk/channel.h
+++ b/include/asterisk/channel.h
@@ -593,6 +593,11 @@ struct ast_assigned_ids {
};
/*!
+ * \brief Forward declaration
+ */
+struct ast_msg_data;
+
+/*!
* \brief
* Structure to describe a channel "technology", ie a channel driver
* See for examples:
@@ -807,6 +812,9 @@ struct ast_channel_tech {
* \retval -1 on error.
*/
int (*pre_call)(struct ast_channel *chan, const char *sub_args);
+
+ /*! \brief Display or transmit text with data*/
+ int (* const send_text_data)(struct ast_channel *chan, struct ast_msg_data *data);
};
/*! Kill the channel channel driver technology descriptor. */
@@ -934,6 +942,10 @@ enum {
* world
*/
AST_CHAN_TP_INTERNAL = (1 << 2),
+ /*!
+ * \brief Channels have this property if they implement send_text_data
+ */
+ AST_CHAN_TP_SEND_TEXT_DATA = (1 << 3),
};
/*! \brief ast_channel flags */
@@ -2134,6 +2146,26 @@ int ast_set_write_format_interleaved_stereo(struct ast_channel *chan, struct ast
int ast_sendtext(struct ast_channel *chan, const char *text);
/*!
+ * \brief Sends text to a channel in an ast_msg_data structure wrapper with ast_sendtext as fallback
+ * \since 13.22.0
+ * \since 15.5.0
+ *
+ * \param chan channel to act upon
+ * \param msg ast_msg_data structure
+ *
+ * \details
+ * Write text to a display on a channel. If the channel driver doesn't support the
+ * send_text_data callback. then the original send_text callback will be used if
+ * available.
+ *
+ * \note The channel does not need to be locked before calling this function.
+ *
+ * \retval 0 on success
+ * \retval -1 on failure
+ */
+int ast_sendtext_data(struct ast_channel *chan, struct ast_msg_data *msg);
+
+/*!
* \brief Receives a text character from a channel
* \param chan channel to act upon
* \param timeout timeout in milliseconds (0 for infinite wait)
diff --git a/include/asterisk/frame.h b/include/asterisk/frame.h
index c3c0f8817..542407ecc 100644
--- a/include/asterisk/frame.h
+++ b/include/asterisk/frame.h
@@ -48,6 +48,7 @@ extern "C" {
* \arg \b DTMF: A DTMF digit, subclass is the digit
* \arg \b IMAGE: Image transport, mostly used in IAX
* \arg \b TEXT: Text messages and character by character (real time text)
+ * \arg \b TEXT_DATA: Text messages in an ast_msg_data structure
* \arg \b HTML: URL's and web pages
* \arg \b MODEM: Modulated data encodings, such as T.38 and V.150
* \arg \b IAX: Private frame type for the IAX protocol
@@ -129,6 +130,8 @@ enum ast_frame_type {
AST_FRAME_BRIDGE_ACTION_SYNC,
/*! RTCP feedback (the subclass will contain the payload type) */
AST_FRAME_RTCP,
+ /*! Text message in an ast_msg_data structure */
+ AST_FRAME_TEXT_DATA,
};
#define AST_FRAME_DTMF AST_FRAME_DTMF_END
diff --git a/include/asterisk/message.h b/include/asterisk/message.h
index ae6533c46..826fa0ac3 100644
--- a/include/asterisk/message.h
+++ b/include/asterisk/message.h
@@ -407,6 +407,129 @@ void ast_msg_var_iterator_destroy(struct ast_msg_var_iterator *iter);
*/
void ast_msg_var_unref_current(struct ast_msg_var_iterator *iter);
+
+/*! \defgroup ast_msg_data Enhanced Messaging
+ * @{
+ * \page Messaging Enhanced Messaging
+ *
+ * The basic messaging framework has a basic drawback... It can only pass
+ * a text string through the core. This causes several issues:
+ * \li Only a content type of text/plain can be passed.
+ * \li If a softmix bridge is used, the original sender identity is lost.
+ *
+ * The Enhanced Messaging framework allows attributes, such as "From", "To"
+ * and "Content-Type" to be attached to the message by the incoming channel
+ * tech which can then be used by the outgoing channel tech to construct
+ * the appropriate technology-specific outgoing message.
+ */
+
+/*!
+ * \brief Structure used to transport an enhanced message through the frame core
+ * \since 13.22.0
+ * \since 15.5.0
+ */
+struct ast_msg_data;
+
+enum ast_msg_data_source_type {
+ AST_MSG_DATA_SOURCE_TYPE_UNKNOWN = 0,
+ AST_MSG_DATA_SOURCE_TYPE_T140,
+ AST_MSG_DATA_SOURCE_TYPE_IN_DIALOG,
+ AST_MSG_DATA_SOURCE_TYPE_OUT_OF_DIALOG,
+ __AST_MSG_DATA_SOURCE_TYPE_LAST,
+};
+
+enum ast_msg_data_attribute_type {
+ AST_MSG_DATA_ATTR_TO = 0,
+ AST_MSG_DATA_ATTR_FROM,
+ AST_MSG_DATA_ATTR_CONTENT_TYPE,
+ AST_MSG_DATA_ATTR_BODY,
+ __AST_MSG_DATA_ATTR_LAST,
+};
+
+struct ast_msg_data_attribute {
+ enum ast_msg_data_attribute_type type;
+ char *value;
+};
+
+/*!
+ * \brief Allocates an ast_msg_data structure.
+ * \since 13.22.0
+ * \since 15.5.0
+ *
+ * \param source The source type of the message
+ * \param attributes A pointer to an array of ast_msg_data_attribute structures
+ * \param count The number of elements in the array
+ *
+ * \return Pointer to msg structure or NULL on allocation failure.
+ * Caller must call ast_free when done.
+ */
+struct ast_msg_data *ast_msg_data_alloc(enum ast_msg_data_source_type source,
+ struct ast_msg_data_attribute attributes[], size_t count);
+
+/*!
+ * \brief Clone an ast_msg_data structure
+ * \since 13.22.0
+ * \since 15.5.0
+ *
+ * \param msg The message to clone
+ *
+ * \return New message structure or NULL if there was an allocation failure.
+ * Caller must call ast_free when done.
+ */
+struct ast_msg_data *ast_msg_data_dup(struct ast_msg_data *msg);
+
+/*!
+ * \brief Get length of the structure
+ * \since 13.22.0
+ * \since 15.5.0
+ *
+ * \param msg Pointer to ast_msg_data structure
+ *
+ * \return The length of the structure itself plus the dynamically allocated attribute buffer.
+ */
+size_t ast_msg_data_get_length(struct ast_msg_data *msg);
+
+/*!
+ * \brief Get "source type" from ast_msg_data
+ * \since 13.22.0
+ * \since 15.5.0
+ *
+ * \param msg Pointer to ast_msg_data structure
+ *
+ * \return The source type field.
+ */
+enum ast_msg_data_source_type ast_msg_data_get_source_type(struct ast_msg_data *msg);
+
+/*!
+ * \brief Get attribute from ast_msg_data
+ * \since 13.22.0
+ * \since 15.5.0
+ *
+ * \param msg Pointer to ast_msg_data structure
+ * \param attribute_type One of ast_msg_data_attribute_type
+ *
+ * \return The attribute or an empty string ("") if the attribute wasn't set.
+ */
+const char *ast_msg_data_get_attribute(struct ast_msg_data *msg,
+ enum ast_msg_data_attribute_type attribute_type);
+
+/*!
+ * \brief Queue an AST_FRAME_TEXT_DATA frame containing an ast_msg_data structure
+ * \since 13.22.0
+ * \since 15.5.0
+ *
+ * \param channel The channel on which to queue the frame
+ * \param msg Pointer to ast_msg_data structure
+ *
+ * \retval -1 Error
+ * \retval 0 Success
+ */
+int ast_msg_data_queue_frame(struct ast_channel *channel, struct ast_msg_data *msg);
+
+/*!
+ * @}
+ */
+
#if defined(__cplusplus) || defined(c_plusplus)
}
#endif