- int ret = MM_ERROR_NONE;
- GstBuffer *_buffer = NULL;
- mm_player_t *player = (mm_player_t *) hplayer;
- guint8 *buf = NULL;
- uint64_t size = 0;
- GstElement* element = NULL;
- MMPlayerStreamType streamtype = MM_PLAYER_STREAM_TYPE_AUDIO;
- media_format_h fmt = NULL;
- bool flag = FALSE;
- bool is_eos = FALSE;
-
- MMPLAYER_RETURN_VAL_IF_FAIL (packet, MM_ERROR_INVALID_ARGUMENT);
- MMPLAYER_RETURN_VAL_IF_FAIL ( player &&
- player->pipeline &&
- player->pipeline->mainbin &&
- player->pipeline->mainbin[MMPLAYER_M_SRC].gst,
- MM_ERROR_PLAYER_INTERNAL );
-
- /* get stream type if audio or video */
- media_packet_is_audio (packet, &flag);
- if (flag) {
- streamtype = MM_PLAYER_STREAM_TYPE_AUDIO;
- } else {
- media_packet_is_video (packet, &flag);
- if (flag)
- streamtype = MM_PLAYER_STREAM_TYPE_VIDEO;
- else
- streamtype = MM_PLAYER_STREAM_TYPE_TEXT;
- }
-
- element = __mmplayer_get_source_element(player, streamtype);
- if (!element) {
- LOGE ("there is no source element of type %d", streamtype);
- ret = MM_ERROR_PLAYER_INTERNAL;
- goto ERROR;
- }
-
- /* check buffer level */
- ret = __mmplayer_check_buffer_level (player, element, streamtype);
- if (ret != MM_ERROR_NONE)
- return ret;
-
- /* get data */
- if (media_packet_get_buffer_data_ptr (packet, (void **) &buf) != MEDIA_PACKET_ERROR_NONE) {
- LOGE("failed to get buffer data ptr");
- ret = MM_ERROR_PLAYER_INTERNAL;
- goto ERROR;
- }
-
- if (media_packet_get_buffer_size (packet, &size) != MEDIA_PACKET_ERROR_NONE) {
- LOGE("failed to get buffer size");
- ret = MM_ERROR_PLAYER_INTERNAL;
- goto ERROR;
- }
-
- if (buf != NULL && size > 0) {
- GstMapInfo buff_info = GST_MAP_INFO_INIT;
- uint64_t pts = 0;
-
- /* get size */
- _buffer = gst_buffer_new_and_alloc (size);
-
- if (!_buffer) {
- LOGE("failed to allocate memory for push buffer\n");
- ret = MM_ERROR_PLAYER_NO_FREE_SPACE;
- goto ERROR;
- }
-
- if (gst_buffer_map (_buffer, &buff_info, GST_MAP_READWRITE)) {
-
- memcpy (buff_info.data, buf, size);
- buff_info.size = size;
-
- gst_buffer_unmap (_buffer, &buff_info);
- }
-
- if (streamtype == MM_PLAYER_STREAM_TYPE_VIDEO) {
- /* get format to check video format */
- media_packet_get_format (packet, &fmt);
- if (fmt) {
- if (_mmplayer_update_video_info(hplayer, fmt)) {
- LOGD("update video caps");
- g_object_set(G_OBJECT(player->pipeline->mainbin[MMPLAYER_M_SRC].gst),
- "caps", player->v_stream_caps, NULL);
- }
- }
- }
-
- /* get pts */
- if (media_packet_get_pts (packet, &pts) != MEDIA_PACKET_ERROR_NONE) {
- LOGE("failed to get pts info");
- ret = MM_ERROR_PLAYER_INTERNAL;
- goto ERROR;
- }
- GST_BUFFER_PTS (_buffer) = (GstClockTime)pts;
- gst_app_src_push_buffer (GST_APP_SRC (element), _buffer);
- }
-
- /* check eos */
- if (media_packet_is_end_of_stream(packet, &is_eos) != MEDIA_PACKET_ERROR_NONE) {
- LOGE("failed to get eos info");
- ret = MM_ERROR_PLAYER_INTERNAL;
- goto ERROR;
- }
-
- if (is_eos) {
- LOGW ("we got eos of stream type(%d)", streamtype);
- g_signal_emit_by_name (element, "end-of-stream", &ret);
- }
+ int ret = MM_ERROR_NONE;
+ GstBuffer *_buffer = NULL;
+ mmplayer_t *player = (mmplayer_t *)hplayer;
+ guint8 *buf = NULL;
+ uint64_t size = 0;
+ GstElement *element = NULL;
+ mmplayer_stream_type_e streamtype = MM_PLAYER_STREAM_TYPE_AUDIO;
+ media_format_h fmt = NULL;
+ bool flag = false;
+ bool is_eos = false;
+ gboolean need_update_caps = FALSE;
+
+ MMPLAYER_RETURN_VAL_IF_FAIL(packet, MM_ERROR_INVALID_ARGUMENT);
+ MMPLAYER_RETURN_VAL_IF_FAIL(player &&
+ player->pipeline &&
+ player->pipeline->mainbin &&
+ player->pipeline->mainbin[MMPLAYER_M_SRC].gst,
+ MM_ERROR_PLAYER_NOT_INITIALIZED);
+
+ /* get stream type if audio or video */
+ media_packet_is_audio(packet, &flag);
+ if (flag) {
+ streamtype = MM_PLAYER_STREAM_TYPE_AUDIO;
+ } else {
+ media_packet_is_video(packet, &flag);
+ if (flag)
+ streamtype = MM_PLAYER_STREAM_TYPE_VIDEO;
+ else
+ streamtype = MM_PLAYER_STREAM_TYPE_TEXT;
+ }
+
+ element = __mmplayer_get_source_element(player, streamtype);
+ if (!element) {
+ LOGE("there is no source element of type %d", streamtype);
+ ret = MM_ERROR_PLAYER_INTERNAL;
+ goto ERROR;
+ }
+
+ /* check buffer level */
+ ret = __mmplayer_check_buffer_level(player, element, streamtype);
+ if (ret != MM_ERROR_NONE)
+ return ret;
+
+ /* get data */
+ if (media_packet_get_buffer_data_ptr(packet, (void **)&buf) != MEDIA_PACKET_ERROR_NONE) {
+ LOGE("failed to get buffer data ptr");
+ ret = MM_ERROR_PLAYER_INTERNAL;
+ goto ERROR;
+ }
+
+ if (media_packet_get_buffer_size(packet, &size) != MEDIA_PACKET_ERROR_NONE) {
+ LOGE("failed to get buffer size");
+ ret = MM_ERROR_PLAYER_INTERNAL;
+ goto ERROR;
+ }
+
+ if (buf != NULL && size > 0) {
+ GstMapInfo buff_info = GST_MAP_INFO_INIT;
+ uint64_t pts = 0;
+ uint64_t duration = 0;
+ int wait_cnt = 0;
+
+ /* get size */
+ _buffer = gst_buffer_new_and_alloc(size);
+
+ if (!_buffer) {
+ LOGE("failed to allocate memory for push buffer");
+ ret = MM_ERROR_PLAYER_NO_FREE_SPACE;
+ goto ERROR;
+ }
+
+ if (gst_buffer_map(_buffer, &buff_info, GST_MAP_READWRITE)) {
+ memcpy(buff_info.data, buf, size);
+ buff_info.size = size;
+
+ gst_buffer_unmap(_buffer, &buff_info);
+ }
+
+ /* wait till the pipeline is ready to get data, if not some data is missed */
+ while ((GST_STATE(element) < GST_STATE_PAUSED) && (wait_cnt < PLAYER_DATA_PUSH_WAIT_COUNT)) {
+ LOGW("wait to update source state : %d, %d", player->state, GST_STATE(element));
+ usleep(PLAYER_STATE_CHECK_INTERVAL);
+ wait_cnt++;
+ }
+
+ if (wait_cnt == PLAYER_DATA_PUSH_WAIT_COUNT) {
+ LOGE("source is not ready %d", GST_STATE(element));
+ ret = MM_ERROR_PLAYER_INTERNAL;
+ goto ERROR;
+ }
+
+ if (streamtype == MM_PLAYER_STREAM_TYPE_VIDEO) {
+ /* get format to check video format */
+ media_packet_get_format(packet, &fmt);
+ if (fmt) {
+ need_update_caps |= __mmplayer_is_video_info_changed (hplayer, fmt);
+ media_format_unref(fmt);
+ }
+ need_update_caps |= __mm_player_is_codec_data_changed(player, packet, streamtype);
+
+ if (need_update_caps)
+ g_object_set(G_OBJECT(player->pipeline->mainbin[MMPLAYER_M_SRC].gst),
+ "caps", player->v_stream_caps, NULL);
+
+ /* get duration */
+ if (media_packet_get_duration(packet, &duration) != MEDIA_PACKET_ERROR_NONE) {
+ LOGW("failed to get duration info");
+ /* keep push without error handling */
+ }
+
+ if (duration == 0)
+ duration = DEFAULT_VIDEO_FRAME_DURATION * GST_MSECOND;
+
+ GST_BUFFER_DURATION(_buffer) = (GstClockTime)duration;
+ } else if (streamtype == MM_PLAYER_STREAM_TYPE_AUDIO) {
+ media_packet_get_format(packet, &fmt);
+ if (fmt) {
+ need_update_caps |= __mmplayer_is_audio_info_changed (hplayer, fmt);
+ media_format_unref(fmt);
+ }
+ need_update_caps |= __mm_player_is_codec_data_changed(player, packet, streamtype);
+
+ if (need_update_caps) {
+ LOGD("update audio caps");
+ g_object_set(G_OBJECT(player->pipeline->mainbin[MMPLAYER_M_SRC].gst),
+ "caps", player->a_stream_caps, NULL);
+ }
+ }
+
+ /* get pts */
+ if (media_packet_get_pts(packet, &pts) != MEDIA_PACKET_ERROR_NONE) {
+ LOGE("failed to get pts info");
+ ret = MM_ERROR_PLAYER_INTERNAL;
+ goto ERROR;
+ }
+ GST_BUFFER_PTS(_buffer) = (GstClockTime)pts;
+
+ if (MMPLAYER_CURRENT_STATE(player) != MM_PLAYER_STATE_PLAYING) {
+ /* the pushed pts should be lager than current position if it is not in playing state. */
+ LOGD("type:%s, curr pos: %"G_GINT64_FORMAT", pushed pts:%"G_GINT64_FORMAT", size:%"G_GUINT64_FORMAT,
+ MMPLAYER_STREAM_TYPE_GET_NAME(streamtype), player->last_position, (GstClockTime)pts, (guint64)size);
+ }
+
+ gst_app_src_push_buffer(GST_APP_SRC(element), _buffer);
+ } else {
+ LOGW("There is no data to push : buf %p, size %"G_GUINT64_FORMAT, buf, (guint64)size);
+ }
+
+ /* check eos */
+ if (media_packet_is_end_of_stream(packet, &is_eos) != MEDIA_PACKET_ERROR_NONE) {
+ LOGE("failed to get eos info");
+ return MM_ERROR_PLAYER_INTERNAL;
+ }
+
+ if (is_eos) {
+ LOGW("we got eos of stream type(%s)", MMPLAYER_STREAM_TYPE_GET_NAME(streamtype));
+ g_signal_emit_by_name(element, "end-of-stream", &ret);
+ }
+
+ return ret;