/* MPEG-PS muxer plugin for GStreamer
 * Copyright 2008 Lin YANG <oxcsnicho@gmail.com>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with this library; if not, write to the
 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
 * Boston, MA 02110-1301, USA.
 */
/*
 * Unless otherwise indicated, Source Code is licensed under MIT license.
 * See further explanation attached in License Statement (distributed in the file
 * LICENSE).
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy of
 * this software and associated documentation files (the "Software"), to deal in
 * the Software without restriction, including without limitation the rights to
 * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
 * of the Software, and to permit persons to whom the Software is furnished to do
 * so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in all
 * copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <string.h>

#include "mpegpsmux.h"
#include "mpegpsmux_aac.h"
#include "mpegpsmux_h264.h"

GST_DEBUG_CATEGORY (mpegpsmux_debug);
#define GST_CAT_DEFAULT mpegpsmux_debug

enum
{
  PROP_AGGREGATE_GOPS = 1
};

#define DEFAULT_AGGREGATE_GOPS FALSE

static GstStaticPadTemplate mpegpsmux_sink_factory =
    GST_STATIC_PAD_TEMPLATE ("sink_%u",
    GST_PAD_SINK,
    GST_PAD_REQUEST,
    GST_STATIC_CAPS ("video/mpeg, "
        "mpegversion = (int) { 1, 2, 4 }, "
        "systemstream = (boolean) false; "
        "video/x-dirac;"
        "video/x-h264;"
        "audio/mpeg, "
        "mpegversion = (int) { 1, 2 };"
        "audio/mpeg, "
        "mpegversion = (int) 4, stream-format = (string) { raw, adts }; "
        "audio/x-lpcm, "
        "width = (int) { 16, 20, 24 }, "
        "rate = (int) { 48000, 96000 }, "
        "channels = (int) [ 1, 8 ], "
        "dynamic_range = (int) [ 0, 255 ], "
        "emphasis = (boolean) { FALSE, TRUE }, "
        "mute = (boolean) { FALSE, TRUE }"));

static GstStaticPadTemplate mpegpsmux_src_factory =
GST_STATIC_PAD_TEMPLATE ("src",
    GST_PAD_SRC,
    GST_PAD_ALWAYS,
    GST_STATIC_CAPS ("video/mpeg, "
        "mpegversion = (int) 2, " "systemstream = (boolean) true")
    );

static void gst_mpegpsmux_set_property (GObject * object, guint prop_id,
    const GValue * value, GParamSpec * pspec);
static void gst_mpegpsmux_get_property (GObject * object, guint prop_id,
    GValue * value, GParamSpec * pspec);

static void mpegpsmux_finalize (GObject * object);
static gboolean new_packet_cb (guint8 * data, guint len, void *user_data);

static gboolean mpegpsdemux_prepare_srcpad (MpegPsMux * mux);
static GstFlowReturn mpegpsmux_collected (GstCollectPads * pads,
    MpegPsMux * mux);
static GstPad *mpegpsmux_request_new_pad (GstElement * element,
    GstPadTemplate * templ, const gchar * name, const GstCaps * caps);
static void mpegpsmux_release_pad (GstElement * element, GstPad * pad);
static GstStateChangeReturn mpegpsmux_change_state (GstElement * element,
    GstStateChange transition);

#define parent_class mpegpsmux_parent_class
G_DEFINE_TYPE (MpegPsMux, mpegpsmux, GST_TYPE_ELEMENT);

static void
mpegpsmux_class_init (MpegPsMuxClass * klass)
{
  GstElementClass *gstelement_class = GST_ELEMENT_CLASS (klass);
  GObjectClass *gobject_class = G_OBJECT_CLASS (klass);

  gobject_class->set_property = gst_mpegpsmux_set_property;
  gobject_class->get_property = gst_mpegpsmux_get_property;
  gobject_class->finalize = mpegpsmux_finalize;

  gstelement_class->request_new_pad = mpegpsmux_request_new_pad;
  gstelement_class->release_pad = mpegpsmux_release_pad;
  gstelement_class->change_state = mpegpsmux_change_state;

  g_object_class_install_property (gobject_class, PROP_AGGREGATE_GOPS,
      g_param_spec_boolean ("aggregate-gops", "Aggregate GOPs",
          "Whether to aggregate GOPs and push them out as buffer lists",
          DEFAULT_AGGREGATE_GOPS, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  gst_element_class_add_pad_template (gstelement_class,
      gst_static_pad_template_get (&mpegpsmux_sink_factory));
  gst_element_class_add_pad_template (gstelement_class,
      gst_static_pad_template_get (&mpegpsmux_src_factory));

  gst_element_class_set_static_metadata (gstelement_class,
      "MPEG Program Stream Muxer", "Codec/Muxer",
      "Multiplexes media streams into an MPEG Program Stream",
      "Lin YANG <oxcsnicho@gmail.com>");
}

static void
mpegpsmux_init (MpegPsMux * mux)
{
  mux->srcpad = gst_pad_new_from_static_template (&mpegpsmux_src_factory,
      "src");
  gst_pad_use_fixed_caps (mux->srcpad);
  gst_element_add_pad (GST_ELEMENT (mux), mux->srcpad);

  mux->collect = gst_collect_pads_new ();
  gst_collect_pads_set_function (mux->collect,
      (GstCollectPadsFunction) GST_DEBUG_FUNCPTR (mpegpsmux_collected), mux);

  mux->psmux = psmux_new ();
  psmux_set_write_func (mux->psmux, new_packet_cb, mux);

  mux->first = TRUE;
  mux->last_flow_ret = GST_FLOW_OK;
  mux->last_ts = 0;             /* XXX: or -1? */
}

