goto end;
}
- _MSG("Waiting for data availability");
- fflush(stdout);
-
/* Check for data availability */
do {
data_ret = lttng_data_pending(session_name);
*/
if (data_ret) {
usleep(DEFAULT_DATA_AVAILABILITY_WAIT_TIME);
- _MSG(".");
- fflush(stdout);
}
} while (data_ret != 0);
- MSG("");
-
end:
error:
return ret;
filter_expression, 0, NULL);
}
+/*
+ * Depending on the event, return a newly allocated JUL filter expression or
+ * NULL if not applicable.
+ *
+ * An event with NO loglevel and the name is * will return NULL.
+ */
+static char *set_jul_filter(const char *filter, struct lttng_event *ev)
+{
+ int err;
+ char *jul_filter = NULL;
+
+ assert(ev);
+
+ /* Don't add filter for the '*' event. */
+ if (ev->name[0] != '*') {
+ if (filter) {
+ err = asprintf(&jul_filter, "%s && logger_name == \"%s\"", filter,
+ ev->name);
+ } else {
+ err = asprintf(&jul_filter, "logger_name == \"%s\"", ev->name);
+ }
+ if (err < 0) {
+ PERROR("asprintf");
+ goto end;
+ }
+ }
+
+ /* Add loglevel filtering if any for the JUL domain. */
+ if (ev->loglevel_type != LTTNG_EVENT_LOGLEVEL_ALL) {
+ char *op;
+
+ if (ev->loglevel_type == LTTNG_EVENT_LOGLEVEL_RANGE) {
+ op = ">=";
+ } else {
+ op = "==";
+ }
+
+ if (filter) {
+ err = asprintf(&jul_filter, "%s && int_loglevel %s %d", filter, op,
+ ev->loglevel);
+ } else {
+ err = asprintf(&jul_filter, "int_loglevel %s %d", op,
+ ev->loglevel);
+ }
+ if (err < 0) {
+ PERROR("asprintf");
+ free(jul_filter);
+ jul_filter = NULL;
+ goto end;
+ }
+ }
+
+end:
+ return jul_filter;
+}
+
/*
* Enable event(s) for a channel, possibly with exclusions and a filter.
* If no event name is specified, all events are enabled.
*/
int lttng_enable_event_with_exclusions(struct lttng_handle *handle,
struct lttng_event *ev, const char *channel_name,
- const char *filter_expression,
+ const char *original_filter_expression,
int exclusion_count, char **exclusion_list)
{
struct lttcomm_session_msg lsm;
int ret = 0;
struct filter_parser_ctx *ctx = NULL;
FILE *fmem = NULL;
+ /*
+ * Cast as non-const since we may replace the filter expression
+ * by a dynamically allocated string. Otherwise, the original
+ * string is not modified.
+ */
+ char *filter_expression = (char *) original_filter_expression;
+ int free_filter_expression = 0;
if (handle == NULL || ev == NULL) {
return -LTTNG_ERR_INVALID;
lsm.u.enable.exclusion_count = exclusion_count;
lsm.u.enable.bytecode_len = 0;
- if (exclusion_count == 0 && filter_expression == NULL) {
- ret = lttng_ctl_ask_sessiond(&lsm, NULL);
- return ret;
+ /*
+ * For the JUL domain, a filter is enforced except for the enable all
+ * event. This is done to avoid having the event in all sessions thus
+ * filtering by logger name.
+ */
+ if (exclusion_count == 0 && filter_expression == NULL &&
+ handle->domain.type != LTTNG_DOMAIN_JUL) {
+ goto ask_sessiond;
}
/*
*/
/* Parse filter expression */
- if (filter_expression != NULL) {
+ if (filter_expression != NULL || handle->domain.type == LTTNG_DOMAIN_JUL) {
+ if (handle->domain.type == LTTNG_DOMAIN_JUL) {
+ char *jul_filter;
+
+ /* Setup JUL filter if needed. */
+ jul_filter = set_jul_filter(filter_expression, ev);
+ if (!jul_filter && !filter_expression) {
+ /* No JUL and no filter, just skip everything below. */
+ goto ask_sessiond;
+ } else {
+ /*
+ * With a JUL filter, the original filter has been added to it
+ * thus replace the filter expression.
+ */
+ filter_expression = jul_filter;
+ free_filter_expression = 1;
+ }
+ }
/*
* casting const to non-const, as the underlying function will
lsm.u.enable.bytecode_len = sizeof(ctx->bytecode->b)
+ bytecode_get_len(&ctx->bytecode->b);
- }
-
- /* Allocate variable length data */
- if (lsm.u.enable.exclusion_count != 0) {
- varlen_data = zmalloc(lsm.u.enable.bytecode_len
- + LTTNG_SYMBOL_NAME_LEN * exclusion_count);
- if (!varlen_data) {
- ret = -LTTNG_ERR_EXCLUSION_NOMEM;
- goto varlen_alloc_error;
- }
- /* Put exclusion names first in the data */
- while (exclusion_count--) {
- strncpy(varlen_data + LTTNG_SYMBOL_NAME_LEN * exclusion_count,
- *(exclusion_list + exclusion_count),
- LTTNG_SYMBOL_NAME_LEN);
- }
- /* Add filter bytecode next */
- if (lsm.u.enable.bytecode_len != 0) {
- memcpy(varlen_data + LTTNG_SYMBOL_NAME_LEN * lsm.u.enable.exclusion_count,
- &ctx->bytecode->b,
- lsm.u.enable.bytecode_len);
- }
- } else {
- /* no exclusions - use the already allocated filter bytecode */
- varlen_data = (char *)(&ctx->bytecode->b);
+ lsm.u.enable.expression_len = strlen(filter_expression) + 1;
+ }
+
+ varlen_data = zmalloc(lsm.u.enable.bytecode_len
+ + lsm.u.enable.expression_len
+ + LTTNG_SYMBOL_NAME_LEN * exclusion_count);
+ if (!varlen_data) {
+ ret = -LTTNG_ERR_EXCLUSION_NOMEM;
+ goto varlen_alloc_error;
+ }
+ /* Put exclusion names first in the data */
+ while (exclusion_count--) {
+ strncpy(varlen_data + LTTNG_SYMBOL_NAME_LEN * exclusion_count,
+ *(exclusion_list + exclusion_count),
+ LTTNG_SYMBOL_NAME_LEN);
+ }
+ /* Add filter expression next */
+ if (lsm.u.enable.expression_len != 0) {
+ memcpy(varlen_data
+ + LTTNG_SYMBOL_NAME_LEN * lsm.u.enable.exclusion_count,
+ filter_expression,
+ lsm.u.enable.expression_len);
+ }
+ /* Add filter bytecode next */
+ if (lsm.u.enable.bytecode_len != 0) {
+ memcpy(varlen_data
+ + LTTNG_SYMBOL_NAME_LEN * lsm.u.enable.exclusion_count
+ + lsm.u.enable.expression_len,
+ &ctx->bytecode->b,
+ lsm.u.enable.bytecode_len);
}
ret = lttng_ctl_ask_sessiond_varlen(&lsm, varlen_data,
(LTTNG_SYMBOL_NAME_LEN * lsm.u.enable.exclusion_count) +
- lsm.u.enable.bytecode_len, NULL);
-
- if (lsm.u.enable.exclusion_count != 0) {
- free(varlen_data);
- }
+ lsm.u.enable.bytecode_len + lsm.u.enable.expression_len,
+ NULL);
+ free(varlen_data);
varlen_alloc_error:
if (filter_expression) {
if (fclose(fmem) != 0) {
perror("fclose");
}
+ if (free_filter_expression) {
+ /*
+ * The filter expression has been replaced and must be
+ * freed as it is not the original filter expression
+ * received as a parameter.
+ */
+ free(filter_expression);
+ }
}
return ret;
perror("fclose");
}
return ret;
+
+ask_sessiond:
+ ret = lttng_ctl_ask_sessiond(&lsm, NULL);
+ return ret;
}
/*
lsm.cmd_type = LTTNG_CREATE_SESSION_LIVE;
lttng_ctl_copy_string(lsm.session.name, name, sizeof(lsm.session.name));
- size = uri_parse_str_urls(url, NULL, &uris);
- if (size <= 0) {
- ret = -LTTNG_ERR_INVALID;
- goto end;
- }
+ if (url) {
+ size = uri_parse_str_urls(url, NULL, &uris);
+ if (size <= 0) {
+ ret = -LTTNG_ERR_INVALID;
+ goto end;
+ }
- /* file:// is not accepted for live session. */
- if (uris[0].dtype == LTTNG_DST_PATH) {
- ret = -LTTNG_ERR_INVALID;
- goto end;
+ /* file:// is not accepted for live session. */
+ if (uris[0].dtype == LTTNG_DST_PATH) {
+ ret = -LTTNG_ERR_INVALID;
+ goto end;
+ }
+ } else {
+ size = 0;
}
lsm.u.session_live.nb_uri = size;