X-Git-Url: https://git.lttng.org/?a=blobdiff_plain;f=src%2Fcommon%2Factions%2Fstop-session.c;h=fa2c77b1352cf3bff466c89cc627602cd28ed279;hb=a0377dfefe40662ba7d68617bce6ff467114136c;hp=33077b6766d0773ca9ed0ddf87b6072e7bf1794c;hpb=c0a66c84b5b2484b75798aec7543b680b4d4ab6c;p=lttng-tools.git diff --git a/src/common/actions/stop-session.c b/src/common/actions/stop-session.c index 33077b676..fa2c77b13 100644 --- a/src/common/actions/stop-session.c +++ b/src/common/actions/stop-session.c @@ -5,21 +5,24 @@ * */ -#include #include #include +#include #include +#include +#include #include #include #define IS_STOP_SESSION_ACTION(action) \ - (lttng_action_get_type_const(action) == LTTNG_ACTION_TYPE_STOP_SESSION) + (lttng_action_get_type(action) == LTTNG_ACTION_TYPE_STOP_SESSION) struct lttng_action_stop_session { struct lttng_action parent; /* Owned by this. */ char *session_name; + struct lttng_rate_policy *policy; }; struct lttng_action_stop_session_comm { @@ -30,14 +33,19 @@ struct lttng_action_stop_session_comm { * Variable data: * * - session name (null terminated) + * - policy */ char data[]; } LTTNG_PACKED; +static const struct lttng_rate_policy * +lttng_action_stop_session_internal_get_rate_policy( + const struct lttng_action *action); + static struct lttng_action_stop_session *action_stop_session_from_action( struct lttng_action *action) { - assert(action); + LTTNG_ASSERT(action); return container_of(action, struct lttng_action_stop_session, parent); } @@ -45,7 +53,7 @@ static struct lttng_action_stop_session *action_stop_session_from_action( static const struct lttng_action_stop_session * action_stop_session_from_action_const(const struct lttng_action *action) { - assert(action); + LTTNG_ASSERT(action); return container_of(action, struct lttng_action_stop_session, parent); } @@ -84,13 +92,13 @@ static bool lttng_action_stop_session_is_equal( b = action_stop_session_from_action_const(_b); /* Action is not valid if this is not true. */ - assert(a->session_name); - assert(b->session_name); + LTTNG_ASSERT(a->session_name); + LTTNG_ASSERT(b->session_name); if (strcmp(a->session_name, b->session_name)) { goto end; } - is_equal = true; + is_equal = lttng_rate_policy_is_equal(a->policy, b->policy); end: return is_equal; } @@ -103,12 +111,12 @@ static int lttng_action_stop_session_serialize( size_t session_name_len; int ret; - assert(action); - assert(payload); + LTTNG_ASSERT(action); + LTTNG_ASSERT(payload); action_stop_session = action_stop_session_from_action(action); - assert(action_stop_session->session_name); + LTTNG_ASSERT(action_stop_session->session_name); DBG("Serializing stop session action: session-name: %s", action_stop_session->session_name); @@ -130,6 +138,12 @@ static int lttng_action_stop_session_serialize( goto end; } + ret = lttng_rate_policy_serialize(action_stop_session->policy, payload); + if (ret) { + ret = -1; + goto end; + } + ret = 0; end: return ret; @@ -145,6 +159,7 @@ static void lttng_action_stop_session_destroy(struct lttng_action *action) action_stop_session = action_stop_session_from_action(action); + lttng_rate_policy_destroy(action_stop_session->policy); free(action_stop_session->session_name); free(action_stop_session); @@ -156,26 +171,43 @@ ssize_t lttng_action_stop_session_create_from_payload( struct lttng_payload_view *view, struct lttng_action **p_action) { - ssize_t consumed_len; + ssize_t consumed_len, ret; const struct lttng_action_stop_session_comm *comm; const char *session_name; - struct lttng_action *action; + struct lttng_action *action = NULL; enum lttng_action_status status; - - action = lttng_action_stop_session_create(); - if (!action) { - consumed_len = -1; - goto end; - } + struct lttng_rate_policy *policy = NULL; comm = (typeof(comm)) view->buffer.data; session_name = (const char *) &comm->data; + /* Session name. */ if (!lttng_buffer_view_contains_string( &view->buffer, session_name, comm->session_name_len)) { consumed_len = -1; goto end; } + consumed_len = sizeof(*comm) + comm->session_name_len; + + /* Rate policy. */ + { + struct lttng_payload_view policy_view = + lttng_payload_view_from_view( + view, consumed_len, -1); + ret = lttng_rate_policy_create_from_payload( + &policy_view, &policy); + if (ret < 0) { + consumed_len = -1; + goto end; + } + consumed_len += ret; + } + + action = lttng_action_stop_session_create(); + if (!action) { + consumed_len = -1; + goto end; + } status = lttng_action_stop_session_set_session_name( action, session_name); @@ -184,19 +216,90 @@ ssize_t lttng_action_stop_session_create_from_payload( goto end; } - consumed_len = sizeof(*comm) + comm->session_name_len; + LTTNG_ASSERT(policy); + status = lttng_action_stop_session_set_rate_policy(action, policy); + if (status != LTTNG_ACTION_STATUS_OK) { + consumed_len = -1; + goto end; + } + *p_action = action; action = NULL; end: + lttng_rate_policy_destroy(policy); lttng_action_stop_session_destroy(action); return consumed_len; } +static enum lttng_error_code lttng_action_stop_session_mi_serialize( + const struct lttng_action *action, struct mi_writer *writer) +{ + int ret; + enum lttng_error_code ret_code; + enum lttng_action_status status; + const char *session_name = NULL; + const struct lttng_rate_policy *policy = NULL; + + LTTNG_ASSERT(action); + LTTNG_ASSERT(IS_STOP_SESSION_ACTION(action)); + + status = lttng_action_stop_session_get_session_name( + action, &session_name); + LTTNG_ASSERT(status == LTTNG_ACTION_STATUS_OK); + LTTNG_ASSERT(session_name != NULL); + + status = lttng_action_stop_session_get_rate_policy(action, &policy); + LTTNG_ASSERT(status == LTTNG_ACTION_STATUS_OK); + LTTNG_ASSERT(policy != NULL); + + /* Open action stop session. */ + ret = mi_lttng_writer_open_element( + writer, mi_lttng_element_action_start_session); + if (ret) { + goto mi_error; + } + + /* Session name. */ + ret = mi_lttng_writer_write_element_string( + writer, mi_lttng_element_session_name, session_name); + if (ret) { + goto mi_error; + } + + /* Rate policy. */ + ret_code = lttng_rate_policy_mi_serialize(policy, writer); + if (ret_code != LTTNG_OK) { + goto end; + } + + /* Close action stop session element. */ + ret = mi_lttng_writer_close_element(writer); + if (ret) { + goto mi_error; + } + + ret_code = LTTNG_OK; + goto end; + +mi_error: + ret_code = LTTNG_ERR_MI_IO_FAIL; +end: + return ret_code; +} + struct lttng_action *lttng_action_stop_session_create(void) { - struct lttng_action *action; + struct lttng_action *action = NULL; + struct lttng_rate_policy *policy = NULL; + enum lttng_action_status status; + + /* Create a every N = 1 rate policy. */ + policy = lttng_rate_policy_every_n_create(1); + if (!policy) { + goto end; + } action = zmalloc(sizeof(struct lttng_action_stop_session)); if (!action) { @@ -207,9 +310,20 @@ struct lttng_action *lttng_action_stop_session_create(void) lttng_action_stop_session_validate, lttng_action_stop_session_serialize, lttng_action_stop_session_is_equal, - lttng_action_stop_session_destroy); + lttng_action_stop_session_destroy, + lttng_action_stop_session_internal_get_rate_policy, + lttng_action_generic_add_error_query_results, + lttng_action_stop_session_mi_serialize); + + status = lttng_action_stop_session_set_rate_policy(action, policy); + if (status != LTTNG_ACTION_STATUS_OK) { + free(action); + action = NULL; + goto end; + } end: + lttng_rate_policy_destroy(policy); return action; } @@ -259,3 +373,65 @@ enum lttng_action_status lttng_action_stop_session_get_session_name( end: return status; } + +enum lttng_action_status lttng_action_stop_session_set_rate_policy( + struct lttng_action *action, + const struct lttng_rate_policy *policy) +{ + enum lttng_action_status status; + struct lttng_action_stop_session *stop_session_action; + struct lttng_rate_policy *copy = NULL; + + if (!action || !policy || !IS_STOP_SESSION_ACTION(action)) { + status = LTTNG_ACTION_STATUS_INVALID; + goto end; + } + + copy = lttng_rate_policy_copy(policy); + if (!copy) { + status = LTTNG_ACTION_STATUS_ERROR; + goto end; + } + stop_session_action = action_stop_session_from_action(action); + + /* Free the previous rate policy .*/ + lttng_rate_policy_destroy(stop_session_action->policy); + + stop_session_action->policy = copy; + status = LTTNG_ACTION_STATUS_OK; + copy = NULL; + +end: + lttng_rate_policy_destroy(copy); + return status; +} + +enum lttng_action_status lttng_action_stop_session_get_rate_policy( + const struct lttng_action *action, + const struct lttng_rate_policy **policy) +{ + enum lttng_action_status status; + const struct lttng_action_stop_session *stop_session_action; + + if (!action || !policy || !IS_STOP_SESSION_ACTION(action)) { + status = LTTNG_ACTION_STATUS_INVALID; + goto end; + } + + stop_session_action = action_stop_session_from_action_const(action); + + *policy = stop_session_action->policy; + status = LTTNG_ACTION_STATUS_OK; +end: + return status; +} + +static const struct lttng_rate_policy * +lttng_action_stop_session_internal_get_rate_policy( + const struct lttng_action *action) +{ + const struct lttng_action_stop_session *_action; + _action = action_stop_session_from_action_const(action); + + return _action->policy; +}