ctf: refactor metadata decoder to always have an instance
authorPhilippe Proulx <eeppeliteloop@gmail.com>
Tue, 9 Jul 2019 23:40:45 +0000 (19:40 -0400)
committerSimon Marchi <simon.marchi@efficios.com>
Wed, 4 Sep 2019 15:38:52 +0000 (11:38 -0400)
This patch changes the internal `ctf` plugin's metadata decoder API so
that you need to create a decoder instance to read properties instead of
calling ctf_metadata_decoder_packetized_file_stream_to_buf().

Now, you create a metadata decoder, you call
ctf_metadata_decoder_append_content() (similar to what was called
ctf_metadata_decoder_decode()), and then you can get the decoder's
current properties:

* ctf_metadata_decoder_get_ir_trace_class()
* ctf_metadata_decoder_borrow_ctf_trace_class()
* ctf_metadata_decoder_get_byte_order()
* ctf_metadata_decoder_get_uuid()
* ctf_metadata_decoder_get_text()

The decoder's configuration contains two new flags:

`create_trace_class`:
    Controls whether or not ctf_metadata_decoder_append_content()
    invokes the AST visitor to generate trace class objects.

    Trace classes are not needed, for example, for the `metadata-info`
    query.

`keep_plain_text`:
    Controls whether or not the decoder accumulates the metadata
    stream's plain text when you call
    ctf_metadata_decoder_append_content().

    This needs to be true to use ctf_metadata_decoder_get_text().

The goal of all this is to eventually add new metadata property getters
which do not need to create trace classes or to keep the metadata plain
text.

Signed-off-by: Philippe Proulx <eeppeliteloop@gmail.com>
Change-Id: If1095da91aee0f446d7f5efcec765e5abbb2b30a
Reviewed-on: https://review.lttng.org/c/babeltrace/+/1842
CI-Build: Simon Marchi <simon.marchi@efficios.com>
Reviewed-by: Simon Marchi <simon.marchi@efficios.com>
Tested-by: jenkins <jenkins@lttng.org>
src/plugins/ctf/common/metadata/decoder.c
src/plugins/ctf/common/metadata/decoder.h
src/plugins/ctf/fs-src/metadata.c
src/plugins/ctf/fs-src/query.c
src/plugins/ctf/lttng-live/metadata.c