static void
mpegpsmux_finalize (GObject * object)
{
  MpegPsMux *mux = GST_MPEG_PSMUX (object);

  if (mux->collect) {
    gst_object_unref (mux->collect);
    mux->collect = NULL;
  }
  if (mux->psmux) {
    psmux_free (mux->psmux);
    mux->psmux = NULL;
  }

  if (mux->gop_list != NULL) {
    gst_buffer_list_unref (mux->gop_list);
    mux->gop_list = NULL;
  }

  G_OBJECT_CLASS (mpegpsmux_parent_class)->finalize (object);
}

static void
gst_mpegpsmux_set_property (GObject * object, guint prop_id,
    const GValue * value, GParamSpec * pspec)
{
  MpegPsMux *mux = GST_MPEG_PSMUX (object);

  switch (prop_id) {
    case PROP_AGGREGATE_GOPS:
      mux->aggregate_gops = g_value_get_boolean (value);
      break;
    default:
      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
      break;
  }
}

static void
gst_mpegpsmux_get_property (GObject * object, guint prop_id,
    GValue * value, GParamSpec * pspec)
{
  MpegPsMux *mux = GST_MPEG_PSMUX (object);

  switch (prop_id) {
    case PROP_AGGREGATE_GOPS:
      g_value_set_boolean (value, mux->aggregate_gops);
      break;
    default:
      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
      break;
  }
}

