[asterisk-commits] rmudgett: branch rmudgett/ao2_red_black r371821 - in /team/rmudgett/ao2_red_b...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Tue Aug 28 14:59:51 CDT 2012


Author: rmudgett
Date: Tue Aug 28 14:59:47 2012
New Revision: 371821

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=371821
Log:
Make ao2_container_stats() useable by the unit test framework.

Modified:
    team/rmudgett/ao2_red_black/include/asterisk/astobj2.h
    team/rmudgett/ao2_red_black/include/asterisk/test.h
    team/rmudgett/ao2_red_black/main/astobj2.c
    team/rmudgett/ao2_red_black/main/test.c
    team/rmudgett/ao2_red_black/tests/test_astobj2.c

Modified: team/rmudgett/ao2_red_black/include/asterisk/astobj2.h
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/ao2_red_black/include/asterisk/astobj2.h?view=diff&rev=371821&r1=371820&r2=371821
==============================================================================
--- team/rmudgett/ao2_red_black/include/asterisk/astobj2.h (original)
+++ team/rmudgett/ao2_red_black/include/asterisk/astobj2.h Tue Aug 28 14:59:47 2012
@@ -1304,16 +1304,29 @@
 #endif
 
 /*!
+ * \brief Print output.
+ * \since 12.0.0
+ *
+ * \param where User data pointer needed to determine where to put output.
+ * \param fmt printf type format string.
+ *
+ * \return Nothing
+ */
+typedef void (ao2_prnt_fn)(void *where, const char *fmt, ...) __attribute__((format(printf, 2, 3)));
+
+/*!
  * \brief Display statistics of the specified container.
  * \since 12.0.0
  *
  * \param self Container to display statistics.
- * \param fd File descriptor to send output.
+ * \param flags OBJ_NOLOCK if a lock is already held on the container.
+ * \param name Container name.  (NULL if anonymous)
+ * \param where User data needed by prnt to determine where to put output.
  * \param prnt Print output callback function to use.
  *
  * \return Nothing
  */
-void ao2_container_stats(struct ao2_container *self, int fd, void (*prnt)(int fd, const char *fmt, ...) __attribute__((format(printf, 2, 3))));
+void ao2_container_stats(struct ao2_container *self, enum search_flags flags, const char *name, void *where, ao2_prnt_fn *prnt);
 
 /*!
  * \brief Perform an integrity check on the specified container.

Modified: team/rmudgett/ao2_red_black/include/asterisk/test.h
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/ao2_red_black/include/asterisk/test.h?view=diff&rev=371821&r1=371820&r2=371821
==============================================================================
--- team/rmudgett/ao2_red_black/include/asterisk/test.h (original)
+++ team/rmudgett/ao2_red_black/include/asterisk/test.h Tue Aug 28 14:59:47 2012
@@ -127,6 +127,7 @@
 #define AST_TEST_REGISTER(cb)
 #define AST_TEST_UNREGISTER(cb)
 #define ast_test_status_update(a,b,c...)
+#define ast_test_debug(test, fmt, ...)	ast_cli		/* Dummy function that should not be called. */
 
 #endif
 
@@ -256,6 +257,17 @@
 int ast_test_register(ast_test_cb_t *cb);
 
 /*!
+ * \brief Unit test debug output.
+ * \since 12.0.0
+ *
+ * \param test Unit test control structure.
+ * \param fmt printf type format string.
+ *
+ * \return Nothing
+ */
+void ast_test_debug(struct ast_test *test, const char *fmt, ...) __attribute__((format(printf, 2, 3)));
+
+/*!
  * \brief update test's status during testing.
  *
  * \param test currently executing test

Modified: team/rmudgett/ao2_red_black/main/astobj2.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/ao2_red_black/main/astobj2.c?view=diff&rev=371821&r1=371820&r2=371821
==============================================================================
--- team/rmudgett/ao2_red_black/main/astobj2.c (original)
+++ team/rmudgett/ao2_red_black/main/astobj2.c Tue Aug 28 14:59:47 2012
@@ -893,14 +893,14 @@
  * \brief Display statistics of the specified container.
  *
  * \param self Container to display statistics.
- * \param fd File descriptor to send output.
+ * \param where User data needed by prnt to determine where to put output.
  * \param prnt Print output callback function to use.
  *
  * \note The container is already locked for reading.
  *
  * \return Nothing
  */