index a422ad433c4a2261cb7dc7626201bec6ebdd86e8..17b2aa4bd211be1474d4d7da288207f7cc7fc2a7 100644 (file)
@@ -40,11 +40,14 @@ extern
 int yydebug;
 
 struct ctf_metadata_decoder {
+       struct ctf_scanner *scanner;
+       GString *text;
        struct ctf_visitor_generate_ir *visitor;
        bt_uuid_t uuid;
        bool is_uuid_set;
        int bo;
        struct ctf_metadata_decoder_config config;
+       struct meta_log_config log_cfg;
 };
 
 struct packet_header {
@@ -61,26 +64,35 @@ struct packet_header {
 } __attribute__((__packed__));
 
 BT_HIDDEN
-bool ctf_metadata_decoder_is_packetized(FILE *fp, int *byte_order,
-               bt_logging_level log_level, bt_self_component *self_comp)
+int ctf_metadata_decoder_packetized_file_stream_to_buf(FILE *fp,
+               char **buf, int byte_order, bool *is_uuid_set,
+               uint8_t *uuid, bt_logging_level log_level,
+               bt_self_component *self_comp);
+
+BT_HIDDEN
+int ctf_metadata_decoder_is_packetized(FILE *fp, bool *is_packetized,
+               int *byte_order, bt_logging_level log_level,
+               bt_self_component *self_comp)
 {
        uint32_t magic;
        size_t len;
        int ret = 0;
 
+       *is_packetized = false;
        len = fread(&magic, sizeof(magic), 1, fp);
        if (len != 1) {
                BT_COMP_LOG_CUR_LVL(BT_LOG_INFO, log_level, self_comp,
                        "Cannot read first metadata packet header: assuming the stream is not packetized.");
+               ret = -1;
                goto end;
        }
 
        if (byte_order) {
                if (magic == TSDL_MAGIC) {
-                       ret = 1;
+                       *is_packetized = true;
                        *byte_order = BYTE_ORDER;
                } else if (magic == GUINT32_SWAP_LE_BE(TSDL_MAGIC)) {
-                       ret = 1;
+                       *is_packetized = true;
                        *byte_order = BYTE_ORDER == BIG_ENDIAN ?
                                LITTLE_ENDIAN : BIG_ENDIAN;
                }
@@ -113,14 +125,29 @@ struct ctf_metadata_decoder *ctf_metadata_decoder_create(
                goto end;
        }
 
+       mdec->log_cfg.log_level = config->log_level;
+       mdec->log_cfg.self_comp = config->self_comp;
+       mdec->scanner = ctf_scanner_alloc();
+       if (!mdec->scanner) {
+               BT_COMP_LOGE("Cannot allocate a metadata lexical scanner: "
+                       "mdec-addr=%p", mdec);
+               goto error;
+       }
+
+       mdec->text = g_string_new(NULL);
+       if (!mdec->text) {
+               BT_COMP_LOGE("Failed to allocate one GString: "
+                       "mdec-addr=%p", mdec);
+               goto error;
+       }
+
+       mdec->bo = -1;
        mdec->config = *config;
        mdec->visitor = ctf_visitor_generate_ir_create(config);
        if (!mdec->visitor) {
                BT_COMP_LOGE("Failed to create a CTF IR metadata AST visitor: "
                        "mdec-addr=%p", mdec);
-               ctf_metadata_decoder_destroy(mdec);
-               mdec = NULL;
-               goto end;
+               goto error;
        }
 
        BT_COMP_LOGD("Creating CTF metadata decoder: "
@@ -128,6 +155,11 @@ struct ctf_metadata_decoder *ctf_metadata_decoder_create(
                "clock-class-offset-ns=%" PRId64 ", addr=%p",
                config->clock_class_offset_s, config->clock_class_offset_ns,
                mdec);
+       goto end;
+
+error:
+       ctf_metadata_decoder_destroy(mdec);
+       mdec = NULL;
 
 end:
        return mdec;
@@ -140,29 +172,40 @@ void ctf_metadata_decoder_destroy(struct ctf_metadata_decoder *mdec)
                return;
        }
 
+       if (mdec->scanner) {
+               ctf_scanner_free(mdec->scanner);
+       }
+
+       if (mdec->text) {
+               g_string_free(mdec->text, TRUE);
+       }
+
        BT_COMP_LOGD("Destroying CTF metadata decoder: addr=%p", mdec);
        ctf_visitor_generate_ir_destroy(mdec->visitor);
        g_free(mdec);
 }
 
 BT_HIDDEN
-enum ctf_metadata_decoder_status ctf_metadata_decoder_decode(
+enum ctf_metadata_decoder_status ctf_metadata_decoder_append_content(
                struct ctf_metadata_decoder *mdec, FILE *fp)
 {
        enum ctf_metadata_decoder_status status =
                CTF_METADATA_DECODER_STATUS_OK;
        int ret;
-       struct ctf_scanner *scanner = NULL;
        char *buf = NULL;
        bool close_fp = false;
-       struct meta_log_config log_cfg;
+       long start_pos = -1;
+       bool is_packetized;
 
        BT_ASSERT(mdec);
-       log_cfg.log_level = mdec->config.log_level;
-       log_cfg.self_comp = mdec->config.self_comp;
+       ret = ctf_metadata_decoder_is_packetized(fp, &is_packetized, &mdec->bo,
+                       mdec->config.log_level, mdec->config.self_comp);
+       if (ret) {
+               status = CTF_METADATA_DECODER_STATUS_ERROR;
+               goto end;
+       }
 
-       if (ctf_metadata_decoder_is_packetized(fp, &mdec->bo,
-                       mdec->config.log_level, mdec->config.self_comp)) {
+       if (is_packetized) {
                BT_COMP_LOGI("Metadata stream is packetized: mdec-addr=%p", mdec);
                ret = ctf_metadata_decoder_packetized_file_stream_to_buf(fp,
                        &buf, mdec->bo, &mdec->is_uuid_set,
@@ -232,17 +275,15 @@ enum ctf_metadata_decoder_status ctf_metadata_decoder_decode(
                yydebug = 1;
        }
 
-       /* Allocate a scanner and append the metadata text content */
-       scanner = ctf_scanner_alloc();
-       if (!scanner) {
-               BT_COMP_LOGE("Cannot allocate a metadata lexical scanner: "
-                       "mdec-addr=%p", mdec);
-               status = CTF_METADATA_DECODER_STATUS_ERROR;
-               goto end;
+       /* Save the file's position: we'll seek back to append the plain text */
+       BT_ASSERT(fp);
+
+       if (mdec->config.keep_plain_text) {
+               start_pos = ftell(fp);
        }
 
-       BT_ASSERT(fp);
-       ret = ctf_scanner_append_ast(scanner, fp);
+       /* Append the metadata text content */
+       ret = ctf_scanner_append_ast(mdec->scanner, fp);
        if (ret) {
                BT_COMP_LOGE("Cannot create the metadata AST out of the metadata text: "
                        "mdec-addr=%p", mdec);
@@ -250,7 +291,28 @@ enum ctf_metadata_decoder_status ctf_metadata_decoder_decode(
                goto end;
        }
 
-       ret = ctf_visitor_semantic_check(0, &scanner->ast->root, &log_cfg);
+       /* We know it's complete: append plain text */
+       if (mdec->config.keep_plain_text) {
+               BT_ASSERT(start_pos != -1);
+               ret = fseek(fp, start_pos, SEEK_SET);
+               if (ret) {
+                       BT_COMP_LOGE("Failed to seek file: ret=%d, mdec-addr=%p",
+                               ret, mdec);
+                       status = CTF_METADATA_DECODER_STATUS_ERROR;
+                       goto end;
+               }
+
+               ret = bt_common_append_file_content_to_g_string(mdec->text, fp);
+               if (ret) {
+                       BT_COMP_LOGE("Failed to append to current plain text: "
+                               "ret=%d, mdec-addr=%p", ret, mdec);
+                       status = CTF_METADATA_DECODER_STATUS_ERROR;
+                       goto end;
+               }
+       }
+
+       ret = ctf_visitor_semantic_check(0, &mdec->scanner->ast->root,
+               &mdec->log_cfg);
        if (ret) {
                BT_COMP_LOGE("Validation of the metadata semantics failed: "
                        "mdec-addr=%p", mdec);
@@ -258,29 +320,27 @@ enum ctf_metadata_decoder_status ctf_metadata_decoder_decode(
                goto end;
        }
 
-       ret = ctf_visitor_generate_ir_visit_node(mdec->visitor,
-               &scanner->ast->root);
-       switch (ret) {
-       case 0:
-               /* Success */
-               break;
-       case -EINCOMPLETE:
-               BT_COMP_LOGD("While visiting metadata AST: incomplete data: "
-                       "mdec-addr=%p", mdec);
-               status = CTF_METADATA_DECODER_STATUS_INCOMPLETE;
-               goto end;
-       default:
-               BT_COMP_LOGE("Failed to visit AST node to create CTF IR objects: "
-                       "mdec-addr=%p, ret=%d", mdec, ret);
-               status = CTF_METADATA_DECODER_STATUS_IR_VISITOR_ERROR;
-               goto end;
+       if (mdec->config.create_trace_class) {
+               ret = ctf_visitor_generate_ir_visit_node(mdec->visitor,
+                       &mdec->scanner->ast->root);
+               switch (ret) {
+               case 0:
+                       /* Success */
+                       break;
+               case -EINCOMPLETE:
+                       BT_COMP_LOGD("While visiting metadata AST: incomplete data: "
+                               "mdec-addr=%p", mdec);
+                       status = CTF_METADATA_DECODER_STATUS_INCOMPLETE;
+                       goto end;
+               default:
+                       BT_COMP_LOGE("Failed to visit AST node to create CTF IR objects: "
+                               "mdec-addr=%p, ret=%d", mdec, ret);
+                       status = CTF_METADATA_DECODER_STATUS_IR_VISITOR_ERROR;
+                       goto end;
+               }
        }
 
 end:
-       if (scanner) {
-               ctf_scanner_free(scanner);
-       }
-
        yydebug = 0;
 
        if (fp && close_fp) {
@@ -299,6 +359,8 @@ BT_HIDDEN
 bt_trace_class *ctf_metadata_decoder_get_ir_trace_class(
                struct ctf_metadata_decoder *mdec)
 {
+       BT_ASSERT(mdec);
+       BT_ASSERT(mdec->config.create_trace_class);
        return ctf_visitor_generate_ir_get_ir_trace_class(mdec->visitor);
 }
 
@@ -306,5 +368,41 @@ BT_HIDDEN
 struct ctf_trace_class *ctf_metadata_decoder_borrow_ctf_trace_class(
                struct ctf_metadata_decoder *mdec)
 {
+       BT_ASSERT(mdec);
+       BT_ASSERT(mdec->config.create_trace_class);
        return ctf_visitor_generate_ir_borrow_ctf_trace_class(mdec->visitor);
 }
+
+BT_HIDDEN
+const char *ctf_metadata_decoder_get_text(struct ctf_metadata_decoder *mdec)
+{
+       BT_ASSERT(mdec);
+       BT_ASSERT(mdec->config.keep_plain_text);
+       return mdec->text->str;
+}
+
+BT_HIDDEN
+int ctf_metadata_decoder_get_byte_order(struct ctf_metadata_decoder *mdec)
+{
+       BT_ASSERT(mdec);
+       return mdec->bo;
+}
+
+BT_HIDDEN
+int ctf_metadata_decoder_get_uuid(struct ctf_metadata_decoder *mdec,
+               bt_uuid_t uuid)
+{
+       int ret = 0;
+
+       BT_ASSERT(mdec);
+
+       if (!mdec->is_uuid_set) {
+               ret = -1;
+               goto end;
+       }
+
+       bt_uuid_copy(uuid, mdec->uuid);
+
+end:
+       return ret;
+}
index 42e79bf25a91f5e217bb0913e7f5154a74277b12..f67548998751998555a92795e98c78f5bc06055d 100644 (file)
@@ -21,6 +21,9 @@
 #include <babeltrace2/babeltrace.h>
 
 #include "common/macros.h"
+#include "common/uuid.h"
+
+struct ctf_trace_class;
 
 /* A CTF metadata decoder object */
 struct ctf_metadata_decoder;
@@ -36,13 +39,24 @@ enum ctf_metadata_decoder_status {
 
 /* Decoding configuration */
 struct ctf_metadata_decoder_config {
+       /* Active log level to use */
        bt_logging_level log_level;
 
-       /* Weak */
+       /* Component to use for logging (can be `NULL`); weak */
        bt_self_component *self_comp;
 
+       /* Additional clock class offset to apply */
        int64_t clock_class_offset_s;
        int64_t clock_class_offset_ns;
+
+       /* True to create trace class objects */
+       bool create_trace_class;
+
+       /*
+        * True to keep the plain text when content is appended with
+        * ctf_metadata_decoder_append_content().
+        */
+       bool keep_plain_text;
 };
 
 /*
@@ -63,62 +77,89 @@ void ctf_metadata_decoder_destroy(
                struct ctf_metadata_decoder *metadata_decoder);
 
 /*
- * Decodes a new chunk of CTF metadata.
+ * Appends content to the metadata decoder.
  *
  * This function reads the metadata from the current position of `fp`
- * until the end of this file stream. If it finds new information (new
- * event class, new stream class, or new clock class), it appends this
- * information to the decoder's trace object (as returned by
- * ctf_metadata_decoder_get_ir_trace_class()), or it creates this trace.
+ * until the end of this file stream.
  *
  * The metadata can be packetized or not.
  *
- * The metadata chunk needs to be complete and scannable, that is,
- * zero or more complete top-level blocks. If it's incomplete, this
+ * The metadata chunk needs to be complete and lexically scannable, that
+ * is, zero or more complete top-level blocks. If it's incomplete, this
  * function returns `CTF_METADATA_DECODER_STATUS_INCOMPLETE`. If this
  * function returns `CTF_METADATA_DECODER_STATUS_INCOMPLETE`, then you
- * need to call it again with the same metadata and more to make it
+ * need to call it again with the _same_ metadata and more to make it
  * complete. For example:
  *
  *     First call:  event { name = hell
  *     Second call: event { name = hello_world; ... };
  *
- * If the conversion from the metadata text to CTF IR objects fails,
- * this function returns `CTF_METADATA_DECODER_STATUS_IR_VISITOR_ERROR`.
- *
  * If everything goes as expected, this function returns
  * `CTF_METADATA_DECODER_STATUS_OK`.
  */
 BT_HIDDEN
-enum ctf_metadata_decoder_status ctf_metadata_decoder_decode(
+enum ctf_metadata_decoder_status ctf_metadata_decoder_append_content(
                struct ctf_metadata_decoder *metadata_decoder, FILE *fp);
 
+/*
+ * Returns the trace IR trace class of this metadata decoder (new
+ * reference).
+ *
+ * Returns `NULL` if there's none yet or if the metadata decoder is not
+ * configured to create trace classes.
+ */
 BT_HIDDEN
 bt_trace_class *ctf_metadata_decoder_get_ir_trace_class(
                struct ctf_metadata_decoder *mdec);
 
+/*
+ * Returns the CTF IR trace class of this metadata decoder.
+ *
+ * Returns `NULL` if there's none yet or if the metadata decoder is not
+ * configured to create trace classes.
+ */
 BT_HIDDEN
 struct ctf_trace_class *ctf_metadata_decoder_borrow_ctf_trace_class(
                struct ctf_metadata_decoder *mdec);
 
 /*
- * Checks whether or not a given metadata file stream is packetized, and
- * if so, sets `*byte_order` to the byte order of the first packet.
+ * Checks whether or not a given metadata file stream `fp` is
+ * packetized, setting `is_packetized` accordingly on success. On
+ * success, also sets `*byte_order` to the byte order of the first
+ * packet.
+ *
+ * This function uses `log_level` and `self_comp` for logging purposes.
+ * `self_comp` can be `NULL` if not available.
  */
 BT_HIDDEN
-bool ctf_metadata_decoder_is_packetized(FILE *fp, int *byte_order,
-               bt_logging_level log_level,
+int ctf_metadata_decoder_is_packetized(FILE *fp, bool *is_packetized,
+               int *byte_order, bt_logging_level log_level,
                bt_self_component *self_comp);
 
 /*
- * Decodes a packetized metadata file stream to a NULL-terminated
- * text buffer using the given byte order.
+ * Returns the byte order of the decoder's metadata stream as set by the
+ * last call to ctf_metadata_decoder_append_content().
+ *
+ * Returns -1 if unknown (plain text content).
  */
 BT_HIDDEN
-int ctf_metadata_decoder_packetized_file_stream_to_buf(FILE *fp,
-               char **buf, int byte_order, bool *is_uuid_set,
-               uint8_t *uuid, bt_logging_level log_level,
-               bt_self_component *self_comp);
+int ctf_metadata_decoder_get_byte_order(struct ctf_metadata_decoder *mdec);
+
+/*
+ * Returns the UUID of the decoder's metadata stream as set by the last
+ * call to ctf_metadata_decoder_append_content().
+ *
+ * Returns -1 if unknown (plain text content).
+ */
+BT_HIDDEN
+int ctf_metadata_decoder_get_uuid(struct ctf_metadata_decoder *mdec,
+               bt_uuid_t uuid);
+
+/*
+ * Returns the metadata decoder's current metadata text.
+ */
+BT_HIDDEN
+const char *ctf_metadata_decoder_get_text(struct ctf_metadata_decoder *mdec);
 
 static inline
 bool ctf_metadata_decoder_is_packet_version_valid(unsigned int major,
index 42e0532414f0d65670ce7898994f2ff0d9eea37e..41948b79e690561833398f4607ffdee6d604a974 100644 (file)
@@ -102,12 +102,13 @@ int ctf_fs_metadata_set_trace_class(
                .self_comp = self_comp,
                .clock_class_offset_s = config ? config->clock_class_offset_s : 0,
                .clock_class_offset_ns = config ? config->clock_class_offset_ns : 0,
+               .create_trace_class = true,
        };
        bt_logging_level log_level = ctf_fs_trace->log_level;
 
        file = get_file(ctf_fs_trace->path->str, log_level, self_comp);
        if (!file) {
-               BT_COMP_LOGE("Cannot create metadata file object");
+               BT_COMP_LOGE("Cannot create metadata file object.");
                ret = -1;
                goto end;
        }
@@ -115,15 +116,15 @@ int ctf_fs_metadata_set_trace_class(
        ctf_fs_trace->metadata->decoder = ctf_metadata_decoder_create(
                &decoder_config);
        if (!ctf_fs_trace->metadata->decoder) {
-               BT_COMP_LOGE("Cannot create metadata decoder object");
+               BT_COMP_LOGE("Cannot create metadata decoder object.");
                ret = -1;
                goto end;
        }
 
-       ret = ctf_metadata_decoder_decode(ctf_fs_trace->metadata->decoder,
-               file->fp);
+       ret = ctf_metadata_decoder_append_content(
+               ctf_fs_trace->metadata->decoder, file->fp);
        if (ret) {
-               BT_COMP_LOGE("Cannot decode metadata file");
+               BT_COMP_LOGE("Cannot update metadata decoder's content.");
                goto end;
        }
 
index e817165c4e6c4a12285f6e5a30726ab05896262c..62a3f8b60f3cb113ae1eb626b233a72986d03db3 100644 (file)
@@ -59,13 +59,14 @@ bt_component_class_query_method_status metadata_info_query(
                bt_self_component_class_source_as_self_component_class(self_comp_class_src);
        bt_value *result = NULL;
        const bt_value *path_value = NULL;
-       char *metadata_text = NULL;
        FILE *metadata_fp = NULL;
-       GString *g_metadata_text = NULL;
        int ret;
        int bo;
        const char *path;
        bool is_packetized;
+       struct ctf_metadata_decoder *decoder = NULL;
+       struct ctf_metadata_decoder_config decoder_cfg = { 0 };
+       enum ctf_metadata_decoder_status decoder_status;
 
        result = bt_value_map_create();
        if (!result) {
@@ -107,69 +108,36 @@ bt_component_class_query_method_status metadata_info_query(
                goto error;
        }
 
-       is_packetized = ctf_metadata_decoder_is_packetized(metadata_fp,
+       ret = ctf_metadata_decoder_is_packetized(metadata_fp, &is_packetized,
                &bo, log_level, NULL);
-
-       if (is_packetized) {
-               ret = ctf_metadata_decoder_packetized_file_stream_to_buf(
-                       metadata_fp, &metadata_text, bo, NULL, NULL,
-                       log_level, NULL);
-               if (ret) {
-                       BT_COMP_CLASS_LOGE_APPEND_CAUSE(self_comp_class,
-                               "Cannot decode packetized metadata file: path=\"%s\"",
-                               path);
-                       goto error;
-               }
-       } else {
-               long filesize;
-
-               ret = fseek(metadata_fp, 0, SEEK_END);
-               if (ret) {
-                       BT_COMP_CLASS_LOGE_APPEND_CAUSE_ERRNO(self_comp_class,
-                               "Failed to seek to the end of the metadata file",
-                               ": path=\"%s\"", path);
-                       goto error;
-               }
-               filesize = ftell(metadata_fp);
-               if (filesize < 0) {
-                       BT_COMP_CLASS_LOGE_APPEND_CAUSE_ERRNO(self_comp_class,
-                               "Failed to get the current position in the metadata file",
-                               ": path=\"%s\"", path);
-                       goto error;
-               }
-               rewind(metadata_fp);
-               metadata_text = malloc(filesize + 1);
-               if (!metadata_text) {
-                       BT_COMP_CLASS_LOGE_APPEND_CAUSE(self_comp_class,
-                               "Cannot allocate buffer for metadata text.");
-                       goto error;
-               }
-
-               if (fread(metadata_text, filesize, 1, metadata_fp) != 1) {
-                       BT_COMP_CLASS_LOGE_APPEND_CAUSE_ERRNO(self_comp_class,
-                               "Cannot read metadata file", ": path=\"%s\"",
-                               path);
-                       goto error;
-               }
-
-               metadata_text[filesize] = '\0';
+       if (ret) {
+               BT_COMP_CLASS_LOGE_APPEND_CAUSE(self_comp_class,
+                       "Cannot check whether or not the metadata stream is packetized: path=\"%s\".",
+                       path);
+               goto error;
        }
 
-       g_metadata_text = g_string_new(NULL);
-       if (!g_metadata_text) {
+       decoder_cfg.log_level = log_level;
+       decoder_cfg.keep_plain_text = true;
+       decoder = ctf_metadata_decoder_create(&decoder_cfg);
+       if (!decoder) {
+               BT_COMP_CLASS_LOGE_APPEND_CAUSE(self_comp_class,
+                       "Cannot create metadata decoder: path=\"%s\".", path);
                goto error;
        }
 
-       if (strncmp(metadata_text, METADATA_TEXT_SIG,
-                       sizeof(METADATA_TEXT_SIG) - 1) != 0) {
-               g_string_assign(g_metadata_text, METADATA_TEXT_SIG);
-               g_string_append(g_metadata_text, " */\n\n");
+       rewind(metadata_fp);
+       decoder_status = ctf_metadata_decoder_append_content(decoder,
+               metadata_fp);
+       if (decoder_status) {
+               BT_COMP_CLASS_LOGE_APPEND_CAUSE(self_comp_class,
+                       "Cannot update metadata decoder's content: path=\"%s\".",
+                       path);
+               goto error;
        }
 
-       g_string_append(g_metadata_text, metadata_text);
-
        ret = bt_value_map_insert_string_entry(result, "text",
-               g_metadata_text->str);
+               ctf_metadata_decoder_get_text(decoder));
        if (ret) {
                BT_COMP_CLASS_LOGE_APPEND_CAUSE(self_comp_class,
                        "Cannot insert metadata text into query result.");
@@ -195,11 +163,7 @@ error:
        }
 
 end:
-       free(metadata_text);
-
-       if (g_metadata_text) {
-               g_string_free(g_metadata_text, TRUE);
-       }
+       ctf_metadata_decoder_destroy(decoder);
 
        if (metadata_fp) {
                fclose(metadata_fp);
index db1dfd7d41025c076dac324fc107f09ff9e745c2..61227141b4079883e6aeee25262dab7c0fb277a4 100644 (file)
@@ -217,10 +217,11 @@ enum lttng_live_iterator_status lttng_live_metadata_update(
        }
 
        /*
-        * The call to ctf_metadata_decoder_decode will append new metadata to
-        * our current trace class.
+        * The call to ctf_metadata_decoder_append_content() will append
+        * new metadata to our current trace class.
         */
-       decoder_status = ctf_metadata_decoder_decode(metadata->decoder, fp);
+       decoder_status = ctf_metadata_decoder_append_content(
+               metadata->decoder, fp);
        switch (decoder_status) {
        case CTF_METADATA_DECODER_STATUS_OK:
                if (!trace->trace_class) {
@@ -288,6 +289,7 @@ int lttng_live_metadata_create_stream(struct lttng_live_session *session,
                .self_comp = session->self_comp,
                .clock_class_offset_s = 0,
                .clock_class_offset_ns = 0,
+               .create_trace_class = true,
        };
 
        metadata = g_new0(struct lttng_live_metadata, 1);
This page took 0.033317 seconds and 4 git commands to generate.