static GstFlowReturn
mpegpsmux_create_stream (MpegPsMux * mux, MpegPsPadData * ps_data, GstPad * pad)
{
  /* Create a steam. Fill in codec specific information */

  GstFlowReturn ret = GST_FLOW_ERROR;
  GstCaps *caps;
  GstStructure *s;
  gboolean is_video = FALSE;

  caps = gst_pad_get_current_caps (pad);
  if (caps == NULL) {
    GST_DEBUG_OBJECT (pad, "Sink pad caps were not set before pushing");
    return GST_FLOW_NOT_NEGOTIATED;
  }

  s = gst_caps_get_structure (caps, 0);
  g_return_val_if_fail (s != NULL, FALSE);

  if (gst_structure_has_name (s, "video/x-dirac")) {
    GST_DEBUG_OBJECT (pad, "Creating Dirac stream");
    ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_VIDEO_DIRAC);
    is_video = TRUE;
  } else if (gst_structure_has_name (s, "audio/x-ac3")) {
    GST_DEBUG_OBJECT (pad, "Creating AC3 stream");
    ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_PS_AUDIO_AC3);
  } else if (gst_structure_has_name (s, "audio/x-dts")) {
    GST_DEBUG_OBJECT (pad, "Creating DTS stream");
    ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_PS_AUDIO_DTS);
  } else if (gst_structure_has_name (s, "audio/x-lpcm")) {
    GST_DEBUG_OBJECT (pad, "Creating LPCM stream");
    ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_PS_AUDIO_LPCM);
  } else if (gst_structure_has_name (s, "video/x-h264")) {
    const GValue *value;
    GST_DEBUG_OBJECT (pad, "Creating H264 stream");
    /* Codec data contains SPS/PPS which need to go in stream for valid ES */
    value = gst_structure_get_value (s, "codec_data");
    if (value) {
      ps_data->codec_data = gst_buffer_ref (gst_value_get_buffer (value));
      GST_DEBUG_OBJECT (pad, "%" G_GSIZE_FORMAT " bytes of codec data",
          gst_buffer_get_size (ps_data->codec_data));
      ps_data->prepare_func = mpegpsmux_prepare_h264;
    } else {
      ps_data->codec_data = NULL;
    }
    ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_VIDEO_H264);
    is_video = TRUE;
  } else if (gst_structure_has_name (s, "audio/mpeg")) {
    gint mpegversion;
    if (!gst_structure_get_int (s, "mpegversion", &mpegversion)) {
      GST_ELEMENT_ERROR (pad, STREAM, FORMAT,
          ("Invalid data format presented"),
          ("Caps with type audio/mpeg did not have mpegversion"));
      goto beach;
    }

    switch (mpegversion) {
      case 1:
        GST_DEBUG_OBJECT (pad, "Creating MPEG Audio, version 1 stream");
        ps_data->stream =
            psmux_create_stream (mux->psmux, PSMUX_ST_AUDIO_MPEG1);
        break;
      case 2:
        GST_DEBUG_OBJECT (pad, "Creating MPEG Audio, version 2 stream");
        ps_data->stream =
            psmux_create_stream (mux->psmux, PSMUX_ST_AUDIO_MPEG2);
        break;
      case 4:
      {
        const GValue *value;
        /* Codec data contains SPS/PPS which need to go in stream for valid ES */
        GST_DEBUG_OBJECT (pad, "Creating MPEG Audio, version 4 stream");
        value = gst_structure_get_value (s, "codec_data");
        if (value) {
          ps_data->codec_data = gst_buffer_ref (gst_value_get_buffer (value));
          GST_DEBUG_OBJECT (pad, "%" G_GSIZE_FORMAT " bytes of codec data",
              gst_buffer_get_size (ps_data->codec_data));
          ps_data->prepare_func = mpegpsmux_prepare_aac;
        } else {
          ps_data->codec_data = NULL;
        }
        ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_AUDIO_AAC);
        break;
      }
      default:
        GST_WARNING_OBJECT (pad, "unsupported mpegversion %d", mpegversion);
        goto beach;
    }
  } else if (gst_structure_has_name (s, "video/mpeg")) {
    gint mpegversion;
    if (!gst_structure_get_int (s, "mpegversion", &mpegversion)) {
      GST_ELEMENT_ERROR (mux, STREAM, FORMAT,
          ("Invalid data format presented"),
          ("Caps with type video/mpeg did not have mpegversion"));
      goto beach;
    }

    if (mpegversion == 1) {
      GST_DEBUG_OBJECT (pad, "Creating MPEG Video, version 1 stream");
      ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_VIDEO_MPEG1);
    } else if (mpegversion == 2) {
      GST_DEBUG_OBJECT (pad, "Creating MPEG Video, version 2 stream");
      ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_VIDEO_MPEG2);
    } else {
      GST_DEBUG_OBJECT (pad, "Creating MPEG Video, version 4 stream");
      ps_data->stream = psmux_create_stream (mux->psmux, PSMUX_ST_VIDEO_MPEG4);
    }
    is_video = TRUE;
  }

  if (ps_data->stream != NULL) {
    ps_data->stream_id = ps_data->stream->stream_id;
    ps_data->stream_id_ext = ps_data->stream->stream_id_ext;
    GST_DEBUG_OBJECT (pad, "Stream created, stream_id=%04x, stream_id_ext=%04x",
        ps_data->stream_id, ps_data->stream_id_ext);

    gst_structure_get_int (s, "rate", &ps_data->stream->audio_sampling);
    gst_structure_get_int (s, "channels", &ps_data->stream->audio_channels);
    gst_structure_get_int (s, "bitrate", &ps_data->stream->audio_bitrate);

    ret = GST_FLOW_OK;

    if (is_video && mux->video_stream_id == 0) {
      mux->video_stream_id = ps_data->stream_id;
      GST_INFO_OBJECT (mux, "video pad stream_id 0x%02x", mux->video_stream_id);
    }
  }

