[lttng-dev] [Patch LTTng-ust v2 5/7] Send and receive serialized data for CTF global enumerations

Geneviève Bastien gbastien+lttng at versatic.net
Tue Feb 11 16:35:34 EST 2014


Updates the functions used for the communication between UST and the session
daemon so that global type declarations can be sent and received. The
description of the global type declarations follows the event that uses them.
The extra fields for each global type category follow the descriptions of all
global type declarations.

Signed-off-by: Geneviève Bastien <gbastien+lttng at versatic.net>
---
 include/lttng/ust-ctl.h            |   4 +-
 include/ust-comm.h                 |   8 ++-
 liblttng-ust-comm/lttng-ust-comm.c | 111 ++++++++++++++++++++++++++++++++-----
 liblttng-ust-ctl/ustctl.c          |  74 ++++++++++++++++++++++++-
 liblttng-ust/lttng-events.c        |   4 +-
 5 files changed, 182 insertions(+), 19 deletions(-)

diff --git a/include/lttng/ust-ctl.h b/include/lttng/ust-ctl.h
index 783492b..b44fb41 100644
--- a/include/lttng/ust-ctl.h
+++ b/include/lttng/ust-ctl.h
@@ -421,7 +421,9 @@ int ustctl_recv_register_event(int sock,
 					 */
 	size_t *nr_fields,
 	struct ustctl_field **fields,
-	char **model_emf_uri);
+	char **model_emf_uri,
+	size_t *nr_global_type_decl,
+	struct ustctl_global_type_decl **global_type_decl);
 
 /*
  * Returns 0 on success, negative error value on error.
diff --git a/include/ust-comm.h b/include/ust-comm.h
index b9bbb39..ed46364 100644
--- a/include/ust-comm.h
+++ b/include/ust-comm.h
@@ -49,6 +49,7 @@
 #define LTTNG_UST_COMM_REG_MSG_PADDING			64
 
 struct lttng_event_field;
+struct lttng_global_type_decl;
 struct lttng_ctx_field;
 
 struct ustctl_reg_msg {
@@ -127,7 +128,7 @@ struct ustcomm_notify_hdr {
 	uint32_t notify_cmd;
 } LTTNG_PACKED;
 
-#define USTCOMM_NOTIFY_EVENT_MSG_PADDING	32
+#define USTCOMM_NOTIFY_EVENT_MSG_PADDING	28
 struct ustcomm_notify_event_msg {
 	uint32_t session_objd;
 	uint32_t channel_objd;
@@ -136,6 +137,7 @@ struct ustcomm_notify_event_msg {
 	uint32_t signature_len;
 	uint32_t fields_len;
 	uint32_t model_emf_uri_len;
+	uint32_t global_type_decl_len;
 	char padding[USTCOMM_NOTIFY_EVENT_MSG_PADDING];
 	/* followed by signature, fields, and model_emf_uri */
 } LTTNG_PACKED;
@@ -221,7 +223,9 @@ int ustcomm_register_event(int sock,
 	size_t nr_fields,		/* fields */
 	const struct lttng_event_field *fields,
 	const char *model_emf_uri,
-	uint32_t *id);			/* event id (output) */
+	uint32_t *id,			/* event id (output) */
+	size_t nr_global_type_decl,
+	const struct lttng_global_type_decl *lttng_global_types); /* global type declarations */
 
 /*
  * Returns 0 on success, negative error value on error.
diff --git a/liblttng-ust-comm/lttng-ust-comm.c b/liblttng-ust-comm/lttng-ust-comm.c
index 67c6381..a21a195 100644
--- a/liblttng-ust-comm/lttng-ust-comm.c
+++ b/liblttng-ust-comm/lttng-ust-comm.c
@@ -1015,7 +1015,9 @@ int ustcomm_register_event(int sock,
 	size_t nr_fields,		/* fields */
 	const struct lttng_event_field *lttng_fields,
 	const char *model_emf_uri,
