diff --git a/validate/gst/validate/gst-validate-report.c b/validate/gst/validate/gst-validate-report.c index 1300235c2b..de3ef4e098 100644 --- a/validate/gst/validate/gst-validate-report.c +++ b/validate/gst/validate/gst-validate-report.c @@ -683,6 +683,7 @@ gst_validate_printf_valist (gpointer source, const gchar * format, va_list args) } else if (*(GType *) source == GST_TYPE_VALIDATE_ACTION_TYPE) { gint i; gchar *desc, *tmp; + gboolean has_parameters = FALSE; GstValidateActionParameter playback_time_param = { .name = "playback-time", @@ -708,6 +709,7 @@ gst_validate_printf_valist (gpointer source, const gchar * format, va_list args) "\n Is config action (meaning it will be executing right " "at the begining of the execution of the pipeline)"); + tmp = g_strdup_printf ("\n "); desc = g_regex_replace (newline_regex, type->description, -1, 0, tmp, 0, @@ -720,15 +722,27 @@ gst_validate_printf_valist (gpointer source, const gchar * format, va_list args) print_action_parametter (string, type, &playback_time_param); if (type->parameters) { + has_parameters = TRUE; g_string_append_printf (string, "\n\n Parametters:"); for (i = 0; type->parameters[i].name; i++) { print_action_parametter (string, type, &type->parameters[i]); } - } else { - g_string_append_printf (string, "\n\n No Parameters"); - } + + if ((type->flags & GST_VALIDATE_ACTION_TYPE_CAN_BE_OPTIONAL)) { + has_parameters = TRUE; + g_string_append_printf (string, "\n %-26s : %s", "optional", + "Don't raise an error if this action hasn't been executed of failed"); + g_string_append_printf (string, "\n %-28s %s", "", + "Possible types:"); + g_string_append_printf (string, "\n %-31s %s", "", "boolean"); + g_string_append_printf (string, "\n %-28s %s", "", + "Default: false"); + } + + if (!has_parameters) + g_string_append_printf (string, "\n\n No Parameters"); } else if (GST_IS_OBJECT (source)) { g_string_printf (string, "\n%s --> ", GST_OBJECT_NAME (source)); } else if (G_IS_OBJECT (source)) { diff --git a/validate/gst/validate/gst-validate-scenario.c b/validate/gst/validate/gst-validate-scenario.c index 826c85641c..7bf59b2afd 100644 --- a/validate/gst/validate/gst-validate-scenario.c +++ b/validate/gst/validate/gst-validate-scenario.c @@ -180,6 +180,7 @@ struct _GstValidateActionPrivate GstValidateExecuteActionReturn state; /* Actually ActionState */ gboolean printed; gboolean executing_last_subaction; + gboolean optional; }; GST_DEFINE_MINI_OBJECT_TYPE (GstValidateAction, gst_validate_action); @@ -369,12 +370,29 @@ _set_variable_func (const gchar * name, double *value, gpointer user_data) return FALSE; } +/* Check that @list doesn't contain any non-optional actions */ +static gboolean +actions_list_is_done (GList * list) +{ + GList *l; + + for (l = list; l != NULL; l = g_list_next (l)) { + GstValidateAction *action = l->data; + + if (!action->priv->optional) + return FALSE; + } + + return TRUE; +} + static void _check_scenario_is_done (GstValidateScenario * scenario) { SCENARIO_LOCK (scenario); - if (!scenario->priv->actions && !scenario->priv->interlaced_actions - && !scenario->priv->on_addition_actions) { + if (actions_list_is_done (scenario->priv->actions) && + actions_list_is_done (scenario->priv->interlaced_actions) && + actions_list_is_done (scenario->priv->on_addition_actions)) { SCENARIO_UNLOCK (scenario); g_signal_emit (scenario, scenario_signals[DONE], 0); @@ -1077,6 +1095,7 @@ _fill_action (GstValidateScenario * scenario, GstValidateAction * action, const gchar *str_playback_time = NULL; GstValidateScenarioPrivate *priv = scenario->priv; GstValidateExecuteActionReturn res = GST_VALIDATE_EXECUTE_ACTION_OK; + gboolean optional; action->type = gst_structure_get_name (structure); action_type = _find_action_type (action->type); @@ -1113,6 +1132,15 @@ _fill_action (GstValidateScenario * scenario, GstValidateAction * action, if (!action->priv->main_structure) action->priv->main_structure = gst_structure_copy (structure); + if (gst_structure_get_boolean (structure, "optional", &optional)) { + if ((action_type->flags & GST_VALIDATE_ACTION_TYPE_CAN_BE_OPTIONAL) == 0) { + GST_ERROR_OBJECT (scenario, "Action type %s can't be optional", + gst_structure_get_name (structure)); + return GST_VALIDATE_EXECUTE_ACTION_ERROR; + } + action->priv->optional = optional; + } + if (IS_CONFIG_ACTION_TYPE (action_type->flags) || (gst_structure_get_boolean (action->structure, "as-config", &is_config) && is_config == TRUE)) { @@ -1900,7 +1928,8 @@ message_cb (GstBus * bus, GstMessage * message, GstValidateScenario * scenario) tmpconcat = actions; if (type->flags & GST_VALIDATE_ACTION_TYPE_NO_EXECUTION_NOT_FATAL || - action->priv->state == GST_VALIDATE_EXECUTE_ACTION_OK) { + action->priv->state == GST_VALIDATE_EXECUTE_ACTION_OK || + action->priv->optional) { gst_validate_action_unref (action); continue; @@ -1918,6 +1947,7 @@ message_cb (GstBus * bus, GstMessage * message, GstValidateScenario * scenario) g_list_free (all_actions); scenario->priv->actions = NULL; scenario->priv->interlaced_actions = NULL; + scenario->priv->on_addition_actions = NULL; if (nb_actions > 0) GST_VALIDATE_REPORT (scenario, SCENARIO_NOT_ENDED, @@ -2305,6 +2335,12 @@ gst_validate_scenario_finalize (GObject * object) { GstValidateScenarioPrivate *priv = GST_VALIDATE_SCENARIO (object)->priv; + g_list_free_full (priv->actions, (GDestroyNotify) gst_mini_object_unref); + g_list_free_full (priv->interlaced_actions, + (GDestroyNotify) gst_mini_object_unref); + g_list_free_full (priv->on_addition_actions, + (GDestroyNotify) gst_mini_object_unref); + g_mutex_clear (&priv->lock); G_OBJECT_CLASS (gst_validate_scenario_parent_class)->finalize (object); diff --git a/validate/gst/validate/gst-validate-scenario.h b/validate/gst/validate/gst-validate-scenario.h index f595a82098..36b6f80d79 100644 --- a/validate/gst/validate/gst-validate-scenario.h +++ b/validate/gst/validate/gst-validate-scenario.h @@ -132,6 +132,9 @@ GType gst_validate_action_get_type (void); * for that action type to be used. * @GST_VALIDATE_ACTION_TYPE_NO_EXECUTION_NOT_FATAL: Do not concider the non execution of the action * as a fatal error. + * @GST_VALIDATE_ACTION_TYPE_CAN_BE_OPTIONAL: The action can use the 'optional' keyword. Such action + * instances will have the #GST_VALIDATE_ACTION_TYPE_NO_EXECUTION_NOT_FATAL + * flag set and won't be considered as fatal if they fail. */ typedef enum { @@ -142,6 +145,7 @@ typedef enum GST_VALIDATE_ACTION_TYPE_CAN_EXECUTE_ON_ADDITION = 1 << 4, GST_VALIDATE_ACTION_TYPE_NEEDS_CLOCK = 1 << 5, GST_VALIDATE_ACTION_TYPE_NO_EXECUTION_NOT_FATAL = 1 << 6, + GST_VALIDATE_ACTION_TYPE_CAN_BE_OPTIONAL = 1 << 7, } GstValidateActionTypeFlags; /**