beach:
  return ret;
}

static GstFlowReturn
mpegpsmux_create_streams (MpegPsMux * mux)
{
  /* Create stream for each pad */

  GstFlowReturn ret = GST_FLOW_OK;
  GSList *walk = mux->collect->data;

  /* Create the streams */
  while (walk) {
    GstCollectData *c_data = (GstCollectData *) walk->data;
    MpegPsPadData *ps_data = (MpegPsPadData *) walk->data;

    walk = g_slist_next (walk);

    if (ps_data->stream == NULL) {
      ret = mpegpsmux_create_stream (mux, ps_data, c_data->pad);
      if (ret != GST_FLOW_OK)
        goto no_stream;
    }
  }

  return GST_FLOW_OK;
no_stream:
  GST_ELEMENT_ERROR (mux, STREAM, MUX,
      ("Could not create handler for stream"), (NULL));
  return ret;
}

static GstBuffer *
mpegpsmux_queue_buffer_for_stream (MpegPsMux * mux, MpegPsPadData * ps_data)
{
  GstCollectData *c_data = (GstCollectData *) ps_data;
  GstBuffer *buf;

  g_assert (ps_data->queued.buf == NULL);

  buf = gst_collect_pads_peek (mux->collect, c_data);
  if (buf == NULL)
    return NULL;

  ps_data->queued.buf = buf;

  /* do any raw -> byte-stream format conversions (e.g. for H.264, AAC) */
  if (ps_data->prepare_func) {
    buf = ps_data->prepare_func (buf, ps_data, mux);
    if (buf) {                  /* Take the prepared buffer instead */
      gst_buffer_unref (ps_data->queued.buf);
      ps_data->queued.buf = buf;
    } else {                    /* If data preparation returned NULL, use unprepared one */
      buf = ps_data->queued.buf;
    }
  }

  ps_data->queued.pts = GST_BUFFER_PTS (buf);
  if (GST_CLOCK_TIME_IS_VALID (ps_data->queued.pts)) {
    ps_data->queued.pts = gst_segment_to_running_time (&c_data->segment,
        GST_FORMAT_TIME, ps_data->queued.pts);
  }

  ps_data->queued.dts = GST_BUFFER_DTS (buf);
  if (GST_CLOCK_TIME_IS_VALID (ps_data->queued.dts)) {
    ps_data->queued.dts = gst_segment_to_running_time (&c_data->segment,
        GST_FORMAT_TIME, ps_data->queued.dts);
  }

  if (GST_BUFFER_PTS_IS_VALID (buf) && GST_BUFFER_DTS_IS_VALID (buf)) {
    ps_data->queued.ts = MIN (ps_data->queued.dts, ps_data->queued.pts);
  } else if (GST_BUFFER_PTS_IS_VALID (buf) && !GST_BUFFER_DTS_IS_VALID (buf)) {
    ps_data->queued.ts = ps_data->queued.pts;
  } else if (GST_BUFFER_DTS_IS_VALID (buf) && !GST_BUFFER_PTS_IS_VALID (buf)) {
    GST_WARNING_OBJECT (c_data->pad, "got DTS without PTS");
    ps_data->queued.ts = ps_data->queued.dts;
  } else {
    ps_data->queued.ts = GST_CLOCK_TIME_NONE;
  }

  if (ps_data->queued.ts != GST_CLOCK_TIME_NONE)
    ps_data->last_ts = ps_data->queued.ts;

  GST_DEBUG_OBJECT (mux, "Queued buffer with ts %" GST_TIME_FORMAT ": "
      "uncorrected pts %" GST_TIME_FORMAT " dts %" GST_TIME_FORMAT ", "
      "buffer pts %" GST_TIME_FORMAT " dts %" GST_TIME_FORMAT " for PID 0x%04x",
      GST_TIME_ARGS (ps_data->queued.ts),
      GST_TIME_ARGS (GST_BUFFER_PTS (buf)),
      GST_TIME_ARGS (GST_BUFFER_DTS (buf)),
      GST_TIME_ARGS (ps_data->queued.pts),
      GST_TIME_ARGS (ps_data->queued.dts), ps_data->stream_id);

  return buf;
}