-	uint32_t *id)			/* event id (output) */
+	uint32_t *id,			/* event id (output) */
+	size_t nr_global_type_decl,
+	const struct lttng_global_type_decl *lttng_global_types) /* global type declarations */
 {
 	ssize_t len;
 	struct {
@@ -1026,10 +1028,12 @@ int ustcomm_register_event(int sock,
 		struct ustcomm_notify_hdr header;
 		struct ustcomm_notify_event_reply r;
 	} reply;
-	size_t signature_len, fields_len, model_emf_uri_len;
+	size_t signature_len, fields_len, model_emf_uri_len, global_type_len;
 	struct ustctl_field *fields = NULL;
+	struct ustctl_global_type_decl *global_type_decl = NULL;
 	size_t nr_write_fields = 0;
-	int ret;
+	size_t nr_write_global_type_decl = 0;
+	int ret, i;
 
 	memset(&msg, 0, sizeof(msg));
 	msg.header.notify_cmd = USTCTL_NOTIFY_CMD_EVENT;
@@ -1057,14 +1061,26 @@ int ustcomm_register_event(int sock,
 		model_emf_uri_len = 0;
 	}
 	msg.m.model_emf_uri_len = model_emf_uri_len;
+	/* Calculate global type declarations len, serialize global types. */
+	if (nr_global_type_decl > 0) {
+		ret = serialize_global_type_decl(&nr_write_global_type_decl, &global_type_decl,
+				nr_global_type_decl, lttng_global_types);
+		if (ret) {
+			free(fields);
+			return ret;
+		}
+	}
+	global_type_len = sizeof(*global_type_decl) * nr_write_global_type_decl;
+	msg.m.global_type_decl_len = global_type_len;
+
 	len = ustcomm_send_unix_sock(sock, &msg, sizeof(msg));
 	if (len > 0 && len != sizeof(msg)) {
-		free(fields);
-		return -EIO;
+		ret = -EIO;
+		goto error_fields;
 	}
 	if (len < 0) {
-		free(fields);
-		return len;
+		ret = len;
+		goto error_fields;
 	}
 
 	/* send signature */
@@ -1083,10 +1099,12 @@ int ustcomm_register_event(int sock,
 		len = ustcomm_send_unix_sock(sock, fields, fields_len);
 		free(fields);
 		if (len > 0 && len != fields_len) {
-			return -EIO;
+			ret = -EIO;
+			goto error_global_type;
 		}
 		if (len < 0) {
-			return len;
+			ret = len;
+			goto error_global_type;
 		}
 	} else {
 		free(fields);
@@ -1096,10 +1114,58 @@ int ustcomm_register_event(int sock,
 		/* send model_emf_uri */
 		len = ustcomm_send_unix_sock(sock, model_emf_uri,
 				model_emf_uri_len);
-		if (len > 0 && len != model_emf_uri_len)
-			return -EIO;
-		if (len < 0)
-			return len;
+		if (len > 0 && len != model_emf_uri_len) {
+			ret = -EIO;
+			goto error_global_type;
+		}
+		if (len < 0) {
+			ret = len;
+			goto error_global_type;
+		}
+	}
+
+	/* Send global type declarations */
+	if (global_type_len > 0) {
+		len = ustcomm_send_unix_sock(sock, global_type_decl, global_type_len);
+		DBG("Sending global type declarations for event %s.\n", event_name);
+		if (len > 0 && len != global_type_len) {
+			goto error_global_type;
+		}
+		if (len < 0) {
+			goto error_global_type;
+		}
+		/* Send extra global types information */
+		for (i = 0; i < nr_write_global_type_decl; i++) {
+			struct ustctl_global_type_decl *one_global_type;
+			one_global_type = &global_type_decl[i];
+
+			switch (one_global_type->mtype) {
+			case ustctl_mtype_enum:
+			{
+				int entry_len = one_global_type->u.ctf_enum.len * sizeof(*one_global_type->u.ctf_enum.entries);
+
+				/* Send the entries */
+				DBG("Sending entries for global type enumeration %s.\n",
+						one_global_type->u.ctf_enum.name);
+				len = ustcomm_send_unix_sock(sock, one_global_type->u.ctf_enum.entries, entry_len);
+				free(one_global_type->u.ctf_enum.entries);
+				one_global_type->u.ctf_enum.entries = NULL;
+				if (len > 0 && len != entry_len) {
+					goto error_global_type;
+				}
+				if (len < 0) {
+					goto error_global_type;
+				}
+				break;
+			}
+			default:
+				break;
+			}
+		}
+		free(global_type_decl);
+
+	} else {
+		free(global_type_decl);
 	}
 
 	/* receive reply */
@@ -1133,6 +1199,25 @@ int ustcomm_register_event(int sock,
 			return len;
 		}
 	}
+
+error_fields:
+	free(fields);
+error_global_type:
+	/* First free dynamically allocated content in global_type */
+	for (i = 0; i < nr_write_global_type_decl; i++) {
+		struct ustctl_global_type_decl *one_global_type;
+		one_global_type = &global_type_decl[i];
+
+		switch (one_global_type->mtype) {
+		case ustctl_mtype_enum:
+			free(one_global_type->u.ctf_enum.entries);
+			break;
+		default:
+			break;
+		}
+	}
+	free(global_type_decl);
+	return ret;
 }
 
 /*
diff --git a/liblttng-ust-ctl/ustctl.c b/liblttng-ust-ctl/ustctl.c
index 00d9802..f1cfbb5 100644
--- a/liblttng-ust-ctl/ustctl.c
+++ b/liblttng-ust-ctl/ustctl.c
@@ -1724,13 +1724,17 @@ int ustctl_recv_register_event(int sock,
 	char **signature,
 	size_t *nr_fields,
 	struct ustctl_field **fields,
-	char **model_emf_uri)
+	char **model_emf_uri,
+	size_t *nr_global_type_decl,
+	struct ustctl_global_type_decl **global_type_decl)
 {
 	ssize_t len;
 	struct ustcomm_notify_event_msg msg;
-	size_t signature_len, fields_len, model_emf_uri_len;
+	size_t signature_len, fields_len, model_emf_uri_len, global_type_decl_len;
 	char *a_sign = NULL, *a_model_emf_uri = NULL;
 	struct ustctl_field *a_fields = NULL;
+	struct ustctl_global_type_decl *a_global_type = NULL;
+	int i;
 
 	len = ustcomm_recv_unix_sock(sock, &msg, sizeof(msg));
 	if (len > 0 && len != sizeof(msg))
@@ -1754,6 +1758,12 @@ int ustctl_recv_register_event(int sock,
 
 	model_emf_uri_len = msg.model_emf_uri_len;
 
+	global_type_decl_len = msg.global_type_decl_len;
+
+	if (global_type_decl_len % sizeof(*a_global_type) != 0) {
+		return -EINVAL;
+	}
+
 	/* recv signature. contains at least \0. */
 	a_sign = zmalloc(signature_len);
 	if (!a_sign)
@@ -1818,13 +1828,73 @@ int ustctl_recv_register_event(int sock,
 		a_model_emf_uri[model_emf_uri_len - 1] = '\0';
 	}
 
+	/* recv global types */
+	if (global_type_decl_len) {
+		a_global_type = zmalloc(global_type_decl_len);
+		if (!a_global_type) {
+			len = -ENOMEM;
+			goto signature_error;
+		}
+		len = ustcomm_recv_unix_sock(sock, a_global_type, global_type_decl_len);
+		DBG("Received global types for event %s.\n", event_name);
+		if (len > 0 && len != global_type_decl_len) {
+			len = -EIO;
+			goto global_type_error;
+		}
+		if (len == 0) {
+			len = -EPIPE;
+			goto global_type_error;
+		}
+		if (len < 0) {
+			goto global_type_error;
+		}
+		/* Receive extra information per global type category */
+		for (i = 0; i < global_type_decl_len / sizeof(*a_global_type); i++) {
+			struct ustctl_global_type_decl *one_global_type;
+			one_global_type = &a_global_type[i];
+
+			switch (one_global_type->mtype) {
+			case ustctl_mtype_enum:
+			{
+				int entry_len = one_global_type->u.ctf_enum.len * sizeof(*one_global_type->u.ctf_enum.entries);
+				/* Send the entries */
+				one_global_type->u.ctf_enum.entries = zmalloc(entry_len);
+				if (!one_global_type->u.ctf_enum.entries) {
+					len = -ENOMEM;
+					goto global_type_error;
+				}
+				len = ustcomm_recv_unix_sock(sock, one_global_type->u.ctf_enum.entries, entry_len);
+				DBG("Received entries for enum %s.\n", one_global_type->u.ctf_enum.name);
+				if (len > 0 && len != entry_len) {
+					len = -EIO;
+					goto global_type_error;
+				}
+				if (len == 0) {
+					len = -EPIPE;
+					goto global_type_error;
+				}
+				if (len < 0) {
+					goto global_type_error;
+				}
+				break;
+			}
+			default:
+				break;
+			}
+		}
+	}
+
 	*signature = a_sign;
 	*nr_fields = fields_len / sizeof(*a_fields);
 	*fields = a_fields;
 	*model_emf_uri = a_model_emf_uri;
+	*nr_global_type_decl = global_type_decl_len / sizeof(*a_global_type);
+	*global_type_decl = a_global_type;
 
 	return 0;
 
+global_type_error:
+	free(a_global_type);
 model_error:
 	free(a_model_emf_uri);
 fields_error:
diff --git a/liblttng-ust/lttng-events.c b/liblttng-ust/lttng-events.c
index 6e16cf2..c0db4a7 100644
--- a/liblttng-ust/lttng-events.c
+++ b/liblttng-ust/lttng-events.c
@@ -430,7 +430,9 @@ int lttng_event_create(const struct lttng_event_desc *desc,
 		desc->nr_fields,
 		desc->fields,
 		uri,
-		&event->id);
+		&event->id,
+		desc->u.ext.nr_global_type_decl,
+		desc->u.ext.global_type_decl);
 	if (ret < 0) {
 		DBG("Error (%d) registering event to sessiond", ret);
 		goto sessiond_register_error;
-- 
1.8.5.4




More information about the lttng-dev mailing list