Reset Pipeline on GST_STATE_CHANGE_FAILURE change state

classic Classic list List threaded Threaded
1 message Options
Reply | Threaded
Open this post in threaded view
|

Reset Pipeline on GST_STATE_CHANGE_FAILURE change state

tr0nc0
Hi,
I am doing some maintenance on an application using gstreamer 0.10.36

Upon a streaming error due to a corrupted file system I receive two errors at application level, the first one from the "filesrc" source element and then by the mpegaudioparse from within the decodebin2 element.

GST error from mpegaudioparse50: 'GStreamer encountered a general stream error.' (debug info: gstbaseparse.c(2926): gst_base_parse_loop (): /GstPipeline:pipeline/GstDecodeBin2:msd_decoder/GstMpegAudioParse:mpegaudioparse50: streaming stopped, reason error)


As a recovery action the application flags an error and attempts first to set the pipeline to PAUSE in order to set a new file path into the filesrc element and then, when GST_STATE_CHANGE_FAILURE is returned on the PAUSE change state, the application tryes to reset the pipeline to GST_STATE_NULL,

    GstStateChangeReturn result =  gst_element_set_state (m_pipeline, GST_STATE_NULL);
    return result != GST_STATE_CHANGE_FAILURE;

Also this operation keeps failing returning GST_STATE_CHANGE_FAILURE from the decodebin2 element.
Also I was actually surprised that GST_STATE_CHANGE_FAILURE seems to be set by the bin parent of decodebin2 rather than from one of its children (as can be seen from coredump below)

Is there actually any way to recover from this scenario? Every code sample I have found online just handles this scenario by calling exit and closing.
Some example perform gst_object_unref of the element/pipeline, but does not sound correct, resources are still allocated and this action could lead to a crash.


Below the info on the decodebin2 state taken from coredump:

DECODEBIN2

(gdb) p ((GstDecodeBin *)((GList *) 0x2c0dd0)->data)
$155 = (GstDecodeBin *) 0x382008


(gdb) p ((GstDecodeBin *)((GList *) 0x2c0dd0)->data)->bin
$117 = {
  element = {
    object = {
      object = {
        g_type_instance = {
          g_class = 0x380590
        },
        ref_count = 1,
        qdata = 0x0
      },
      refcount = 0,
      lock = 0x3c8898,
      name = 0x3c21e0 "msd_decoder",
      name_prefix = 0x0,
      parent = 0x378478,
      flags = 0,
      _gst_reserved = 0x0
    },
    state_lock = 0x36bd90,
    state_cond = 0x507f30,
    state_cookie = 8,
    current_state = GST_STATE_PAUSED,
    next_state = GST_STATE_VOID_PENDING,
    pending_state = GST_STATE_VOID_PENDING,
    last_return = GST_STATE_CHANGE_FAILURE,
    bus = 0x3fc2c0,
    clock = 0x395138,
    base_time = 81560000000,
    numpads = 2,
    pads = 0x4d6930,
    numsrcpads = 1,
---Type <return> to continue, or q <return> to quit---
    srcpads = 0x34e490,
    numsinkpads = 1,
    sinkpads = 0x40cc00,
    pads_cookie = 4,
    abidata = {
      ABI = {
        target_state = GST_STATE_PAUSED,
        start_time = 87960000000
      },
      _gst_reserved = {0x3, 0x0, 0x7ad31600, 0x14}
    }
  },
  numchildren = 4,
  children = 0x4584b0,
  children_cookie = 10,
  child_bus = 0x3fc380,
  messages = 0x0,
  polling = 0,
  state_dirty = 0,
  clock_dirty = 0,
  provided_clock = 0x0,
  clock_provider = 0x0,
  priv = 0x382138,
  _gst_reserved = {0x0, 0x0, 0x0}
}

HERE THE STATUS OF DECODEBIN2 4 CHILDREN