static MpegPsPadData *
mpegpsmux_choose_best_stream (MpegPsMux * mux)
{
  /* Choose from which stream to mux with */

  MpegPsPadData *best = NULL;
  GstCollectData *c_best = NULL;
  GSList *walk;

  for (walk = mux->collect->data; walk != NULL; walk = g_slist_next (walk)) {
    GstCollectData *c_data = (GstCollectData *) walk->data;
    MpegPsPadData *ps_data = (MpegPsPadData *) walk->data;

    if (ps_data->eos == FALSE) {
      if (ps_data->queued.buf == NULL) {
        GstBuffer *buf;

        buf = mpegpsmux_queue_buffer_for_stream (mux, ps_data);
        if (buf == NULL) {
          GST_DEBUG_OBJECT (mux, "we have EOS");
          ps_data->eos = TRUE;
          continue;
        }
      }

      /* If we don't yet have a best pad, take this one, otherwise take
       * whichever has the oldest timestamp */
      if (best != NULL) {
        if (ps_data->last_ts == GST_CLOCK_TIME_NONE ||
            (best->last_ts != GST_CLOCK_TIME_NONE &&
                ps_data->last_ts < best->last_ts)) {
          best = ps_data;
          c_best = c_data;
        }
      } else {
        best = ps_data;
        c_best = c_data;
      }
    }
  }
  if (c_best) {
    gst_buffer_unref (gst_collect_pads_pop (mux->collect, c_best));
  }

  return best;
}

static GstFlowReturn
mpegpsmux_push_gop_list (MpegPsMux * mux)
{
  GstFlowReturn flow;

  g_assert (mux->gop_list != NULL);

  GST_DEBUG_OBJECT (mux, "Sending pending GOP of %u buffers",
      gst_buffer_list_length (mux->gop_list));
  flow = gst_pad_push_list (mux->srcpad, mux->gop_list);
  mux->gop_list = NULL;
  return flow;
}

static GstFlowReturn
mpegpsmux_collected (GstCollectPads * pads, MpegPsMux * mux)
{
  /* main muxing function */

  GstFlowReturn ret = GST_FLOW_OK;
  MpegPsPadData *best = NULL;
  gboolean keyunit;

  GST_DEBUG_OBJECT (mux, "Pads collected");

  if (mux->first) {             /* process block for the first mux */
    /* iterate through the collect pads and add streams to @mux */
    ret = mpegpsmux_create_streams (mux);
    /* Assumption : all pads are already added at this time */

    if (G_UNLIKELY (ret != GST_FLOW_OK))
      return ret;

    best = mpegpsmux_choose_best_stream (mux);

    /* prepare the src pad (output), return if failed */
    if (!mpegpsdemux_prepare_srcpad (mux)) {
      GST_DEBUG_OBJECT (mux, "Failed to send new segment");
      goto new_seg_fail;
    }

    mux->first = FALSE;
  } else {
    best = mpegpsmux_choose_best_stream (mux);
  }

  if (best != NULL) {
    GstBuffer *buf = best->queued.buf;
    gint64 pts, dts;

    g_assert (buf != NULL);

    GST_LOG_OBJECT (mux,
        "Chose stream from pad %" GST_PTR_FORMAT " for output (PID: 0x%04x): "
        "adjusted pts: %" GST_TIME_FORMAT ", dts: %" GST_TIME_FORMAT,
        best->collect.pad, best->stream_id,
        GST_TIME_ARGS (best->queued.pts), GST_TIME_ARGS (best->queued.dts));

    /* and convert to mpeg time stamps */
    pts = GSTTIME_TO_MPEGTIME (best->queued.pts);
    dts = GSTTIME_TO_MPEGTIME (best->queued.dts);

    /* start of new GOP? */
    keyunit = !GST_BUFFER_FLAG_IS_SET (buf, GST_BUFFER_FLAG_DELTA_UNIT);

    if (keyunit && best->stream_id == mux->video_stream_id
        && mux->gop_list != NULL) {
      ret = mpegpsmux_push_gop_list (mux);
      if (ret != GST_FLOW_OK)
        goto done;
    }

    /* give the buffer to libpsmux for processing */
    psmux_stream_add_data (best->stream, buf, pts, dts, keyunit);

    best->queued.buf = NULL;

    /* write the data from libpsmux to stream */
    while (psmux_stream_bytes_in_buffer (best->stream) > 0) {
      GST_LOG_OBJECT (mux, "Before @psmux_write_stream_packet");
      if (!psmux_write_stream_packet (mux->psmux, best->stream)) {
        GST_DEBUG_OBJECT (mux, "Failed to write data packet");
        goto write_fail;
      }
    }
    mux->last_ts = best->last_ts;
  } else {
    /* FIXME: Drain all remaining streams */
    /* At EOS */
    if (mux->gop_list != NULL)
      mpegpsmux_push_gop_list (mux);

    if (!psmux_write_end_code (mux->psmux)) {
      GST_WARNING_OBJECT (mux, "Writing MPEG PS Program end code failed.");
    }
    gst_pad_push_event (mux->srcpad, gst_event_new_eos ());

    ret = GST_FLOW_EOS;
  }

done:

  return ret;
new_seg_fail:
  return GST_FLOW_ERROR;
write_fail:
  /* FIXME: Failed writing data for some reason. Should set appropriate error */
  return mux->last_flow_ret;
}

