mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-10-05 02:02:26 +00:00
baseaudioencoder: minor fixes and code simplifications
Also modify and elaborate a bit on pre_push (though currently unused to no harm).
This commit is contained in:
parent
d0e9fbf3db
commit
9ce2edc918
2 changed files with 29 additions and 43 deletions
|
@ -196,10 +196,6 @@ struct _GstBaseAudioEncoderPrivate
|
||||||
GstAdapter *adapter;
|
GstAdapter *adapter;
|
||||||
/* offset in adapter up to which already supplied to encoder */
|
/* offset in adapter up to which already supplied to encoder */
|
||||||
gint offset;
|
gint offset;
|
||||||
/* collected encoded data */
|
|
||||||
GstAdapter *adapter_out;
|
|
||||||
/* (estimated) samples (w.r.t. input rate) represented in adapter_out */
|
|
||||||
gint samples_out;
|
|
||||||
/* mark outgoing discont */
|
/* mark outgoing discont */
|
||||||
gboolean discont;
|
gboolean discont;
|
||||||
/* to guess duration of drained data */
|
/* to guess duration of drained data */
|
||||||
|
@ -375,7 +371,6 @@ gst_base_audio_encoder_init (GstBaseAudioEncoder * enc,
|
||||||
GST_DEBUG_OBJECT (enc, "src created");
|
GST_DEBUG_OBJECT (enc, "src created");
|
||||||
|
|
||||||
enc->priv->adapter = gst_adapter_new ();
|
enc->priv->adapter = gst_adapter_new ();
|
||||||
enc->priv->adapter_out = gst_adapter_new ();
|
|
||||||
enc->ctx = &enc->priv->ctx;
|
enc->ctx = &enc->priv->ctx;
|
||||||
|
|
||||||
/* property default */
|
/* property default */
|
||||||
|
@ -409,14 +404,12 @@ gst_base_audio_encoder_reset (GstBaseAudioEncoder * enc, gboolean full)
|
||||||
gst_segment_init (&enc->segment, GST_FORMAT_TIME);
|
gst_segment_init (&enc->segment, GST_FORMAT_TIME);
|
||||||
|
|
||||||
gst_adapter_clear (enc->priv->adapter);
|
gst_adapter_clear (enc->priv->adapter);
|
||||||
gst_adapter_clear (enc->priv->adapter_out);
|
|
||||||
enc->priv->got_data = FALSE;
|
enc->priv->got_data = FALSE;
|
||||||
enc->priv->drained = TRUE;
|
enc->priv->drained = TRUE;
|
||||||
enc->priv->offset = 0;
|
enc->priv->offset = 0;
|
||||||
enc->priv->base_ts = GST_CLOCK_TIME_NONE;
|
enc->priv->base_ts = GST_CLOCK_TIME_NONE;
|
||||||
enc->priv->base_gp = -1;
|
enc->priv->base_gp = -1;
|
||||||
enc->priv->samples = 0;
|
enc->priv->samples = 0;
|
||||||
enc->priv->samples_out = 0;
|
|
||||||
enc->priv->discont = FALSE;
|
enc->priv->discont = FALSE;
|
||||||
|
|
||||||
GST_OBJECT_UNLOCK (enc);
|
GST_OBJECT_UNLOCK (enc);
|
||||||
|
@ -428,7 +421,6 @@ gst_base_audio_encoder_finalize (GObject * object)
|
||||||
GstBaseAudioEncoder *enc = GST_BASE_AUDIO_ENCODER (object);
|
GstBaseAudioEncoder *enc = GST_BASE_AUDIO_ENCODER (object);
|
||||||
|
|
||||||
g_object_unref (enc->priv->adapter);
|
g_object_unref (enc->priv->adapter);
|
||||||
g_object_unref (enc->priv->adapter_out);
|
|
||||||
|
|
||||||
G_OBJECT_CLASS (parent_class)->finalize (object);
|
G_OBJECT_CLASS (parent_class)->finalize (object);
|
||||||
}
|
}
|
||||||
|
@ -464,7 +456,6 @@ gst_base_audio_encoder_finish_frame (GstBaseAudioEncoder * enc, GstBuffer * buf,
|
||||||
GstBaseAudioEncoderPrivate *priv;
|
GstBaseAudioEncoderPrivate *priv;
|
||||||
GstBaseAudioEncoderContext *ctx;
|
GstBaseAudioEncoderContext *ctx;
|
||||||
GstFlowReturn ret = GST_FLOW_OK;
|
GstFlowReturn ret = GST_FLOW_OK;
|
||||||
gint av;
|
|
||||||
|
|
||||||
klass = GST_BASE_AUDIO_ENCODER_GET_CLASS (enc);
|
klass = GST_BASE_AUDIO_ENCODER_GET_CLASS (enc);
|
||||||
priv = enc->priv;
|
priv = enc->priv;
|
||||||
|
@ -487,8 +478,8 @@ gst_base_audio_encoder_finish_frame (GstBaseAudioEncoder * enc, GstBuffer * buf,
|
||||||
samples = (enc->priv->offset / ctx->state.bpf);
|
samples = (enc->priv->offset / ctx->state.bpf);
|
||||||
|
|
||||||
if (G_LIKELY (samples)) {
|
if (G_LIKELY (samples)) {
|
||||||
/* track upstream ts at output collection start if so configured */
|
/* track upstream ts if so configured */
|
||||||
if (!enc->perfect_ts && !priv->samples_out) {
|
if (!enc->perfect_ts) {
|
||||||
guint64 ts, distance;
|
guint64 ts, distance;
|
||||||
|
|
||||||
ts = gst_adapter_prev_timestamp (priv->adapter, &distance);
|
ts = gst_adapter_prev_timestamp (priv->adapter, &distance);
|
||||||
|
@ -544,21 +535,12 @@ gst_base_audio_encoder_finish_frame (GstBaseAudioEncoder * enc, GstBuffer * buf,
|
||||||
if (G_UNLIKELY (gst_adapter_available (priv->adapter) == 0))
|
if (G_UNLIKELY (gst_adapter_available (priv->adapter) == 0))
|
||||||
gst_adapter_clear (priv->adapter);
|
gst_adapter_clear (priv->adapter);
|
||||||
}
|
}
|
||||||
if (G_LIKELY (buf)) {
|
/* sample count advanced below after buffer handling */
|
||||||
priv->samples_out += samples;
|
|
||||||
samples = 0;
|
|
||||||
}
|
|
||||||
/* otherwise retain count of to-be-discarded samples */
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* collect output */
|
/* collect output */
|
||||||
if (G_LIKELY (buf))
|
if (G_LIKELY (buf)) {
|
||||||
gst_adapter_push (enc->priv->adapter_out, buf);
|
GST_LOG_OBJECT (enc, "taking %d bytes for output", GST_BUFFER_SIZE (buf));
|
||||||
|
|
||||||
av = gst_adapter_available (priv->adapter_out);
|
|
||||||
if (av) {
|
|
||||||
GST_LOG_OBJECT (enc, "collecting all %d bytes for output", av);
|
|
||||||
buf = gst_adapter_take_buffer (priv->adapter_out, av);
|
|
||||||
buf = gst_buffer_make_metadata_writable (buf);
|
buf = gst_buffer_make_metadata_writable (buf);
|
||||||
|
|
||||||
/* decorate */
|
/* decorate */
|
||||||
|
@ -570,10 +552,9 @@ gst_base_audio_encoder_finish_frame (GstBaseAudioEncoder * enc, GstBuffer * buf,
|
||||||
GST_BUFFER_TIMESTAMP (buf) = priv->base_ts +
|
GST_BUFFER_TIMESTAMP (buf) = priv->base_ts +
|
||||||
gst_util_uint64_scale (priv->samples - ctx->lookahead, GST_SECOND,
|
gst_util_uint64_scale (priv->samples - ctx->lookahead, GST_SECOND,
|
||||||
ctx->state.rate);
|
ctx->state.rate);
|
||||||
GST_DEBUG_OBJECT (enc, "out samples %d", (gint) priv->samples_out);
|
GST_DEBUG_OBJECT (enc, "out samples %d", samples);
|
||||||
if (G_LIKELY (priv->samples_out > 0)) {
|
if (G_LIKELY (samples > 0)) {
|
||||||
priv->samples += priv->samples_out;
|
priv->samples += samples;
|
||||||
priv->samples_out = 0;
|
|
||||||
GST_BUFFER_DURATION (buf) = priv->base_ts +
|
GST_BUFFER_DURATION (buf) = priv->base_ts +
|
||||||
gst_util_uint64_scale (priv->samples - ctx->lookahead, GST_SECOND,
|
gst_util_uint64_scale (priv->samples - ctx->lookahead, GST_SECOND,
|
||||||
ctx->state.rate) - GST_BUFFER_TIMESTAMP (buf);
|
ctx->state.rate) - GST_BUFFER_TIMESTAMP (buf);
|
||||||
|
@ -599,29 +580,39 @@ gst_base_audio_encoder_finish_frame (GstBaseAudioEncoder * enc, GstBuffer * buf,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
priv->bytes_out += GST_BUFFER_SIZE (buf);
|
||||||
|
|
||||||
if (G_UNLIKELY (priv->discont)) {
|
if (G_UNLIKELY (priv->discont)) {
|
||||||
GST_LOG_OBJECT (enc, "marking discont");
|
GST_LOG_OBJECT (enc, "marking discont");
|
||||||
GST_BUFFER_FLAG_SET (buf, GST_BUFFER_FLAG_DISCONT);
|
GST_BUFFER_FLAG_SET (buf, GST_BUFFER_FLAG_DISCONT);
|
||||||
priv->discont = FALSE;
|
priv->discont = FALSE;
|
||||||
}
|
}
|
||||||
// TODO return value ?
|
|
||||||
if (klass->pre_push)
|
if (klass->pre_push) {
|
||||||
klass->pre_push (enc, buf);
|
/* last chance for subclass to do some dirty stuff */
|
||||||
|
ret = klass->pre_push (enc, &buf);
|
||||||
|
if (ret != GST_FLOW_OK || !buf) {
|
||||||
|
GST_DEBUG_OBJECT (enc, "subclass returned %s, buf %p",
|
||||||
|
gst_flow_get_name (ret), buf);
|
||||||
|
if (buf)
|
||||||
|
gst_buffer_unref (buf);
|
||||||
|
goto exit;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
GST_LOG_OBJECT (enc, "pushing buffer of size %d with ts %" GST_TIME_FORMAT
|
GST_LOG_OBJECT (enc, "pushing buffer of size %d with ts %" GST_TIME_FORMAT
|
||||||
", duration %" GST_TIME_FORMAT, GST_BUFFER_SIZE (buf),
|
", duration %" GST_TIME_FORMAT, GST_BUFFER_SIZE (buf),
|
||||||
GST_TIME_ARGS (GST_BUFFER_TIMESTAMP (buf)),
|
GST_TIME_ARGS (GST_BUFFER_TIMESTAMP (buf)),
|
||||||
GST_TIME_ARGS (GST_BUFFER_DURATION (buf)));
|
GST_TIME_ARGS (GST_BUFFER_DURATION (buf)));
|
||||||
|
|
||||||
priv->bytes_out += GST_BUFFER_SIZE (buf);
|
|
||||||
|
|
||||||
ret = gst_pad_push (enc->srcpad, buf);
|
ret = gst_pad_push (enc->srcpad, buf);
|
||||||
GST_LOG_OBJECT (enc, "buffer pushed: %s", gst_flow_get_name (ret));
|
GST_LOG_OBJECT (enc, "buffer pushed: %s", gst_flow_get_name (ret));
|
||||||
|
} else {
|
||||||
|
/* merely advance samples, most work for that already done above */
|
||||||
|
priv->samples += samples;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* account for discarded */
|
exit:
|
||||||
priv->samples += samples;
|
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
/* ERRORS */
|
/* ERRORS */
|
||||||
|
@ -657,10 +648,6 @@ gst_base_audio_encoder_push_buffers (GstBaseAudioEncoder * enc, gboolean force)
|
||||||
priv = enc->priv;
|
priv = enc->priv;
|
||||||
ctx = enc->ctx;
|
ctx = enc->ctx;
|
||||||
|
|
||||||
/* ensure clear start */
|
|
||||||
gst_adapter_clear (priv->adapter_out);
|
|
||||||
priv->samples_out = 0;
|
|
||||||
|
|
||||||
while (ret == GST_FLOW_OK) {
|
while (ret == GST_FLOW_OK) {
|
||||||
|
|
||||||
buf = NULL;
|
buf = NULL;
|
||||||
|
@ -723,9 +710,6 @@ gst_base_audio_encoder_push_buffers (GstBaseAudioEncoder * enc, gboolean force)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (gst_adapter_available (priv->adapter_out))
|
|
||||||
gst_base_audio_encoder_finish_frame (enc, NULL, 0);
|
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -188,6 +188,8 @@ struct _GstBaseAudioEncoder {
|
||||||
* (i.e. not unref'ed).
|
* (i.e. not unref'ed).
|
||||||
* @pre_push: Optional.
|
* @pre_push: Optional.
|
||||||
* Called just prior to pushing (encoded data) buffer downstream.
|
* Called just prior to pushing (encoded data) buffer downstream.
|
||||||
|
* Subclass has full discretionary access to buffer,
|
||||||
|
* and a not OK flow return will abort downstream pushing.
|
||||||
* @getcaps: Optional.
|
* @getcaps: Optional.
|
||||||
* Allows for a custom sink getcaps implementation (e.g.
|
* Allows for a custom sink getcaps implementation (e.g.
|
||||||
* for multichannel input specification). If not implemented,
|
* for multichannel input specification). If not implemented,
|
||||||
|
@ -216,7 +218,7 @@ struct _GstBaseAudioEncoderClass {
|
||||||
void (*flush) (GstBaseAudioEncoder *enc);
|
void (*flush) (GstBaseAudioEncoder *enc);
|
||||||
|
|
||||||
GstFlowReturn (*pre_push) (GstBaseAudioEncoder *enc,
|
GstFlowReturn (*pre_push) (GstBaseAudioEncoder *enc,
|
||||||
GstBuffer *buffer);
|
GstBuffer **buffer);
|
||||||
|
|
||||||
gboolean (*event) (GstBaseAudioEncoder *enc,
|
gboolean (*event) (GstBaseAudioEncoder *enc,
|
||||||
GstEvent *event);
|
GstEvent *event);
|
||||||
|
|
Loading…
Reference in a new issue