-typedef void (*ao2_container_statistics)(struct ao2_container *self, int fd, void (*prnt)(int fd, const char *fmt, ...) __attribute__((format(printf, 2, 3))));
+typedef void (*ao2_container_statistics)(struct ao2_container *self, void *where, ao2_prnt_fn *prnt);
 
 /*!
  * \brief Perform an integrity check on the specified container.
@@ -1807,19 +1807,24 @@
 	return clone;
 }
 
-void ao2_container_stats(struct ao2_container *self, int fd, void (*prnt)(int fd, const char *fmt, ...) __attribute__((format(printf, 2, 3))))
+void ao2_container_stats(struct ao2_container *self, enum search_flags flags, const char *name, void *where, ao2_prnt_fn *prnt)
 {
 	if (!INTERNAL_OBJ(self) || !self->v_table) {
-		prnt(fd, "Invalid container\n");
+		prnt(where, "Invalid container\n");
 		ast_assert(0);
 		return;
 	}
 
-	ao2_rdlock(self);
-	prnt(fd, "Number of objects: %d\n", self->elements);
+	if (!(flags & OBJ_NOLOCK)) {
+		ao2_rdlock(self);
+	}
+	if (name) {
+		prnt(where, "Container name: %s\n", name);
+	}
+	prnt(where, "Number of objects: %d\n", self->elements);
 #if defined(AST_DEVMODE)
-	prnt(fd, "Number of nodes: %d\n", self->nodes);
-	prnt(fd, "Number of empty nodes: %d\n", self->nodes - self->elements);
+	prnt(where, "Number of nodes: %d\n", self->nodes);
+	prnt(where, "Number of empty nodes: %d\n", self->nodes - self->elements);
 	/*
 	 * XXX
 	 * If the max_empty_nodes count gets out of single digits you
@@ -1829,12 +1834,14 @@
 	 * Empty nodes do not harm the container but they do make
 	 * container operations less efficient.
 	 */
-	prnt(fd, "Maximum empty nodes: %d\n", self->max_empty_nodes);
+	prnt(where, "Maximum empty nodes: %d\n", self->max_empty_nodes);
 	if (self->v_table->stats) {
-		self->v_table->stats(self, fd, prnt);
+		self->v_table->stats(self, where, prnt);
 	}
 #endif	/* defined(AST_DEVMODE) */
-	ao2_unlock(self);
+	if (!(flags & OBJ_NOLOCK)) {
+		ao2_unlock(self);
+	}
 }
 
 int ao2_container_check(struct ao2_container *self, enum search_flags flags)
@@ -2761,14 +2768,14 @@
  * \since 12.0.0
  *
  * \param self Container to display statistics.
- * \param fd File descriptor to send output.
+ * \param where User data needed by prnt to determine where to put output.
  * \param prnt Print output callback function to use.
  *
  * \note The container is already locked for reading.
  *
  * \return Nothing
  */