static GstPad *
mpegpsmux_request_new_pad (GstElement * element,
    GstPadTemplate * templ, const gchar * name, const GstCaps * caps)
{
  MpegPsMux *mux = GST_MPEG_PSMUX (element);
  GstPad *pad = NULL;
  MpegPsPadData *pad_data = NULL;

  pad = gst_pad_new_from_template (templ, name);

  pad_data = (MpegPsPadData *) gst_collect_pads_add_pad (mux->collect, pad,
      sizeof (MpegPsPadData), NULL, TRUE);
  if (pad_data == NULL)
    goto pad_failure;

  pad_data->last_ts = GST_CLOCK_TIME_NONE;
  pad_data->codec_data = NULL;
  pad_data->prepare_func = NULL;

  if (G_UNLIKELY (!gst_element_add_pad (element, pad)))
    goto could_not_add;

  return pad;

could_not_add:
  GST_ELEMENT_ERROR (element, STREAM, FAILED,
      ("Internal data stream error."), ("Could not add pad to element"));
  gst_collect_pads_remove_pad (mux->collect, pad);
  gst_object_unref (pad);
  return NULL;
pad_failure:
  GST_ELEMENT_ERROR (element, STREAM, FAILED,
      ("Internal data stream error."), ("Could not add pad to collectpads"));
  gst_object_unref (pad);
  return NULL;
}

static void
mpegpsmux_release_pad (GstElement * element, GstPad * pad)
{
  /* unref pad data (and codec data) */

  MpegPsMux *mux = GST_MPEG_PSMUX (element);
  MpegPsPadData *pad_data = NULL;

  GST_DEBUG_OBJECT (mux, "Pad %" GST_PTR_FORMAT " being released", pad);

  /* Get the MpegPsPadData out of the pad */
  GST_OBJECT_LOCK (pad);
  pad_data = (MpegPsPadData *) gst_pad_get_element_private (pad);
  if (G_LIKELY (pad_data)) {
    /* Free codec data reference if any */
    if (pad_data->codec_data) {
      GST_DEBUG_OBJECT (element, "releasing codec_data reference");
      gst_buffer_unref (pad_data->codec_data);
      pad_data->codec_data = NULL;
    }
  }
  if (pad_data->stream_id == mux->video_stream_id)
    mux->video_stream_id = 0;
  GST_OBJECT_UNLOCK (pad);

  gst_collect_pads_remove_pad (mux->collect, pad);
}

