[svn-commits] file: branch group/media_formats r406169 - in /team/group/media_formats: incl...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Wed Jan 22 12:27:24 CST 2014


Author: file
Date: Wed Jan 22 12:27:18 2014
New Revision: 406169

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=406169
Log:
Add the format interface which extends core format logic for codecs.

Modified:
    team/group/media_formats/include/asterisk/codec.h
    team/group/media_formats/include/asterisk/format_ng.h
    team/group/media_formats/main/format_ng.c

Modified: team/group/media_formats/include/asterisk/codec.h
URL: http://svnview.digium.com/svn/asterisk/team/group/media_formats/include/asterisk/codec.h?view=diff&rev=406169&r1=406168&r2=406169
==============================================================================
--- team/group/media_formats/include/asterisk/codec.h (original)
+++ team/group/media_formats/include/asterisk/codec.h Wed Jan 22 12:27:18 2014
@@ -86,6 +86,7 @@
  * allows it to be passed through in frames and configured in channel drivers.
  *
  * \param codec to register
+ * \param mod the module this codec is provided by
  *
  * \retval 0 success
  * \retval -1 failure

Modified: team/group/media_formats/include/asterisk/format_ng.h
URL: http://svnview.digium.com/svn/asterisk/team/group/media_formats/include/asterisk/format_ng.h?view=diff&rev=406169&r1=406168&r2=406169
==============================================================================
--- team/group/media_formats/include/asterisk/format_ng.h (original)
+++ team/group/media_formats/include/asterisk/format_ng.h Wed Jan 22 12:27:18 2014
@@ -99,6 +99,14 @@
 };
 
 /*!
+ * \brief Initialize media format support
+ *
+ * \retval 0 success
+ * \retval -1 failure
+ */
+int ast_format_init(void);
+
+/*!
  * \brief Create a new media format
  *
  * \param codec The codec to use
@@ -166,4 +174,27 @@
  */
 void ast_format_sdp_generate(const struct ast_format *format, unsigned int payload, struct ast_str **str);
 
+/*!
+ * \brief Register a format interface for use with the provided codec
+ *
+ * \param codec The name of codec the interface is applicable to
+ * \param interface A pointer to the interface implementation
+ * \param mod The module this format interface is provided by
+ *
+ * \retval 0 success
+ * \retval -1 failure
+ */
+int __ast_format_interface_register(const char *codec, struct ast_format_interface *interface, struct ast_module *mod);
+
+/*!
+ * \brief Register a format interface for use with the provided codec
+ *
+ * \param codec The name of codec the interface is applicable to
+ * \param interface A pointer to the interface implementation
+ *
+ * \retval 0 success
+ * \retval -1 failure
+ */
+#define ast_format_interface_register(codec, interface) __ast_format_interface_register(codec, interface, ast_module_info->self)
+
 #endif /* _AST_FORMAT_H */

Modified: team/group/media_formats/main/format_ng.c
URL: http://svnview.digium.com/svn/asterisk/team/group/media_formats/main/format_ng.c?view=diff&rev=406169&r1=406168&r2=406169
==============================================================================
--- team/group/media_formats/main/format_ng.c (original)
+++ team/group/media_formats/main/format_ng.c Wed Jan 22 12:27:18 2014
@@ -35,6 +35,114 @@
 #include "asterisk/codec.h"
 #include "asterisk/format_ng.h"
 #include "asterisk/astobj2.h"
+#include "asterisk/strings.h"
+
+/*! \brief Number of buckets to use for format interfaces (should be prime for performance reasons) */
+#define FORMAT_INTERFACE_BUCKETS 53
+
+/*! \brief Structure used when registering a format interface */
+struct format_interface {
+	/*! \brief Pointer to the format interface itself */
+	struct ast_format_interface *interface;
+	/*! \brief Name of the codec the interface is for */
+	char codec[0];
+};
+
+/*! \brief Container for registered format interfaces */
+static struct ao2_container *interfaces;
+
+static int format_interface_hash(const void *obj, int flags)
+{
+	const struct format_interface *format_interface;
+	const char *key;
+
+	switch (flags & OBJ_SEARCH_MASK) {
+	case OBJ_SEARCH_KEY:
+		key = obj;
+		return ast_str_hash(key);
+	case OBJ_SEARCH_OBJECT:
+		format_interface = obj;
+		return ast_str_hash(format_interface->codec);
+	default:
+		/* Hash can only work on something with a full key. */
+		ast_assert(0);
+		return 0;
+	}
+}
+
+static int format_interface_cmp(void *obj, void *arg, int flags)
+{
+	const struct format_interface *left = obj;
+	const struct format_interface *right = arg;
+	const char *right_key = arg;
+	int cmp;
+
+	switch (flags & OBJ_SEARCH_MASK) {
+	case OBJ_SEARCH_OBJECT:
+		cmp = strcmp(left->codec, right->codec);
+		break;
+	case OBJ_SEARCH_KEY:
+		cmp = strcmp(left->codec, right_key);
+		break;
+	case OBJ_SEARCH_PARTIAL_KEY:
+		cmp = strncmp(left->codec, right_key, strlen(right_key));
+		break;
+	default:
+		ast_assert(0);
+		cmp = 0;
+		break;
+	}
+	if (cmp) {
+		return 0;
+	}
+
+	return CMP_MATCH;
+}
+
+int ast_format_init(void)
+{
+	interfaces = ao2_container_alloc_options(AO2_ALLOC_OPT_LOCK_RWLOCK, FORMAT_INTERFACE_BUCKETS, format_interface_hash,
+		format_interface_cmp);
+	if (!interfaces) {
+		return -1;
+	}
+
+	return 0;
+}
+
+/*! \brief Destructor for format interface */
+static void format_interface_destroy(void *obj)
+{
+	struct format_interface *format_interface = obj;
+
+	ao2_cleanup(format_interface->interface);
+}
+
+int __ast_format_interface_register(const char *codec, struct ast_format_interface *interface, struct ast_module *mod)
+{
+	SCOPED_AO2WRLOCK(lock, interfaces);
+	struct format_interface *format_interface;
+
+	format_interface = ao2_find(interfaces, codec, OBJ_SEARCH_KEY);
+	if (format_interface) {
+		ast_log(LOG_ERROR, "A format interface is already present for codec '%s'\n", codec);
+		ao2_ref(format_interface, -1);
+		return -1;
+	}
+
+	format_interface = ao2_alloc(sizeof(*format_interface) + strlen(codec) + 1, format_interface_destroy);
+	if (!format_interface) {
+		return -1;
+	}
+
+	format_interface->interface = interface;
+	ao2_link_flags(interfaces, interface, OBJ_NOLOCK);
+	ao2_ref(format_interface, -1);
+
+	ast_verb(2, "Registered format interface for codec '%s'\n", codec);
+
+	return 0;
+}
 
 /*! \brief Destructor for media formats */
 static void format_destroy(void *obj)
@@ -52,6 +160,7 @@
 struct ast_format *ast_format_create(struct ast_codec *codec)
 {
 	struct ast_format *format;
+	struct format_interface *format_interface;
 
 	format = ao2_alloc(sizeof(*format), format_destroy);
 	if (!format) {
@@ -59,6 +168,12 @@
 	}
 
 	format->codec = ao2_bump(codec);
+
+	format_interface = ao2_find(interfaces, codec->name, OBJ_SEARCH_KEY);
+	if (format_interface) {
+		format->interface = ao2_bump(format_interface->interface);
+		ao2_ref(format_interface, -1);
+	}
 
 	return format;
 }




More information about the svn-commits mailing list