ctf: add metadata decoder config. and `strict-metadata` param in src.ctf.fs
authorPhilippe Proulx <eeppeliteloop@gmail.com>
Wed, 14 Jun 2017 15:15:00 +0000 (11:15 -0400)
committerJérémie Galarneau <jeremie.galarneau@efficios.com>
Wed, 14 Jun 2017 21:38:08 +0000 (17:38 -0400)
The common metadata decoder now accepts an optional configuration
structure. The offset (seconds and nanoseconds) to apply to all the
clock classes is found in there, as well as a new option which makes the
decoder strict. In strict mode, the decoder does not allow the decoded
metadata stream to be off semantically. For example, in strict mode,
clock classes named `monotonic` are not forced to be absolute when it is
detected that the stream was produced by an LTTng tracer.

It's not expected that the strict mode be something that any user would
want under normal conditions because the non-strict mode fixes errors
made by known tracers to make things work for the other components of
the graph. As such, there's no quick --strict option in the CLI's
`convert` command: the user can instantiate its own source.ctf.fs
component with --component for this and pass the options with --params:

    babeltrace -c src.ctf.fs --path ~/my-traces/trace -p strict-metadata=yes

I'm also fixing the parameter names and types for the clock class
offsets, both in the CLI and in source.ctf.fs, so that all the project's
modules are in sync regarding this. The parameters are now
`clock-class-offset-s` and `clock-class-offset-ns`, and with the
`convert` command, they are set with resp. --clock-offset and
--clock-offset-ns. They used to be passed to the `run` command as string
values (using --key and --value), but now they are part of the
component's --params option so that they are recognized as constant
integer values (even if negative).

Signed-off-by: Philippe Proulx <eeppeliteloop@gmail.com>
Signed-off-by: Jérémie Galarneau <jeremie.galarneau@efficios.com>
cli/babeltrace-cfg-cli-args.c
plugins/ctf/common/metadata/ast.h
plugins/ctf/common/metadata/decoder.c
plugins/ctf/common/metadata/decoder.h
plugins/ctf/common/metadata/visitor-generate-ir.c
plugins/ctf/fs-src/fs.c
plugins/ctf/fs-src/fs.h
plugins/ctf/fs-src/metadata.c
plugins/ctf/fs-src/metadata.h
plugins/ctf/lttng-live/metadata.c