static gboolean
new_packet_cb (guint8 * data, guint len, void *user_data)
{
  /* Called when the PsMux has prepared a packet for output. Return FALSE
   * on error */

  MpegPsMux *mux = (MpegPsMux *) user_data;
  GstBuffer *buf;
  GstFlowReturn ret;

  GST_LOG_OBJECT (mux, "Outputting a packet of length %d", len);

  data = g_memdup (data, len);
  buf = gst_buffer_new_wrapped (data, len);

  GST_BUFFER_TIMESTAMP (buf) = mux->last_ts;

  if (mux->aggregate_gops) {
    if (mux->gop_list == NULL)
      mux->gop_list = gst_buffer_list_new ();

    gst_buffer_list_add (mux->gop_list, buf);
    return TRUE;
  }

  ret = gst_pad_push (mux->srcpad, buf);

  if (G_UNLIKELY (ret != GST_FLOW_OK)) {
    mux->last_flow_ret = ret;
    return FALSE;
  }

  return TRUE;
}

/* prepare the source pad for output */
static gboolean
mpegpsdemux_prepare_srcpad (MpegPsMux * mux)
{
  GstSegment segment;
  GValue val = { 0, };
  GList *headers, *l;
  GstCaps *caps;
  gchar s_id[32];

  /* stream-start (FIXME: create id based on input ids) */
  g_snprintf (s_id, sizeof (s_id), "mpegpsmux-%08x", g_random_int ());
  gst_pad_push_event (mux->srcpad, gst_event_new_stream_start (s_id));

  caps = gst_caps_new_simple ("video/mpeg",
      "mpegversion", G_TYPE_INT, 2, "systemstream", G_TYPE_BOOLEAN, TRUE, NULL);

  headers = psmux_get_stream_headers (mux->psmux);
  g_value_init (&val, GST_TYPE_ARRAY);
  for (l = headers; l != NULL; l = l->next) {
    GValue buf_val = { 0, };

    g_value_init (&buf_val, GST_TYPE_BUFFER);
    gst_value_take_buffer (&buf_val, GST_BUFFER (l->data));
    l->data = NULL;
    gst_value_array_append_value (&val, &buf_val);
    g_value_unset (&buf_val);
  }
  gst_caps_set_value (caps, "streamheader", &val);
  g_value_unset (&val);
  g_list_free (headers);

  /* Set caps on src pad and push new segment */
  gst_pad_push_event (mux->srcpad, gst_event_new_caps (caps));
  gst_caps_unref (caps);

  gst_segment_init (&segment, GST_FORMAT_BYTES);
  gst_pad_push_event (mux->srcpad, gst_event_new_segment (&segment));

  return TRUE;
}

static GstStateChangeReturn
mpegpsmux_change_state (GstElement * element, GstStateChange transition)
{
  /* control the collect pads */

  MpegPsMux *mux = GST_MPEG_PSMUX (element);
  GstStateChangeReturn ret;

  switch (transition) {
    case GST_STATE_CHANGE_NULL_TO_READY:
      break;
    case GST_STATE_CHANGE_READY_TO_PAUSED:
      gst_collect_pads_start (mux->collect);
      break;
    case GST_STATE_CHANGE_PAUSED_TO_PLAYING:
      break;
    case GST_STATE_CHANGE_PAUSED_TO_READY:
      gst_collect_pads_stop (mux->collect);
      break;
    case GST_STATE_CHANGE_READY_TO_NULL:
      break;
    default:
      break;
  }

  ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition);

  switch (transition) {
    default:
      break;
  }

  return ret;
}

static gboolean
plugin_init (GstPlugin * plugin)
{
  if (!gst_element_register (plugin, "mpegpsmux", GST_RANK_PRIMARY,
          mpegpsmux_get_type ()))
    return FALSE;

  GST_DEBUG_CATEGORY_INIT (mpegpsmux_debug, "mpegpsmux", 0,
      "MPEG Program Stream muxer");

  return TRUE;
}

GST_PLUGIN_DEFINE (GST_VERSION_MAJOR, GST_VERSION_MINOR,
    mpegpsmux, "MPEG-PS muxer",
    plugin_init, VERSION, "LGPL", GST_PACKAGE_NAME, GST_PACKAGE_ORIGIN);