-static void hash_ao2_stats(struct ao2_container_hash *self, int fd, void (*prnt)(int fd, const char *fmt, ...) __attribute__((format(printf, 2, 3))))
+static void hash_ao2_stats(struct ao2_container_hash *self, void *where, ao2_prnt_fn *prnt)
 {
 #define FORMAT  "%10.10s %10.10s %10.10s\n"
 #define FORMAT2 "%10d %10d %10d\n"
@@ -2776,17 +2783,17 @@
 	int bucket;
 	int suppressed_buckets = 0;
 
-	prnt(fd, "Number of buckets: %d\n\n", self->n_buckets);
-
-	prnt(fd, FORMAT, "Bucket", "Objects", "Max");
+	prnt(where, "Number of buckets: %d\n\n", self->n_buckets);
+
+	prnt(where, FORMAT, "Bucket", "Objects", "Max");
 	for (bucket = 0; bucket < self->n_buckets; ++bucket) {
 		if (self->buckets[bucket].max_elements) {
-			prnt(fd, FORMAT2, bucket, self->buckets[bucket].elements,
+			prnt(where, FORMAT2, bucket, self->buckets[bucket].elements,
 				self->buckets[bucket].max_elements);
 			suppressed_buckets = 0;
 		} else if (!suppressed_buckets) {
 			suppressed_buckets = 1;
-			prnt(fd, "...\n");
+			prnt(where, "...\n");
 		}
 	}
 
@@ -4768,36 +4775,36 @@
  * \since 12.0.0
  *
  * \param self Container to display statistics.
- * \param fd File descriptor to send output.
+ * \param where User data needed by prnt to determine where to put output.
  * \param prnt Print output callback function to use.
  *
  * \note The container is already locked for reading.
  *
  * \return Nothing
  */
-static void rb_ao2_stats(struct ao2_container_rbtree *self, int fd, void (*prnt)(int fd, const char *fmt, ...) __attribute__((format(printf, 2, 3))))
+static void rb_ao2_stats(struct ao2_container_rbtree *self, void *where, ao2_prnt_fn *prnt)
 {
 	int idx;
 
 	for (idx = 0; idx < ARRAY_LEN(self->stats.fixup_insert_left); ++idx) {
-		prnt(fd, "Number of left insert fixups case %d: %d\n", idx + 1,
+		prnt(where, "Number of left insert fixups case %d: %d\n", idx + 1,
 			self->stats.fixup_insert_left[idx]);
 	}
 	for (idx = 0; idx < ARRAY_LEN(self->stats.fixup_insert_right); ++idx) {
-		prnt(fd, "Number of right insert fixups case %d: %d\n", idx + 1,
+		prnt(where, "Number of right insert fixups case %d: %d\n", idx + 1,
 			self->stats.fixup_insert_right[idx]);
 	}
 
 	for (idx = 0; idx < ARRAY_LEN(self->stats.delete_children); ++idx) {
-		prnt(fd, "Number of nodes deleted with %d children: %d\n", idx,
+		prnt(where, "Number of nodes deleted with %d children: %d\n", idx,
 			self->stats.delete_children[idx]);
 	}
 	for (idx = 0; idx < ARRAY_LEN(self->stats.fixup_delete_left); ++idx) {
-		prnt(fd, "Number of left delete fixups case %d: %d\n", idx + 1,
+		prnt(where, "Number of left delete fixups case %d: %d\n", idx + 1,
 			self->stats.fixup_delete_left[idx]);
 	}
 	for (idx = 0; idx < ARRAY_LEN(self->stats.fixup_delete_right); ++idx) {
-		prnt(fd, "Number of right delete fixups case %d: %d\n", idx + 1,
+		prnt(where, "Number of right delete fixups case %d: %d\n", idx + 1,
 			self->stats.fixup_delete_right[idx]);
 	}
 }
@@ -5362,6 +5369,40 @@
 #endif	/* defined(AST_DEVMODE) */
 
 #if defined(AST_DEVMODE)
+AST_THREADSTORAGE(ao2_out_buf);
+
+/*!
+ * \brief Print CLI output.
+ * \since 12.0.0
+ *
+ * \param where User data pointer needed to determine where to put output.
+ * \param fmt printf type format string.
+ *
+ * \return Nothing
+ */
+static void cli_output(void *where, const char *fmt, ...) __attribute__((format(printf, 2, 3)));
+static void cli_output(void *where, const char *fmt, ...)
+{
+	int res;
+	struct ast_str *buf;
+	va_list ap;
+
+	buf = ast_str_thread_get(&ao2_out_buf, 256);
+	if (!buf) {
+		return;
+	}
+
+	va_start(ap, fmt);
+	res = ast_str_set_va(&buf, 0, fmt, ap);
+	va_end(ap);
+
+	if (res != AST_DYNSTR_BUILD_FAILED) {
+		ast_cli(*(int *) where, "%s", ast_str_buffer(buf));
+	}
+}
+#endif	/* defined(AST_DEVMODE) */
+
+#if defined(AST_DEVMODE)
 /*! \brief Show container statistics - CLI command */
 static char *handle_cli_astobj2_container_stats(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
 {
@@ -5386,7 +5427,7 @@
 	name = a->argv[3];
 	reg = ao2_find(reg_containers, name, OBJ_KEY);
 	if (reg) {
-		ao2_container_stats(reg->registered, a->fd, ast_cli);
+		ao2_container_stats(reg->registered, 0, name, (void *) &a->fd, cli_output);
 		ao2_ref(reg, -1);
 	} else {
 		ast_cli(a->fd, "Container '%s' not found.\n", name);

Modified: team/rmudgett/ao2_red_black/main/test.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/ao2_red_black/main/test.c?view=diff&rev=371821&r1=371820&r2=371821
==============================================================================
--- team/rmudgett/ao2_red_black/main/test.c (original)
+++ team/rmudgett/ao2_red_black/main/test.c Tue Aug 28 14:59:47 2012
@@ -100,6 +100,27 @@
 static struct ast_test *test_remove(ast_test_cb_t *cb);
 static int test_cat_cmp(const char *cat1, const char *cat2);
 
+void ast_test_debug(struct ast_test *test, const char *fmt, ...)
+{
+	struct ast_str *buf = NULL;
+	va_list ap;
+
+	buf = ast_str_create(128);
+	if (!buf) {
+		return;
+	}
+
+	va_start(ap, fmt);
+	ast_str_set_va(&buf, 0, fmt, ap);
+	va_end(ap);
+
+	if (test->cli) {
+		ast_cli(test->cli->fd, "%s", ast_str_buffer(buf));
+	}
+
+	ast_free(buf);
+}
+
 int __ast_test_status_update(const char *file, const char *func, int line,
 		struct ast_test *test, const char *fmt, ...)
 {

Modified: team/rmudgett/ao2_red_black/tests/test_astobj2.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/ao2_red_black/tests/test_astobj2.c?view=diff&rev=371821&r1=371820&r2=371821
==============================================================================
--- team/rmudgett/ao2_red_black/tests/test_astobj2.c (original)
+++ team/rmudgett/ao2_red_black/tests/test_astobj2.c Tue Aug 28 14:59:47 2012
@@ -732,6 +732,7 @@
 		ast_test_status_update(test, "container integrity check failed\n");
 		res = AST_TEST_FAIL;
 	}
+	ao2_container_stats(c1, 0, "BUGBUG c1", (void *) test, (ao2_prnt_fn *) ast_test_debug);
 
 cleanup:
 	/* destroy containers */




More information about the asterisk-commits mailing list