index cd8fb1892d831656017865e400f0918c941c715a..541329ab136bc53bfc53bb1cdf221ca9419cd2d8 100644 (file)
@@ -4093,7 +4093,8 @@ struct bt_config *bt_config_convert_from_args(int argc, const char *argv[],
                        break;
                case OPT_CLOCK_FORCE_CORRELATE:
                        append_implicit_component_param(
-                               &implicit_muxer_args, "assume-absolute-clock-classes", "yes");
+                               &implicit_muxer_args,
+                               "assume-absolute-clock-classes", "yes");
                        break;
                case OPT_CLOCK_GMT:
                        append_implicit_component_param(
@@ -4102,8 +4103,9 @@ struct bt_config *bt_config_convert_from_args(int argc, const char *argv[],
                        break;
                case OPT_CLOCK_OFFSET:
                        base_implicit_ctf_input_args.exists = true;
-                       ret = append_implicit_component_extra_param(
-                               &base_implicit_ctf_input_args, "clock-offset-cycles", arg);
+                       append_implicit_component_param(
+                                       &implicit_muxer_args,
+                                       "clock-class-offset-s", arg);
                        if (ret) {
                                goto error;
                        }
@@ -4112,7 +4114,7 @@ struct bt_config *bt_config_convert_from_args(int argc, const char *argv[],
                        base_implicit_ctf_input_args.exists = true;
                        ret = append_implicit_component_extra_param(
                                &base_implicit_ctf_input_args,
-                               "clock-offset-ns", arg);
+                               "clock-class-offset-ns", arg);
                        if (ret) {
                                goto error;
                        }
index 737158cd0fcd73f863b4d2b3ecf57cbec3bc07d7..74bcde9f00d3d1adf8ecd63de3dbc837ee276901 100644 (file)
@@ -24,6 +24,8 @@
 #include <babeltrace/ctf-ir/trace.h>
 #include <babeltrace/babeltrace-internal.h>
 
+#include "decoder.h"
+
 // the parameter name (of the reentrant 'yyparse' function)
 // data is a pointer to a 'SParserParam' structure
 //#define YYPARSE_PARAM        scanner
@@ -309,7 +311,8 @@ const char *node_type(struct ctf_node *node);
 
 BT_HIDDEN
 struct ctf_visitor_generate_ir *ctf_visitor_generate_ir_create(
-               int64_t clock_class_offset_ns, const char *name);
+               const struct ctf_metadata_decoder_config *config,
+               const char *name);
 
 void ctf_visitor_generate_ir_destroy(struct ctf_visitor_generate_ir *visitor);
 
index 8837da7769e168019a7dd22dbb2ad1db136ccbae..aad6aa1e571c2bd54bbe1d2087d630d8e6742d30 100644 (file)
@@ -41,6 +41,7 @@ struct ctf_metadata_decoder {
        uint8_t uuid[16];
        bool is_uuid_set;
        int bo;
+       struct ctf_metadata_decoder_config config;
 };
 
 struct packet_header {
@@ -327,22 +328,35 @@ int ctf_metadata_decoder_packetized_file_stream_to_buf(
 
 BT_HIDDEN
 struct ctf_metadata_decoder *ctf_metadata_decoder_create(
-               int64_t clock_class_offset_ns, const char *name)
+               const struct ctf_metadata_decoder_config *config,
+               const char *name)
 {
        struct ctf_metadata_decoder *mdec =
                g_new0(struct ctf_metadata_decoder, 1);
+       struct ctf_metadata_decoder_config default_config = {
+               .clock_class_offset_s = 0,
+               .clock_class_offset_ns = 0,
+               .strict = false,
+       };
+
+       if (!config) {
+               config = &default_config;
+       }
 
        BT_LOGD("Creating CTF metadata decoder: "
-               "clock-class-offset-ns=%" PRId64 ", name=\"%s\"",
-               clock_class_offset_ns, name);
+               "clock-class-offset-s=%" PRId64 ", "
+               "clock-class-offset-ns=%" PRId64 ", "
+               "strict=%d, name=\"%s\"",
+               config->clock_class_offset_s, config->clock_class_offset_ns,
+               config->strict, name);
 
        if (!mdec) {
                BT_LOGE_STR("Failed to allocate one CTF metadata decoder.");
                goto end;
        }
 
-       mdec->visitor = ctf_visitor_generate_ir_create(clock_class_offset_ns,
-                       name);
+       mdec->config = *config;
+       mdec->visitor = ctf_visitor_generate_ir_create(config, name);
        if (!mdec->visitor) {
                BT_LOGE("Failed to create a CTF IR metadata AST visitor: "
                        "mdec-addr=%p", mdec);
@@ -351,9 +365,12 @@ struct ctf_metadata_decoder *ctf_metadata_decoder_create(
                goto end;
        }
 
-       BT_LOGD("Created CTF metadata decoder: "
-               "clock-class-offset-ns=%" PRId64 ", name=\"%s\", addr=%p",
-               clock_class_offset_ns, name, mdec);
+       BT_LOGD("Creating CTF metadata decoder: "
+               "clock-class-offset-s=%" PRId64 ", "
+               "clock-class-offset-ns=%" PRId64 ", "
+               "strict=%d, name=\"%s\", addr=%p",
+               config->clock_class_offset_s, config->clock_class_offset_ns,
+               config->strict, name, mdec);
 
 end:
        return mdec;
index 959bdd4002f5336130e91fede02e53646225caa3..b7a9507752894d5866e8bcc5e2db7f254a565678 100644 (file)
@@ -16,6 +16,7 @@
  */
 
 #include <stdint.h>
+#include <stdbool.h>
 
 struct bt_ctf_trace;
 
@@ -31,16 +32,23 @@ enum ctf_metadata_decoder_status {
        CTF_METADATA_DECODER_STATUS_IR_VISITOR_ERROR    = -4,
 };
 
+/* Decoding configuration */
+struct ctf_metadata_decoder_config {
+       int64_t clock_class_offset_s;
+       int64_t clock_class_offset_ns;
+       bool strict;
+};
+
 /*
- * Creates a CTF metadata decoder. `clock_class_offset_ns` is an
- * offset to apply to the decoded clock classes's offsets. `name` is
- * this decoder's trace's name.
+ * Creates a CTF metadata decoder. `name` is this decoder's trace's
+ * name.
  *
  * Returns `NULL` on error.
  */
 BT_HIDDEN
 struct ctf_metadata_decoder *ctf_metadata_decoder_create(
-               int64_t clock_class_offset_ns, const char *name);
+               const struct ctf_metadata_decoder_config *config,
+               const char *name);
 
 /*
  * Destroys a CTF metadata decoder that you created with
index 19a67896bfe936b850d7b41d75c66cf2f71c6cc0..0ebb0157ae28215c670f6ed35ef5a4bde7c772e0 100644 (file)
@@ -54,6 +54,7 @@
 #include "scanner.h"
 #include "parser.h"
 #include "ast.h"
+#include "decoder.h"
 
 /* Bit value (left shift) */
 #define _BV(_val)              (1 << (_val))
@@ -200,9 +201,6 @@ struct ctx {
        /* 1 if this is an LTTng trace */
        bool is_lttng;
 
-       /* Offset (ns) to apply to clock classes on creation */
-       int64_t clock_class_offset_ns;
-
        /* Eventual name suffix of the trace to set */
        char *trace_name_suffix;
 
@@ -218,6 +216,9 @@ struct ctx {
         * int64_t -> struct bt_ctf_stream_class *
         */
        GHashTable *stream_classes;
+
+       /* Config passed by the user */
+       struct ctf_metadata_decoder_config decoder_config;
 };
 
 /*
@@ -601,11 +602,14 @@ end:
  */
 static
 struct ctx *ctx_create(struct bt_ctf_trace *trace,
-               int64_t clock_class_offset_ns, const char *trace_name_suffix)
+               const struct ctf_metadata_decoder_config *decoder_config,
+               const char *trace_name_suffix)
 {
        struct ctx *ctx = NULL;
        struct ctx_decl_scope *scope = NULL;
 
+       assert(decoder_config);
+
        ctx = g_new0(struct ctx, 1);
        if (!ctx) {
                BT_LOGE_STR("Failed to allocate one visitor context.");
@@ -638,7 +642,7 @@ struct ctx *ctx_create(struct bt_ctf_trace *trace,
        ctx->current_scope = scope;
        scope = NULL;
        ctx->trace_bo = BT_CTF_BYTE_ORDER_NATIVE;
-       ctx->clock_class_offset_ns = clock_class_offset_ns;
+       ctx->decoder_config = *decoder_config;
        return ctx;
 
 error:
@@ -4348,12 +4352,14 @@ int visit_env(struct ctx *ctx, struct ctf_node *node)
                                goto error;
                        }
 
-                       if (strcmp(left, "tracer_name") == 0) {
-                               if (strncmp(right, "lttng", 5) == 0) {
-                                       BT_LOGI("Detected LTTng trace from `%s` environment value: "
-                                               "tracer-name=\"%s\"",
-                                               left, right);
-                                       ctx->is_lttng = 1;
+                       if (!ctx->decoder_config.strict) {
+                               if (strcmp(left, "tracer_name") == 0) {
+                                       if (strncmp(right, "lttng", 5) == 0) {
+                                               BT_LOGI("Non-strict mode: detected LTTng trace from `%s` environment value: "
+                                                       "tracer-name=\"%s\"",
+                                                       left, right);
+                                               ctx->is_lttng = 1;
+                                       }
                                }
                        }
 
@@ -4770,6 +4776,7 @@ int apply_clock_class_offset(struct ctx *ctx, struct bt_ctf_clock_class *clock)
        int ret;
        uint64_t freq;
        int64_t offset_cycles;
+       int64_t offset_to_apply;
 
        freq = bt_ctf_clock_class_get_frequency(clock);
        if (freq == -1ULL) {
@@ -4785,7 +4792,10 @@ int apply_clock_class_offset(struct ctx *ctx, struct bt_ctf_clock_class *clock)
                goto end;
        }
 
-       offset_cycles += cycles_from_ns(freq, ctx->clock_class_offset_ns);
+       offset_to_apply =
+               ctx->decoder_config.clock_class_offset_s * 1000000000LL +
+               ctx->decoder_config.clock_class_offset_ns;
+       offset_cycles += cycles_from_ns(freq, offset_to_apply);
        ret = bt_ctf_clock_class_set_offset_cycles(clock, offset_cycles);
 
 end:
@@ -5033,7 +5043,8 @@ end:
 
 BT_HIDDEN
 struct ctf_visitor_generate_ir *ctf_visitor_generate_ir_create(
-               int64_t clock_class_offset_ns, const char *name)
+               const struct ctf_metadata_decoder_config *decoder_config,
+               const char *name)
 {
        int ret;
        struct ctx *ctx = NULL;
@@ -5053,7 +5064,7 @@ struct ctf_visitor_generate_ir *ctf_visitor_generate_ir_create(
        }
 
        /* Create visitor's context */
-       ctx = ctx_create(trace, clock_class_offset_ns, name);
+       ctx = ctx_create(trace, decoder_config, name);
        if (!ctx) {
                BT_LOGE_STR("Cannot create visitor's context.");
                goto error;
index f6a9f791d983695352151e1f8e2bca08a38c5873..aa1d6b1f40481809764fdaf9d38c1f483f49bbde 100644 (file)
@@ -898,7 +898,7 @@ end:
 
 BT_HIDDEN
 struct ctf_fs_trace *ctf_fs_trace_create(const char *path, const char *name,
-               struct metadata_overrides *overrides)
+               struct ctf_fs_metadata_config *metadata_config)
 {
        struct ctf_fs_trace *ctf_fs_trace;
        int ret;
@@ -929,7 +929,7 @@ struct ctf_fs_trace *ctf_fs_trace_create(const char *path, const char *name,
                goto error;
        }
 
-       ret = ctf_fs_metadata_set_trace(ctf_fs_trace, overrides);
+       ret = ctf_fs_metadata_set_trace(ctf_fs_trace, metadata_config);
        if (ret) {
                goto error;
        }
@@ -1149,10 +1149,6 @@ int create_ctf_fs_traces(struct ctf_fs_component *ctf_fs,
        GList *trace_names = NULL;
        GList *tp_node;
        GList *tn_node;
-       struct metadata_overrides metadata_overrides = {
-               .clock_offset_s = ctf_fs->options.clock_offset,
-               .clock_offset_ns = ctf_fs->options.clock_offset_ns,
-       };
 
        norm_path = bt_common_normalize_path(path_param, NULL);
        if (!norm_path) {
@@ -1185,7 +1181,7 @@ int create_ctf_fs_traces(struct ctf_fs_component *ctf_fs,
                GString *trace_name = tn_node->data;
 
                ctf_fs_trace = ctf_fs_trace_create(trace_path->str,
-                               trace_name->str, &metadata_overrides);
+                               trace_name->str, &ctf_fs->metadata_config);
                if (!ctf_fs_trace) {
                        BT_LOGE("Cannot create trace for `%s`.",
                                trace_path->str);
@@ -1266,31 +1262,41 @@ struct ctf_fs_component *ctf_fs_create(struct bt_private_component *priv_comp,
        ret = bt_value_string_get(value, &path_param);
        assert(ret == 0);
        BT_PUT(value);
-       value = bt_value_map_get(params, "offset-s");
+       value = bt_value_map_get(params, "clock-class-offset-s");
        if (value) {
-               int64_t offset;
+               if (!bt_value_is_integer(value)) {
+                       BT_LOGE("clock-class-offset-s should be an integer");
+                       goto error;
+               }
+               ret = bt_value_integer_get(value,
+                       &ctf_fs->metadata_config.clock_class_offset_s);
+               assert(ret == 0);
+               BT_PUT(value);
+       }
 
+       value = bt_value_map_get(params, "clock-class-offset-ns");
+       if (value) {
                if (!bt_value_is_integer(value)) {
-                       BT_LOGE("offset-s should be an integer");
+                       BT_LOGE("clock-class-offset-ns should be an integer");
                        goto error;
                }
-               ret = bt_value_integer_get(value, &offset);
+               ret = bt_value_integer_get(value,
+                       &ctf_fs->metadata_config.clock_class_offset_ns);
                assert(ret == 0);
-               ctf_fs->options.clock_offset = offset;
                BT_PUT(value);
        }
 
-       value = bt_value_map_get(params, "offset-ns");
+       value = bt_value_map_get(params, "strict-metadata");
        if (value) {
-               int64_t offset;
+               bt_bool strict;
 
-               if (!bt_value_is_integer(value)) {
-                       BT_LOGE("offset-ns should be an integer");
+               if (!bt_value_is_bool(value)) {
+                       BT_LOGE("strict-metadata should be a boolean");
                        goto error;
                }
-               ret = bt_value_integer_get(value, &offset);
+               ret = bt_value_bool_get(value, &strict);
                assert(ret == 0);
-               ctf_fs->options.clock_offset_ns = offset;
+               ctf_fs->metadata_config.strict = !!strict;
                BT_PUT(value);
        }
 
index c5c12fb4e6b22a13815053b5430bf59f4c73a982..13b0d07c6b5e802e64d50f38bef5523894ca7d37 100644 (file)
@@ -60,11 +60,6 @@ struct ctf_fs_metadata {
        int bo;
 };
 
-struct ctf_fs_component_options {
-       int64_t clock_offset;
-       int64_t clock_offset_ns;
-};
-
 struct ctf_fs_component {
        /* Weak, guaranteed to exist */
        struct bt_private_component *priv_comp;
@@ -75,7 +70,7 @@ struct ctf_fs_component {
        /* Array of struct ctf_fs_trace *, owned by this */
        GPtrArray *traces;
 
-       struct ctf_fs_component_options options;
+       struct ctf_fs_metadata_config metadata_config;
 };
 
 struct ctf_fs_trace {
@@ -143,7 +138,7 @@ struct bt_value *ctf_fs_query(struct bt_component_class *comp_class,
 
 BT_HIDDEN
 struct ctf_fs_trace *ctf_fs_trace_create(const char *path, const char *name,
-               struct metadata_overrides *overrides);
+               struct ctf_fs_metadata_config *config);
 
 BT_HIDDEN
 void ctf_fs_trace_destroy(struct ctf_fs_trace *trace);
index 91465cb98bf6d7462acc0747599368616df4cf16..75e962f2d0bb586c61ab86a505da4deb0762846e 100644 (file)
@@ -40,8 +40,6 @@
 #define BT_LOG_TAG "PLUGIN-CTF-FS-METADATA-SRC"
 #include "logging.h"
 
-#define NSEC_PER_SEC 1000000000LL
-
 BT_HIDDEN
 FILE *ctf_fs_metadata_open_file(const char *trace_path)
 {
@@ -99,12 +97,16 @@ end:
 }
 
 int ctf_fs_metadata_set_trace(struct ctf_fs_trace *ctf_fs_trace,
-               struct metadata_overrides *overrides)
+               struct ctf_fs_metadata_config *config)
 {
        int ret = 0;
        struct ctf_fs_file *file = NULL;
        struct ctf_metadata_decoder *metadata_decoder = NULL;
-       int64_t clock_offset_adjustment = 0;
+       struct ctf_metadata_decoder_config decoder_config = {
+               .clock_class_offset_s = config->clock_class_offset_s,
+               .clock_class_offset_ns = config->clock_class_offset_ns,
+               .strict = config->strict,
+       };
 
        file = get_file(ctf_fs_trace->path->str);
        if (!file) {
@@ -113,12 +115,7 @@ int ctf_fs_metadata_set_trace(struct ctf_fs_trace *ctf_fs_trace,
                goto end;
        }
 
-       if (overrides) {
-               clock_offset_adjustment =
-                       overrides->clock_offset_s * NSEC_PER_SEC +
-                       overrides->clock_offset_ns;
-       }
-       metadata_decoder = ctf_metadata_decoder_create(clock_offset_adjustment,
+       metadata_decoder = ctf_metadata_decoder_create(&decoder_config,
                ctf_fs_trace->name->str);
        if (!metadata_decoder) {
                BT_LOGE("Cannot create metadata decoder object");
index 112c681f4f181e11eef3c11e6ceb53f687fb9c48..9c573433cbcdebaf9d99b237bf1ab7819ab25da8 100644 (file)
 struct ctf_fs_trace;
 struct ctf_fs_metadata;
 
-struct metadata_overrides {
-       int64_t clock_offset_s;
-       int64_t clock_offset_ns;
+struct ctf_fs_metadata_config {
+       int64_t clock_class_offset_s;
+       int64_t clock_class_offset_ns;
+       bool strict;
 };
 
 BT_HIDDEN
@@ -46,7 +47,7 @@ void ctf_fs_metadata_fini(struct ctf_fs_metadata *metadata);
 
 BT_HIDDEN
 int ctf_fs_metadata_set_trace(struct ctf_fs_trace *ctf_fs_trace,
-               struct metadata_overrides *overrides);
+               struct ctf_fs_metadata_config *config);
 
 BT_HIDDEN
 FILE *ctf_fs_metadata_open_file(const char *trace_path);
index 1adc81c1553bd893319738aae900c54e1b5c4534..7fec74add2bdb2e2bba8a63c222512a503081d4e 100644 (file)
@@ -248,7 +248,7 @@ int lttng_live_metadata_create_stream(struct lttng_live_session *session,
        if (!match) {
                goto error;
        }
-       metadata->decoder = ctf_metadata_decoder_create(0,
+       metadata->decoder = ctf_metadata_decoder_create(NULL,
                match);
        if (!metadata->decoder) {
                goto error;
This page took 0.034364 seconds and 4 git commands to generate.