(gdb) p ((GList *) 0x4584b0)->prev
$118 = (GList *) 0x0
(gdb) p ((GList *) 0x4584b0)->next
$119 = (GList *) 0x501b80
(gdb) p ((GList *) 0x501b80)->next
$121 = (GList *) 0x4dc240
(gdb) p ((GList *) 0x4dc240)->next
$122 = (GList *) 0x34e8a0
(gdb) p ((GList *) 0x34e8a0)->next
$123 = (GList *) 0x0




(gdb) p ((GstElement *)((GList *) 0x4584b0)->data)->object
$124 = {
  object = {
    g_type_instance = {
      g_class = 0x402268
    },
    ref_count = 3,
    qdata = 0x0
  },
  refcount = 0,
  lock = 0x343350,
  name = 0x45d2f0 "omxmp3dec50",
  name_prefix = 0x0,
  parent = 0x382008,
  flags = 0,
  _gst_reserved = 0x0
}
(gdb) p ((GstElement *)((GList *) 0x4584b0)->data)->current_state
$125 = GST_STATE_PAUSED
(gdb) p ((GstElement *)((GList *) 0x4584b0)->data)->next_state
$126 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x4584b0)->data)->pending_state
$127 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x4584b0)->data)->last_return
$128 = GST_STATE_CHANGE_SUCCESS




(gdb) p ((GstElement *)((GList *) 0x501b80)->data)->object
$129 = {
  object = {
    g_type_instance = {
      g_class = 0x352c00
    },
    ref_count = 2,
    qdata = 0x0
  },
  refcount = 0,
  lock = 0x5ab110,
  name = 0x45e460 "mpegaudioparse50",
  name_prefix = 0x0,
  parent = 0x382008,
  flags = 0,
  _gst_reserved = 0x0
}
(gdb) p ((GstElement *)((GList *) 0x501b80)->data)->current_state
$130 = GST_STATE_PAUSED
(gdb) p ((GstElement *)((GList *) 0x501b80)->data)->next_state
$131 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x501b80)->data)->pending_state
$132 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x501b80)->data)->last_return
$133 = GST_STATE_CHANGE_SUCCESS



(gdb) p ((GstElement *)((GList *) 0x4dc240)->data)->object
$134 = {
  object = {
    g_type_instance = {
      g_class = 0x3e8c68
    },
    ref_count = 2,
    qdata = 0x0
  },
  refcount = 0,
  lock = 0x350320,
  name = 0x47dfc0 "id3demux38",
  name_prefix = 0x0,
  parent = 0x382008,
  flags = 0,
  _gst_reserved = 0x0
}
(gdb) p ((GstElement *)((GList *) 0x4dc240)->data)->current_state
$135 = GST_STATE_PAUSED
(gdb) p ((GstElement *)((GList *) 0x4dc240)->data)->next_state
$136 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x4dc240)->data)->pending_state
$137 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x4dc240)->data)->last_return
$138 = GST_STATE_CHANGE_SUCCESS





(gdb) p ((GstElement *)((GList *) 0x34e8a0)->data)->object
$139 = {
  object = {
    g_type_instance = {
      g_class = 0x381090
    },
    ref_count = 1,
    qdata = 0x0
  },
  refcount = 0,
  lock = 0x3dbc90,
  name = 0x4ddf70 "typefind",
  name_prefix = 0x0,
  parent = 0x382008,
  flags = 0,
  _gst_reserved = 0x0
}
(gdb) p ((GstElement *)((GList *) 0x34e8a0)->data)->current_state
$140 = GST_STATE_PAUSED
(gdb) p ((GstElement *)((GList *) 0x34e8a0)->data)->next_state
$141 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x34e8a0)->data)->pending_state
$142 = GST_STATE_VOID_PENDING
(gdb) p ((GstElement *)((GList *) 0x34e8a0)->data)->last_return
$143 = GST_STATE_CHANGE_SUCCESS