Fix: liblttng-ctl comm: lttng_event_field is not packed
[lttng-tools.git] / src / lib / lttng-ctl / lttng-ctl.c
index 6b745d0204eb30d1c6517c72d2a6314fd1787858..fd5d9e3d66eb9dbddbafa8490da95cf1ab5f21d5 100644 (file)
@@ -804,9 +804,10 @@ int lttng_add_context(struct lttng_handle *handle,
                const char *channel_name)
 {
        int ret;
-       size_t len = 0;
-       char *buf = NULL;
        struct lttcomm_session_msg lsm;
+       struct lttng_dynamic_buffer buffer;
+
+       lttng_dynamic_buffer_init(&buffer);
 
        /* Safety check. Both are mandatory. */
        if (handle == NULL || ctx == NULL) {
@@ -833,55 +834,18 @@ int lttng_add_context(struct lttng_handle *handle,
                goto end;
        }
 
-       if (ctx->ctx == LTTNG_EVENT_CONTEXT_APP_CONTEXT) {
-               size_t provider_len, ctx_len;
-               const char *provider_name = ctx->u.app_ctx.provider_name;
-               const char *ctx_name = ctx->u.app_ctx.ctx_name;
-
-               if (!provider_name || !ctx_name) {
-                       ret = -LTTNG_ERR_INVALID;
-                       goto end;
-               }
-
-               provider_len = strlen(provider_name);
-               if (provider_len == 0) {
-                       ret = -LTTNG_ERR_INVALID;
-                       goto end;
-               }
-               lsm.u.context.provider_name_len = provider_len;
-
-               ctx_len = strlen(ctx_name);
-               if (ctx_len == 0) {
-                       ret = -LTTNG_ERR_INVALID;
-                       goto end;
-               }
-               lsm.u.context.context_name_len = ctx_len;
-
-               len = provider_len + ctx_len;
-               buf = zmalloc(len);
-               if (!buf) {
-                       ret = -LTTNG_ERR_NOMEM;
-                       goto end;
-               }
-
-               memcpy(buf, provider_name, provider_len);
-               memcpy(buf + provider_len, ctx_name, ctx_len);
+       ret = lttng_event_context_serialize(ctx, &buffer);
+       if (ret) {
+               ret = -LTTNG_ERR_INVALID;
+               goto end;
        }
-       memcpy(&lsm.u.context.ctx, ctx, sizeof(struct lttng_event_context));
 
-       if (ctx->ctx == LTTNG_EVENT_CONTEXT_APP_CONTEXT) {
-               /*
-                * Don't leak application addresses to the sessiond.
-                * This is only necessary when ctx is for an app ctx otherwise
-                * the values inside the union (type & config) are overwritten.
-                */
-               lsm.u.context.ctx.u.app_ctx.provider_name = NULL;
-               lsm.u.context.ctx.u.app_ctx.ctx_name = NULL;
-       }
+       lsm.u.context.length = buffer.size;
 
-       ret = lttng_ctl_ask_sessiond_varlen_no_cmd_header(&lsm, buf, len, NULL);
+       ret = lttng_ctl_ask_sessiond_varlen_no_cmd_header(
+                       &lsm, buffer.data, buffer.size, NULL);
 end:
-       free(buf);
+       lttng_dynamic_buffer_reset(&buffer);
        return ret;
 }
 
@@ -1688,8 +1652,13 @@ end:
 int lttng_list_tracepoint_fields(struct lttng_handle *handle,
                struct lttng_event_field **fields)
 {
-       int ret;
+       enum lttng_error_code ret_code;
+       int ret, total_payload_received;
        struct lttcomm_session_msg lsm;
+       char *reception_buffer = NULL;
+       struct lttcomm_list_command_header *cmd_header = NULL;
+       size_t cmd_header_len;
+       unsigned int nb_event_fields = 0;
 
        if (handle == NULL) {
                return -LTTNG_ERR_INVALID;
@@ -1699,12 +1668,45 @@ int lttng_list_tracepoint_fields(struct lttng_handle *handle,
        lsm.cmd_type = LTTNG_LIST_TRACEPOINT_FIELDS;
        COPY_DOMAIN_PACKED(lsm.domain, handle->domain);
 
-       ret = lttng_ctl_ask_sessiond(&lsm, (void **) fields);
+       ret = lttng_ctl_ask_sessiond_fds_varlen(&lsm, NULL, 0, NULL, 0,
+                       (void **) &reception_buffer, (void **) &cmd_header,
+                       &cmd_header_len);
        if (ret < 0) {
-               return ret;
+               goto end;
+       }
+
+       total_payload_received = ret;
+
+       if (!cmd_header) {
+               ret = -LTTNG_ERR_UNK;
+               goto end;
+       }
+
+       if (cmd_header->count > INT_MAX) {
+               ret = -LTTNG_ERR_OVERFLOW;
+               goto end;
        }
 
-       return ret / sizeof(struct lttng_event_field);
+       nb_event_fields = cmd_header->count;
+
+       {
+               const struct lttng_buffer_view view =
+                       lttng_buffer_view_init(reception_buffer, 0, total_payload_received);
+
+               ret_code = lttng_event_fields_create_and_flatten_from_buffer(
+                               &view, nb_event_fields, fields);
+               if (ret_code != LTTNG_OK) {
+                       ret = -ret_code;
+                       goto end;
+               }
+       }
+
+       ret = nb_event_fields;
+
+end:
+       free(cmd_header);
+       free(reception_buffer);
+       return ret;
 }
 
 /*
This page took 0.02436 seconds and 4 git commands to generate.