[svn-commits] kmoore: branch group/media_formats-reviewed-trunk r418615 - in /team/group/me...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Mon Jul 14 22:48:33 CDT 2014


Author: kmoore
Date: Mon Jul 14 22:48:26 2014
New Revision: 418615

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=418615
Log:
media formats: Correct PJSIP outbound codec offers

This fixes the codecs that chan_pjsip offers on outbound call attempts.
chan_pjsip will now offer the endpoint-configured codec preferences
with requested formats replacing equivalent configured formats.
Previously, chan_pjsip would offer the requested formats in addition to
the configured codecs while trunk only currently offers the requested
codecs if any are available. This does not affect the operation of
PJSIP_MEDIA_OFFER() dialplan function.

Review: https://reviewboard.asterisk.org/r/3784/

Modified:
    team/group/media_formats-reviewed-trunk/include/asterisk/format_cap.h
    team/group/media_formats-reviewed-trunk/main/format_cap.c
    team/group/media_formats-reviewed-trunk/tests/test_format_cap.c

Modified: team/group/media_formats-reviewed-trunk/include/asterisk/format_cap.h
URL: http://svnview.digium.com/svn/asterisk/team/group/media_formats-reviewed-trunk/include/asterisk/format_cap.h?view=diff&rev=418615&r1=418614&r2=418615
==============================================================================
--- team/group/media_formats-reviewed-trunk/include/asterisk/format_cap.h (original)
+++ team/group/media_formats-reviewed-trunk/include/asterisk/format_cap.h Mon Jul 14 22:48:26 2014
@@ -149,6 +149,18 @@
 int ast_format_cap_append_from_cap(struct ast_format_cap *dst, const struct ast_format_cap *src, enum ast_media_type type);
 
 /*!
+ * \brief Replace the formats of provided type in dst with equivalent formats from src
+ *
+ * \param dst The destination capabilities structure
+ * \param src The source capabilities structure
+ * \param type The type of formats to replace.
+ *
+ * \note If AST_MEDIA_TYPE_UNKNOWN is passed as the type all known codecs will be replaced.
+ * \note Formats present in src but not dst will not be appended to dst.
+ */
+void ast_format_cap_replace_from_cap(struct ast_format_cap *dst, const struct ast_format_cap *src, enum ast_media_type type);
+
+/*!
  * \brief Parse an "allow" or "deny" list and modify a format capabilities structure accordingly
  *
  * \param cap The capabilities structure to modify

Modified: team/group/media_formats-reviewed-trunk/main/format_cap.c
URL: http://svnview.digium.com/svn/asterisk/team/group/media_formats-reviewed-trunk/main/format_cap.c?view=diff&rev=418615&r1=418614&r2=418615
==============================================================================
--- team/group/media_formats-reviewed-trunk/main/format_cap.c (original)
+++ team/group/media_formats-reviewed-trunk/main/format_cap.c Mon Jul 14 22:48:26 2014
@@ -278,6 +278,40 @@
 	}
 
 	return res;
+}
+
+static int format_cap_replace(struct ast_format_cap *cap, struct ast_format *format, unsigned int framing)
+{
+	struct format_cap_framed *framed;
+	int i;
+
+	ast_assert(format != NULL);
+
+	for (i = 0; i < AST_VECTOR_SIZE(&cap->preference_order); i++) {
+		framed = AST_VECTOR_GET(&cap->preference_order, i);
+
+		if (ast_format_get_codec_id(format) == ast_format_get_codec_id(framed->format)) {
+			ao2_t_replace(framed->format, format, "replacing with new format");
+			framed->framing = framing;
+			return 0;
+		}
+	}
+
+	return -1;
+}
+
+void ast_format_cap_replace_from_cap(struct ast_format_cap *dst, const struct ast_format_cap *src,
+	enum ast_media_type type)
+{
+	int idx;
+
+	for (idx = 0; (idx < AST_VECTOR_SIZE(&src->preference_order)); ++idx) {
+		struct format_cap_framed *framed = AST_VECTOR_GET(&src->preference_order, idx);
+
+		if (type == AST_MEDIA_TYPE_UNKNOWN || ast_format_get_type(framed->format) == type) {
+			format_cap_replace(dst, framed->format, framed->framing);
+		}
+	}
 }
 
 int ast_format_cap_update_by_allow_disallow(struct ast_format_cap *cap, const char *list, int allowing)

Modified: team/group/media_formats-reviewed-trunk/tests/test_format_cap.c
URL: http://svnview.digium.com/svn/asterisk/team/group/media_formats-reviewed-trunk/tests/test_format_cap.c?view=diff&rev=418615&r1=418614&r2=418615
==============================================================================
--- team/group/media_formats-reviewed-trunk/tests/test_format_cap.c (original)
+++ team/group/media_formats-reviewed-trunk/tests/test_format_cap.c Mon Jul 14 22:48:26 2014
@@ -36,6 +36,7 @@
 #include "asterisk/test.h"
 #include "asterisk/module.h"
 #include "asterisk/codec.h"
+#include "asterisk/frame.h"
 #include "asterisk/format.h"
 #include "asterisk/format_cap.h"
 
@@ -106,7 +107,7 @@
 		ast_test_status_update(test, "Could not add newly created format to capabilities structure\n");
 		return AST_TEST_FAIL;
 	} else if (ast_format_cap_count(caps) != 1) {
-		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zd\n",
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zu\n",
 			ast_format_cap_count(caps));
 		return AST_TEST_FAIL;
 	}
@@ -184,7 +185,7 @@
 		ast_test_status_update(test, "Could not add newly created alaw format to capabilities structure\n");
 		return AST_TEST_FAIL;
 	} else if (ast_format_cap_count(caps) != 2) {
-		ast_test_status_update(test, "Number of formats in capabilities structure should be 2 but is %zd\n",
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 2 but is %zu\n",
 			ast_format_cap_count(caps));
 		return AST_TEST_FAIL;
 	}
@@ -340,7 +341,7 @@
 		ast_test_status_update(test, "Could not add newly created format to capabilities structure\n");
 		return AST_TEST_FAIL;
 	} else if (ast_format_cap_count(caps) != 1) {
-		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zd\n",
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zu\n",
 			ast_format_cap_count(caps));
 		return AST_TEST_FAIL;
 	}
@@ -350,7 +351,7 @@
 		ast_test_status_update(test, "Adding of duplicate format to capabilities structure failed\n");
 		return AST_TEST_FAIL;
 	} else if (ast_format_cap_count(caps) != 1) {
-		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zd\n",
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zu\n",
 			ast_format_cap_count(caps));
 		return AST_TEST_FAIL;
 	}
@@ -359,7 +360,7 @@
 		ast_test_status_update(test, "Adding of duplicate named format to capabilities structure failed\n");
 		return AST_TEST_FAIL;
 	} else if (ast_format_cap_count(caps) != 1) {
-		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zd\n",
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zu\n",
 			ast_format_cap_count(caps));
 		return AST_TEST_FAIL;
 	}
@@ -611,7 +612,7 @@
 		ast_test_status_update(test, "Successfully removed a format twice from the capabilities structure\n");
 		return AST_TEST_FAIL;
 	} else if (ast_format_cap_count(caps)) {
-		ast_test_status_update(test, "Capabilities structure should be empty but instead it contains '%zd' formats\n",
+		ast_test_status_update(test, "Capabilities structure should be empty but instead it contains '%zu' formats\n",
 			ast_format_cap_count(caps));
 		return AST_TEST_FAIL;
 	}
@@ -680,7 +681,7 @@
 		ast_test_status_update(test, "Could not remove the ulaw format we just added to capabilities structure\n");
 		return AST_TEST_FAIL;
 	} else if (ast_format_cap_count(caps) != 1) {
-		ast_test_status_update(test, "Capabilities structure should contain 1 format but it contains '%zd'\n",
+		ast_test_status_update(test, "Capabilities structure should contain 1 format but it contains '%zu'\n",
 			ast_format_cap_count(caps));
 		return AST_TEST_FAIL;
 	}
@@ -1261,6 +1262,164 @@
 
 	best_format = ast_format_cap_get_best_by_type(caps, AST_MEDIA_TYPE_TEXT);
 	ast_test_validate(test, best_format == NULL);
+
+	return AST_TEST_PASS;
+}
+
+static int test_law_samples(struct ast_frame *frame)
+{
+	return frame->datalen;
+}
+
+static int test_law_length(unsigned int samples)
+{
+	return samples;
+}
+
+static struct ast_codec test_law = {
+	.name = "test_law",
+	.description = "format cap unit test codec",
+	.type = AST_MEDIA_TYPE_AUDIO,
+	.sample_rate = 8000,
+	.minimum_ms = 10,
+	.maximum_ms = 150,
+	.default_ms = 20,
+	.samples_count = test_law_samples,
+	.get_length = test_law_length,
+	.smooth = 1,
+};
+
+static enum ast_format_cmp_res test_law_cmp(const struct ast_format *format1, const struct ast_format *format2)
+{
+	ast_log(LOG_ERROR, "Comparing format1 %p and format2 %p\n", format1, format2);
+	return format1 == format2 ? AST_FORMAT_CMP_EQUAL : AST_FORMAT_CMP_NOT_EQUAL;
+}
+
+static void test_law_destroy(struct ast_format *format)
+{
+}
+
+static int test_law_clone(const struct ast_format *src, struct ast_format *dst)
+{
+	return 0;
+}
+
+static struct ast_format_interface test_law_interface = {
+	.format_cmp = test_law_cmp,
+	.format_clone = test_law_clone,
+	.format_destroy = test_law_destroy,
+};
+
+AST_TEST_DEFINE(format_cap_replace_from_cap)
+{
+	RAII_VAR(struct ast_format_cap *, caps, NULL, ao2_cleanup);
+	RAII_VAR(struct ast_format_cap *, replace_caps, NULL, ao2_cleanup);
+	RAII_VAR(struct ast_format_cap *, result_caps, NULL, ao2_cleanup);
+	RAII_VAR(struct ast_codec *, ulaw, NULL, ao2_cleanup);
+	RAII_VAR(struct ast_format *, ulaw_format, NULL, ao2_cleanup);
+	RAII_VAR(struct ast_format *, ulaw_format_variant, NULL, ao2_cleanup);
+	RAII_VAR(struct ast_codec *, alaw, NULL, ao2_cleanup);
+	RAII_VAR(struct ast_format *, alaw_format, NULL, ao2_cleanup);
+
+	switch (cmd) {
+	case TEST_INIT:
+		info->name = __PRETTY_FUNCTION__;
+		info->category = "/main/format_cap/";
+		info->summary = "format capabilities adding unit test";
+		info->description =
+			"Test that adding multiple formats to a format capabilities structure succeeds";
+		return AST_TEST_NOT_RUN;
+	case TEST_EXECUTE:
+		break;
+	}
+
+	caps = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
+	replace_caps = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
+	result_caps = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
+	if (!caps || !replace_caps || !result_caps) {
+		ast_test_status_update(test, "Could not allocate an empty format capabilities structure\n");
+		return AST_TEST_FAIL;
+	}
+
+	ulaw = ast_codec_get("test_law", AST_MEDIA_TYPE_AUDIO, 8000);
+	if (!ulaw) {
+		ast_test_status_update(test, "Could not retrieve test_law codec\n");
+		return AST_TEST_FAIL;
+	}
+
+	ulaw_format = ast_format_create(ulaw);
+	if (!ulaw_format) {
+		ast_test_status_update(test, "Could not create ulaw format using built-in codec\n");
+		return AST_TEST_FAIL;
+	}
+
+	ulaw_format_variant = ast_format_create(ulaw);
+	if (!ulaw_format_variant) {
+		ast_test_status_update(test, "Could not create ulaw format variant using built-in codec\n");
+		return AST_TEST_FAIL;
+	}
+
+	alaw = ast_codec_get("alaw", AST_MEDIA_TYPE_AUDIO, 8000);
+	if (!alaw) {
+		ast_test_status_update(test, "Could not retrieve built-in alaw codec\n");
+		return AST_TEST_FAIL;
+	}
+
+	alaw_format = ast_format_create(alaw);
+	if (!alaw_format) {
+		ast_test_status_update(test, "Could not create alaw format using built-in codec\n");
+		return AST_TEST_FAIL;
+	}
+
+	/* fill caps with ulaw and alaw */
+	if (ast_format_cap_append(caps, ulaw_format, 42)) {
+		ast_test_status_update(test, "Could not add ulaw format to capabilities structure\n");
+		return AST_TEST_FAIL;
+	}
+	if (ast_format_cap_append(caps, alaw_format, 84)) {
+		ast_test_status_update(test, "Could not add alaw format to capabilities structure\n");
+		return AST_TEST_FAIL;
+	}
+	if (ast_format_cap_count(caps) != 2) {
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 2 but is %zu\n",
+			ast_format_cap_count(caps));
+		return AST_TEST_FAIL;
+	}
+
+	/* fill replace_caps with the ulaw variant */
+	if (ast_format_cap_append(replace_caps, ulaw_format_variant, 42)) {
+		ast_test_status_update(test, "Could not add ulaw format to capabilities structure\n");
+		return AST_TEST_FAIL;
+	}
+	if (ast_format_cap_count(replace_caps) != 1) {
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 1 but is %zu\n",
+			ast_format_cap_count(replace_caps));
+		return AST_TEST_FAIL;
+	}
+
+	/* fill result_caps with ulaw_variant and alaw */
+	if (ast_format_cap_append(result_caps, ulaw_format_variant, 42)) {
+		ast_test_status_update(test, "Could not add ulaw variant to capabilities structure\n");
+		return AST_TEST_FAIL;
+	}
+	if (ast_format_cap_append(result_caps, alaw_format, 84)) {
+		ast_test_status_update(test, "Could not add alaw format to capabilities structure\n");
+		return AST_TEST_FAIL;
+	}
+	if (ast_format_cap_count(result_caps) != 2) {
+		ast_test_status_update(test, "Number of formats in capabilities structure should be 2 but is %zu\n",
+			ast_format_cap_count(result_caps));
+		return AST_TEST_FAIL;
+	}
+
+	/* replace caps formats from replace_caps */
+	ast_format_cap_replace_from_cap(caps, replace_caps, AST_MEDIA_TYPE_UNKNOWN);
+
+	/* compare result_caps with caps */
+	if (!ast_format_cap_identical(caps, result_caps)) {
+		ast_test_status_update(test, "Actual and expected result caps differ\n");
+		return AST_TEST_FAIL;
+	}
 
 	return AST_TEST_PASS;
 }
@@ -1286,6 +1445,7 @@
 	AST_TEST_UNREGISTER(format_cap_get_compatible);
 	AST_TEST_UNREGISTER(format_cap_iscompatible);
 	AST_TEST_UNREGISTER(format_cap_best_by_type);
+	AST_TEST_UNREGISTER(format_cap_replace_from_cap);
 	return 0;
 }
 
@@ -1310,6 +1470,9 @@
 	AST_TEST_REGISTER(format_cap_get_compatible);
 	AST_TEST_REGISTER(format_cap_iscompatible);
 	AST_TEST_REGISTER(format_cap_best_by_type);
+	AST_TEST_REGISTER(format_cap_replace_from_cap);
+	ast_codec_register(&test_law);
+	ast_format_interface_register("test_law", &test_law_interface);
 	return AST_MODULE_LOAD_SUCCESS;
 }
 




More information about the svn-commits mailing list