The capture_index corresponds to the index at which the capture is
expected on reception of the trigger payload from the tracer.
This field will be populated on reception of the trigger on the sessiond
side and is internal use only.
This is necessary due to the fact that a single condition can have
multiple capture actions associated to it with capture descriptor
duplicate. We plan on forming an ordered set of these capture
descriptors and configure only the set for the enabler. This ensures
that we capture only what is required on the tracer side. On reception,
each capture descriptor will know the index at which the payload field
it corresponds to is situated.
In retrospect this is purely an optimization to prevent the tracer from
doing unnecessary work.
Initially this complexity was planned to be contained to the
lttng-sessiond, but since we now transfer the msgpack payload all the
way to liblttngctl we now have to carry this index all the way to
liblttng-ctl.
Signed-off-by: Jonathan Rajotte <jonathan.rajotte-julien@efficios.com>
Signed-off-by: Jérémie Galarneau <jeremie.galarneau@efficios.com>
Change-Id: Ie3309511347818f88c61c750723f21c73d82f80b
Depends-on: lttng-ust: I5a800fc92e588c2a6a0e26282b0ad5f31c044479
#include <lttng/condition/evaluation-internal.h>
#include <common/dynamic-array.h>
#include <lttng/condition/evaluation-internal.h>
#include <common/dynamic-array.h>
+struct lttng_capture_descriptor {
+ struct lttng_event_expr *event_expression;
+ struct lttng_bytecode *bytecode;
+};
+
struct lttng_condition_event_rule {
struct lttng_condition parent;
struct lttng_event_rule *rule;
struct lttng_condition_event_rule {
struct lttng_condition parent;
struct lttng_event_rule *rule;
- /* Array of `struct lttng_event_expr *`. */
+ /* Array of `struct lttng_capture_descriptor *`. */
struct lttng_dynamic_pointer_array capture_descriptors;
};
struct lttng_dynamic_pointer_array capture_descriptors;
};
{
int ret;
struct lttng_condition_event_rule *event_rule;
{
int ret;
struct lttng_condition_event_rule *event_rule;
+ enum lttng_condition_status status;
/* Used for iteration and communication (size matters). */
uint32_t i, capture_descr_count;
/* Used for iteration and communication (size matters). */
uint32_t i, capture_descr_count;
- capture_descr_count = lttng_dynamic_pointer_array_get_count(
- &event_rule->capture_descriptors);
+ status = lttng_condition_event_rule_get_capture_descriptor_count(
+ condition, &capture_descr_count);
+ if (status != LTTNG_CONDITION_STATUS_OK) {
+ ret = -1;
+ goto end;
+ };
+
DBG("Serializing event rule condition's capture descriptor count: %" PRIu32,
capture_descr_count);
ret = lttng_dynamic_buffer_append(&payload->buffer, &capture_descr_count,
DBG("Serializing event rule condition's capture descriptor count: %" PRIu32,
capture_descr_count);
ret = lttng_dynamic_buffer_append(&payload->buffer, &capture_descr_count,
for (i = 0; i < capture_descr_count; i++) {
const struct lttng_event_expr *expr =
for (i = 0; i < capture_descr_count; i++) {
const struct lttng_event_expr *expr =
- lttng_dynamic_pointer_array_get_pointer(
- &event_rule->capture_descriptors, i);
+ lttng_condition_event_rule_get_capture_descriptor_at_index(
+ condition, i);
DBG("Serializing event rule condition's capture descriptor %" PRIu32,
i);
DBG("Serializing event rule condition's capture descriptor %" PRIu32,
i);
static
bool capture_descriptors_are_equal(
static
bool capture_descriptors_are_equal(
- const struct lttng_condition_event_rule *condition_a,
- const struct lttng_condition_event_rule *condition_b)
+ const struct lttng_condition *condition_a,
+ const struct lttng_condition *condition_b)
- size_t capture_descr_count_a;
- size_t capture_descr_count_b;
+ unsigned int capture_descr_count_a;
+ unsigned int capture_descr_count_b;
+ enum lttng_condition_status status;
- capture_descr_count_a = lttng_dynamic_pointer_array_get_count(
- &condition_a->capture_descriptors);
- capture_descr_count_b = lttng_dynamic_pointer_array_get_count(
- &condition_b->capture_descriptors);
+ status = lttng_condition_event_rule_get_capture_descriptor_count(
+ condition_a, &capture_descr_count_a);
+ if (status != LTTNG_CONDITION_STATUS_OK) {
+ goto not_equal;
+ }
+
+ status = lttng_condition_event_rule_get_capture_descriptor_count(
+ condition_b, &capture_descr_count_b);
+ if (status != LTTNG_CONDITION_STATUS_OK) {
+ goto not_equal;
+ }
if (capture_descr_count_a != capture_descr_count_b) {
goto not_equal;
if (capture_descr_count_a != capture_descr_count_b) {
goto not_equal;
for (i = 0; i < capture_descr_count_a; i++) {
const struct lttng_event_expr *expr_a =
for (i = 0; i < capture_descr_count_a; i++) {
const struct lttng_event_expr *expr_a =
- lttng_dynamic_pointer_array_get_pointer(
- &condition_a->capture_descriptors,
+ lttng_condition_event_rule_get_capture_descriptor_at_index(
+ condition_a,
i);
const struct lttng_event_expr *expr_b =
i);
const struct lttng_event_expr *expr_b =
- lttng_dynamic_pointer_array_get_pointer(
- &condition_b->capture_descriptors,
+ lttng_condition_event_rule_get_capture_descriptor_at_index(
+ condition_b,
i);
if (!lttng_event_expr_is_equal(expr_a, expr_b)) {
i);
if (!lttng_event_expr_is_equal(expr_a, expr_b)) {
- is_equal = capture_descriptors_are_equal(a, b);
+ is_equal = capture_descriptors_are_equal(_a, _b);
-void destroy_event_expr(void *ptr)
+void destroy_capture_descriptor(void *ptr)
- lttng_event_expr_destroy(ptr);
+ struct lttng_capture_descriptor *desc =
+ (struct lttng_capture_descriptor *) ptr;
+
+ lttng_event_expr_destroy(desc->event_expression);
+ free(desc->bytecode);
+ free(desc);
}
struct lttng_condition *lttng_condition_event_rule_create(
}
struct lttng_condition *lttng_condition_event_rule_create(
rule = NULL;
lttng_dynamic_pointer_array_init(&condition->capture_descriptors,
rule = NULL;
lttng_dynamic_pointer_array_init(&condition->capture_descriptors,
+ destroy_capture_descriptor);
parent = &condition->parent;
end:
parent = &condition->parent;
end:
struct lttng_condition_event_rule *event_rule_cond =
container_of(condition,
struct lttng_condition_event_rule, parent);
struct lttng_condition_event_rule *event_rule_cond =
container_of(condition,
struct lttng_condition_event_rule, parent);
+ struct lttng_capture_descriptor *descriptor = NULL;
/* Only accept l-values. */
if (!condition || !IS_EVENT_RULE_CONDITION(condition) || !expr ||
/* Only accept l-values. */
if (!condition || !IS_EVENT_RULE_CONDITION(condition) || !expr ||
+ descriptor = malloc(sizeof(*descriptor));
+ if (descriptor == NULL) {
+ status = LTTNG_CONDITION_STATUS_ERROR;
+ goto end;
+ }
+
+ descriptor->event_expression = expr;
+ descriptor->bytecode = NULL;
+
ret = lttng_dynamic_pointer_array_add_pointer(
ret = lttng_dynamic_pointer_array_add_pointer(
- &event_rule_cond->capture_descriptors, expr);
+ &event_rule_cond->capture_descriptors, descriptor);
if (ret) {
status = LTTNG_CONDITION_STATUS_ERROR;
goto end;
}
if (ret) {
status = LTTNG_CONDITION_STATUS_ERROR;
goto end;
}
+ /* Ownership is transfered to the internal capture_descriptors array */
+ descriptor = NULL;
const struct lttng_condition_event_rule,
parent);
const struct lttng_event_expr *expr = NULL;
const struct lttng_condition_event_rule,
parent);
const struct lttng_event_expr *expr = NULL;
+ struct lttng_capture_descriptor *desc = NULL;
+ unsigned int count;
+ enum lttng_condition_status status;
+
+ if (!condition || !IS_EVENT_RULE_CONDITION(condition)) {
+ goto end;
+ }
+
+ status = lttng_condition_event_rule_get_capture_descriptor_count(condition, &count);
+ if (status != LTTNG_CONDITION_STATUS_OK) {
+ goto end;
+ }
- if (!condition || !IS_EVENT_RULE_CONDITION(condition) ||
- index >= lttng_dynamic_pointer_array_get_count(
- &event_rule_cond->capture_descriptors)) {
- expr = lttng_dynamic_pointer_array_get_pointer(
+ desc = lttng_dynamic_pointer_array_get_pointer(
&event_rule_cond->capture_descriptors, index);
&event_rule_cond->capture_descriptors, index);
+ expr = desc->event_expression;