4 * Copyright(c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
6 * Contact: JongHyuk Choi <jhchoi.choi@samsung.com>, heechul jeon <heechul.jeon@samsung.co>,
7 * YoungHwan An <younghwan_.an@samsung.com>, Eunhae Choi <eunhae1.choi@samsung.com>
9 * Licensed under the Apache License, Version 2.0(the "License");
10 * you may not use this file except in compliance with the License.
11 * You may obtain a copy of the License at
13 * http://www.apache.org/licenses/LICENSE-2.0
15 * Unless required by applicable law or agreed to in writing, software
16 * distributed under the License is distributed on an "AS IS" BASIS,
17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18 * See the License for the specific language governing permissions and
19 * limitations under the License.
23 /*===========================================================================================
27 ========================================================================================== */
29 #include "mm_player_es.h"
30 #include "mm_player_utils.h"
32 #include <gst/app/gstappsrc.h>
34 /*---------------------------------------------------------------------------
35 | LOCAL VARIABLE DEFINITIONS for internal |
36 ---------------------------------------------------------------------------*/
37 #define DEFAULT_FRAMERATE_NUM 30
38 #define DEFAULT_FRAMERATE_DEN 1
39 #define DEFAULT_VIDEO_FRAME_DURATION 33 /* ms */
40 #define PLAYER_DATA_PUSH_WAIT_COUNT 10
41 #define PLAYER_STATE_CHECK_INTERVAL (100 * 1000)
43 /*---------------------------------------------------------------------------
44 | LOCAL FUNCTION PROTOTYPES: |
45 ---------------------------------------------------------------------------*/
46 static gboolean __mm_player_is_codec_data_changed(mmplayer_t *player, media_packet_h packet, mmplayer_stream_type_e streamtype);
48 /*===========================================================================================
50 | FUNCTION DEFINITIONS |
52 ========================================================================================== */
55 __convert_media_format_video_mime_to_str(mmplayer_video_stream_info_t *video,
56 media_format_mimetype_e mime)
58 MMPLAYER_RETURN_VAL_IF_FAIL(video, MM_ERROR_INVALID_ARGUMENT);
61 case MEDIA_FORMAT_MPEG4_SP:
62 video->mime = g_strdup("video/mpeg");
65 case MEDIA_FORMAT_H264_SP:
66 case MEDIA_FORMAT_H264_MP:
67 case MEDIA_FORMAT_H264_HP:
68 video->mime = g_strdup("video/x-h264");
71 video->mime = g_strdup("unknown");
79 __convert_media_format_audio_mime_to_str(mmplayer_audio_stream_info_t *audio,
80 media_format_mimetype_e mime)
82 MMPLAYER_RETURN_VAL_IF_FAIL(audio, MM_ERROR_INVALID_ARGUMENT);
85 case MEDIA_FORMAT_AAC:
86 audio->mime = g_strdup("audio/mpeg");
90 audio->mime = g_strdup("unknown");
98 __parse_media_format(mmplayer_video_stream_info_t *video,
99 mmplayer_audio_stream_info_t *audio, media_format_h format)
102 media_format_mimetype_e mime;
107 if (media_format_get_audio_info(format, &mime, &channel, &samplerate, NULL,
108 &avg_bps) != MEDIA_FORMAT_ERROR_NONE) {
109 LOGE("media_format_get_audio_info failed");
110 return MM_ERROR_PLAYER_INTERNAL;
112 if (mime & MEDIA_FORMAT_AAC) {
113 bool is_adts = false;
114 media_format_get_audio_aac_type (format, &is_adts);
116 audio->user_info = 1;
118 audio->user_info = 2;
120 /* FIXME : Check other mime type (now support AAC only) */
121 __convert_media_format_audio_mime_to_str(audio, mime);
122 audio->sample_rate = samplerate;
123 audio->channels = channel;
127 media_format_mimetype_e mime;
133 if (media_format_get_video_info(format, &mime, &width, &height, &avg_bps,
134 NULL) != MEDIA_FORMAT_ERROR_NONE) {
135 LOGE("media_format_get_video_info failed");
136 return MM_ERROR_PLAYER_INTERNAL;
139 if (media_format_get_video_frame_rate(format, &frame_rate))
140 LOGW("failed to get video frame rate, will be set 30.");
142 LOGD("frame_rate %d", frame_rate);
144 __convert_media_format_video_mime_to_str(video, mime);
146 video->width = width;
147 video->height = height;
148 video->framerate_num = (frame_rate > 0) ? frame_rate : DEFAULT_FRAMERATE_NUM;
149 video->framerate_den = DEFAULT_FRAMERATE_DEN;
152 return MM_ERROR_NONE;
156 __mmplayer_is_video_info_changed (MMHandleType hplayer, media_format_h fmt)
158 mmplayer_t *player = (mmplayer_t *)hplayer;
159 gboolean ret = FALSE;
160 GstStructure *str = NULL;
161 media_format_mimetype_e mimetype = 0;
162 gint cur_width = 0, width = 0;
163 gint cur_height = 0, height = 0;
167 MMPLAYER_RETURN_VAL_IF_FAIL(player && player->v_stream_caps, FALSE);
168 MMPLAYER_RETURN_VAL_IF_FAIL(fmt, FALSE);
170 if (MMPLAYER_CURRENT_STATE(player) != MM_PLAYER_STATE_PAUSED &&
171 MMPLAYER_CURRENT_STATE(player) != MM_PLAYER_STATE_PLAYING) {
172 LOGW("skip update video info, state: %s", MMPLAYER_STATE_GET_NAME(MMPLAYER_CURRENT_STATE(player)));
176 str = gst_caps_get_structure(player->v_stream_caps, 0);
178 LOGE("failed to get caps info");
182 if (!gst_structure_get_int(str, "width", &cur_width))
183 LOGD("missing 'width' field in video caps");
185 if (!gst_structure_get_int(str, "height", &cur_height))
186 LOGD("missing 'height' field in video caps");
188 media_format_get_video_info(fmt, &mimetype, &width, &height, NULL, NULL);
189 if ((cur_width != width) || (cur_height != height)) {
190 LOGW("resolution is changed %dx%d -> %dx%d",
191 cur_width, cur_height, width, height);
192 _mmplayer_set_video_info(hplayer, fmt);
201 __mmplayer_is_audio_info_changed (MMHandleType hplayer, media_format_h fmt)
203 mmplayer_t *player = (mmplayer_t *)hplayer;
204 gboolean ret = FALSE;
205 GstStructure *str = NULL;
206 media_format_mimetype_e mimetype = 0;
207 gint cur_samplerate = 0, samplerate = 0;
208 gint cur_channel = 0, channel = 0;
212 MMPLAYER_RETURN_VAL_IF_FAIL(player && player->a_stream_caps, FALSE);
213 MMPLAYER_RETURN_VAL_IF_FAIL(fmt, FALSE);
215 if (MMPLAYER_CURRENT_STATE(player) != MM_PLAYER_STATE_PAUSED &&
216 MMPLAYER_CURRENT_STATE(player) != MM_PLAYER_STATE_PLAYING) {
217 LOGW("skip update audio info, state: %s", MMPLAYER_STATE_GET_NAME(MMPLAYER_CURRENT_STATE(player)));
221 str = gst_caps_get_structure(player->a_stream_caps, 0);
223 LOGE("failed to get caps info");
227 if (!gst_structure_get_int(str, "channels", &cur_channel))
228 LOGD("missing 'channel' field in audio caps");
230 if (!gst_structure_get_int(str, "rate", &cur_samplerate))
231 LOGD("missing 'rate' field in audio caps");
233 media_format_get_audio_info(fmt, &mimetype, &channel, &samplerate, NULL, NULL);
234 if ((cur_channel != channel) || (cur_samplerate != samplerate)) {
235 LOGW("audio info change channel(%d), samplerate(%d) -> %d, %d",
236 cur_channel, cur_samplerate, channel, samplerate);
237 _mmplayer_set_audio_info(hplayer, fmt);
246 __mmplayer_get_source_element(mmplayer_t *player, mmplayer_stream_type_e type)
248 main_element_id_e elemId = MMPLAYER_M_NUM;
250 if (player && player->pipeline && player->pipeline->mainbin) {
251 /* get elem according to the stream type */
252 if (type == MM_PLAYER_STREAM_TYPE_AUDIO) {
253 if (player->pipeline->mainbin[MMPLAYER_M_2ND_SRC].gst)
254 elemId = MMPLAYER_M_2ND_SRC;
255 else if (g_strrstr(GST_ELEMENT_NAME(player->pipeline->mainbin[MMPLAYER_M_SRC].gst), "audio_appsrc"))
256 elemId = MMPLAYER_M_SRC;
257 } else if (type == MM_PLAYER_STREAM_TYPE_VIDEO) {
258 elemId = MMPLAYER_M_SRC;
259 } else if (type == MM_PLAYER_STREAM_TYPE_TEXT) {
260 elemId = MMPLAYER_M_SUBSRC;
263 if (elemId != MMPLAYER_M_NUM)
264 return player->pipeline->mainbin[elemId].gst;
271 _mmplayer_set_media_stream_max_size(MMHandleType hplayer, mmplayer_stream_type_e type, guint64 max_size)
273 mmplayer_t *player = (mmplayer_t *)hplayer;
274 GstElement *element = NULL;
277 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
279 if ((type < MM_PLAYER_STREAM_TYPE_AUDIO) ||
280 (type > MM_PLAYER_STREAM_TYPE_TEXT) ||
282 LOGE("Invalid param type:%d, max_size:%"G_GUINT64_FORMAT, type, max_size);
283 return MM_ERROR_INVALID_ARGUMENT;
286 LOGD("type:%s, max_size %"G_GUINT64_FORMAT, MMPLAYER_STREAM_TYPE_GET_NAME(type), max_size);
288 if ((element = __mmplayer_get_source_element(player, type))) {
289 LOGD("update max_size of %s", GST_ELEMENT_NAME(element));
290 g_object_set(G_OBJECT(element), "max-bytes", max_size, NULL);
293 player->media_stream_buffer_max_size[type] = max_size;
296 return MM_ERROR_NONE;
300 _mmplayer_get_media_stream_max_size(MMHandleType hplayer, mmplayer_stream_type_e type, guint64 *max_size)
302 mmplayer_t *player = (mmplayer_t *)hplayer;
306 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
307 MMPLAYER_RETURN_VAL_IF_FAIL(max_size, MM_ERROR_INVALID_ARGUMENT);
309 *max_size = player->media_stream_buffer_max_size[type];
313 return MM_ERROR_NONE;
317 _mmplayer_set_media_stream_min_percent(MMHandleType hplayer, mmplayer_stream_type_e type, guint min_percent)
319 mmplayer_t *player = (mmplayer_t *)hplayer;
320 GstElement *element = NULL;
324 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
326 if ((type < MM_PLAYER_STREAM_TYPE_AUDIO) || (type > MM_PLAYER_STREAM_TYPE_TEXT)) {
327 LOGE("Invalid param type:%d", type);
328 return MM_ERROR_INVALID_ARGUMENT;
331 LOGD("type:%s, min_per %u", MMPLAYER_STREAM_TYPE_GET_NAME(type), min_percent);
333 if ((element = __mmplayer_get_source_element(player, type))) {
334 LOGD("update min_per of %s", GST_ELEMENT_NAME(element));
335 g_object_set(G_OBJECT(element), "min-percent", min_percent, NULL);
338 player->media_stream_buffer_min_percent[type] = min_percent;
341 return MM_ERROR_NONE;
345 _mmplayer_get_media_stream_min_percent(MMHandleType hplayer, mmplayer_stream_type_e type, guint *min_percent)
347 mmplayer_t *player = (mmplayer_t *)hplayer;
351 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
352 MMPLAYER_RETURN_VAL_IF_FAIL(min_percent, MM_ERROR_INVALID_ARGUMENT);
354 *min_percent = player->media_stream_buffer_min_percent[type];
358 return MM_ERROR_NONE;
362 __mmplayer_check_buffer_level(mmplayer_t *player, GstElement *element, mmplayer_stream_type_e type)
364 guint64 current_level_bytes = 0;
365 guint64 max_bytes = 0;
366 guint current_level_per = 0;
369 MMPLAYER_RETURN_VAL_IF_FAIL(player && element, MM_ERROR_PLAYER_NOT_INITIALIZED);
370 MMPLAYER_RETURN_VAL_IF_FAIL(((type == MM_PLAYER_STREAM_TYPE_AUDIO) || (type == MM_PLAYER_STREAM_TYPE_VIDEO)), MM_ERROR_INVALID_ARGUMENT);
372 if (player->media_stream_buffer_max_size[type] > 0)
373 max_bytes = player->media_stream_buffer_max_size[type];
375 g_object_get(G_OBJECT(element), "max-bytes", &max_bytes, NULL);
377 if (max_bytes == 0) {
378 LOGW("buffer max size is zero");
379 return MM_ERROR_NONE;
382 g_object_get(G_OBJECT(element), "current-level-bytes", ¤t_level_bytes, NULL);
384 if (max_bytes <= current_level_bytes) {
385 LOGE("no available buffer space, type: %s, max %"G_GUINT64_FORMAT", curr %"G_GUINT64_FORMAT,
386 MMPLAYER_STREAM_TYPE_GET_NAME(type), max_bytes, current_level_bytes);
387 return MM_ERROR_PLAYER_BUFFER_SPACE;
390 if (MMPLAYER_CURRENT_STATE(player) != MM_PLAYER_STATE_PLAYING) {
391 current_level_per = (guint)(gst_util_guint64_to_gdouble(current_level_bytes) / gst_util_guint64_to_gdouble(max_bytes) * 100);
393 LOGD("type: %s, min_per %u, curr_per %u max %"G_GUINT64_FORMAT" cur %"G_GUINT64_FORMAT,
394 MMPLAYER_STREAM_TYPE_GET_NAME(type), player->media_stream_buffer_min_percent[type],
396 player->media_stream_buffer_max_size[type],
397 current_level_bytes);
399 if (current_level_per < player->media_stream_buffer_min_percent[type]) {
400 MMMessageParamType msg_param = {0,};
402 msg_param.union_type = MM_MSG_UNION_BUFFER_STATUS;
403 msg_param.buffer_status.stream_type = type;
404 msg_param.buffer_status.status = MM_PLAYER_MEDIA_STREAM_BUFFER_UNDERRUN;
405 msg_param.buffer_status.bytes = current_level_bytes;
407 MMPLAYER_POST_MSG(player, MM_MESSAGE_PUSH_BUFFER_STATUS, &msg_param);
412 return MM_ERROR_NONE;
416 _mmplayer_submit_packet(MMHandleType hplayer, media_packet_h packet)
418 int ret = MM_ERROR_NONE;
419 GstBuffer *_buffer = NULL;
420 mmplayer_t *player = (mmplayer_t *)hplayer;
423 GstElement *element = NULL;
424 mmplayer_stream_type_e streamtype = MM_PLAYER_STREAM_TYPE_AUDIO;
425 media_format_h fmt = NULL;
428 gboolean need_update_caps = FALSE;
430 MMPLAYER_RETURN_VAL_IF_FAIL(packet, MM_ERROR_INVALID_ARGUMENT);
431 MMPLAYER_RETURN_VAL_IF_FAIL(player &&
433 player->pipeline->mainbin &&
434 player->pipeline->mainbin[MMPLAYER_M_SRC].gst,
435 MM_ERROR_PLAYER_NOT_INITIALIZED);
437 /* get stream type if audio or video */
438 media_packet_is_audio(packet, &flag);
440 streamtype = MM_PLAYER_STREAM_TYPE_AUDIO;
442 media_packet_is_video(packet, &flag);
444 streamtype = MM_PLAYER_STREAM_TYPE_VIDEO;
446 streamtype = MM_PLAYER_STREAM_TYPE_TEXT;
449 element = __mmplayer_get_source_element(player, streamtype);
451 LOGE("there is no source element of type %d", streamtype);
452 ret = MM_ERROR_PLAYER_INTERNAL;
456 /* check buffer level */
457 ret = __mmplayer_check_buffer_level(player, element, streamtype);
458 if (ret != MM_ERROR_NONE)
462 if (media_packet_get_buffer_data_ptr(packet, (void **)&buf) != MEDIA_PACKET_ERROR_NONE) {
463 LOGE("failed to get buffer data ptr");
464 ret = MM_ERROR_PLAYER_INTERNAL;
468 if (media_packet_get_buffer_size(packet, &size) != MEDIA_PACKET_ERROR_NONE) {
469 LOGE("failed to get buffer size");
470 ret = MM_ERROR_PLAYER_INTERNAL;
474 if (buf != NULL && size > 0) {
475 GstMapInfo buff_info = GST_MAP_INFO_INIT;
477 uint64_t duration = 0;
481 _buffer = gst_buffer_new_and_alloc(size);
484 LOGE("failed to allocate memory for push buffer");
485 ret = MM_ERROR_PLAYER_NO_FREE_SPACE;
489 if (gst_buffer_map(_buffer, &buff_info, GST_MAP_READWRITE)) {
490 memcpy(buff_info.data, buf, size);
491 buff_info.size = size;
493 gst_buffer_unmap(_buffer, &buff_info);
496 /* wait till the pipeline is ready to get data, if not some data is missed */
497 while ((GST_STATE(element) < GST_STATE_PAUSED) && (wait_cnt < PLAYER_DATA_PUSH_WAIT_COUNT)) {
498 LOGW("wait to update source state : %d, %d", player->state, GST_STATE(element));
499 usleep(PLAYER_STATE_CHECK_INTERVAL);
503 if (wait_cnt == PLAYER_DATA_PUSH_WAIT_COUNT) {
504 LOGE("source is not ready %d", GST_STATE(element));
505 ret = MM_ERROR_PLAYER_INTERNAL;
509 if (streamtype == MM_PLAYER_STREAM_TYPE_VIDEO) {
510 /* get format to check video format */
511 media_packet_get_format(packet, &fmt);
513 need_update_caps |= __mmplayer_is_video_info_changed (hplayer, fmt);
514 media_format_unref(fmt);
516 need_update_caps |= __mm_player_is_codec_data_changed(player, packet, streamtype);
518 if (need_update_caps)
519 g_object_set(G_OBJECT(player->pipeline->mainbin[MMPLAYER_M_SRC].gst),
520 "caps", player->v_stream_caps, NULL);
523 if (media_packet_get_duration(packet, &duration) != MEDIA_PACKET_ERROR_NONE) {
524 LOGW("failed to get duration info");
525 /* keep push without error handling */
529 duration = DEFAULT_VIDEO_FRAME_DURATION * GST_MSECOND;
531 GST_BUFFER_DURATION(_buffer) = (GstClockTime)duration;
532 } else if (streamtype == MM_PLAYER_STREAM_TYPE_AUDIO) {
533 media_packet_get_format(packet, &fmt);
535 need_update_caps |= __mmplayer_is_audio_info_changed (hplayer, fmt);
536 media_format_unref(fmt);
538 need_update_caps |= __mm_player_is_codec_data_changed(player, packet, streamtype);
540 if (need_update_caps) {
541 LOGD("update audio caps");
542 g_object_set(G_OBJECT(player->pipeline->mainbin[MMPLAYER_M_SRC].gst),
543 "caps", player->a_stream_caps, NULL);
548 if (media_packet_get_pts(packet, &pts) != MEDIA_PACKET_ERROR_NONE) {
549 LOGE("failed to get pts info");
550 ret = MM_ERROR_PLAYER_INTERNAL;
553 GST_BUFFER_PTS(_buffer) = (GstClockTime)pts;
555 if (MMPLAYER_CURRENT_STATE(player) != MM_PLAYER_STATE_PLAYING) {
556 /* the pushed pts should be lager than current position if it is not in playing state. */
557 LOGD("type:%s, curr pos: %"G_GINT64_FORMAT", pushed pts:%"G_GINT64_FORMAT", size:%"G_GUINT64_FORMAT,
558 MMPLAYER_STREAM_TYPE_GET_NAME(streamtype), player->last_position, (GstClockTime)pts, (guint64)size);
561 gst_app_src_push_buffer(GST_APP_SRC(element), _buffer);
563 LOGW("There is no data to push : buf %p, size %"G_GUINT64_FORMAT, buf, (guint64)size);
567 if (media_packet_is_end_of_stream(packet, &is_eos) != MEDIA_PACKET_ERROR_NONE) {
568 LOGE("failed to get eos info");
569 return MM_ERROR_PLAYER_INTERNAL;
573 LOGW("we got eos of stream type(%s)", MMPLAYER_STREAM_TYPE_GET_NAME(streamtype));
574 g_signal_emit_by_name(element, "end-of-stream", &ret);
580 gst_buffer_unref(_buffer);
585 __mmplayer_video_caps_new(MMHandleType hplayer, mmplayer_video_stream_info_t *video,
586 const char *fieldname, ...)
589 GstCaps *caps = NULL;
590 GstStructure *structure = NULL;
592 mmplayer_t *player = MM_PLAYER_CAST(hplayer);
595 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
596 MMPLAYER_RETURN_VAL_IF_FAIL(video, MM_ERROR_PLAYER_NOT_INITIALIZED);
598 LOGD("width=%d height=%d framerate num=%d, den=%d",
599 video->width, video->height, video->framerate_num, video->framerate_den);
601 caps = gst_caps_new_simple(video->mime,
602 "width", G_TYPE_INT, video->width,
603 "height", G_TYPE_INT, video->height,
604 "framerate", GST_TYPE_FRACTION, video->framerate_num, video->framerate_den, NULL);
606 for (cap_size = 0; cap_size < gst_caps_get_size(caps); cap_size++) {
607 va_start(var_args, fieldname);
608 structure = gst_caps_get_structure(caps, cap_size);
609 gst_structure_set_valist(structure, fieldname, var_args);
613 if (video->extradata_size) {
614 GstBuffer *buf = NULL;
615 GstMapInfo buff_info = GST_MAP_INFO_INIT;
617 buf = gst_buffer_new_and_alloc(video->extradata_size);
619 if (gst_buffer_map(buf, &buff_info, GST_MAP_READ)) {
620 memcpy(buff_info.data, video->codec_extradata, video->extradata_size);
621 buff_info.size = video->extradata_size;
622 gst_buffer_unmap(buf, &buff_info);
625 gst_caps_set_simple(caps, "codec_data", GST_TYPE_BUFFER, buf, NULL);
626 gst_buffer_unref(buf);
629 if (player->v_stream_caps) {
630 LOGW("caps will be updated ");
632 gst_caps_unref(player->v_stream_caps);
633 player->v_stream_caps = NULL;
636 player->v_stream_caps = gst_caps_copy(caps);
637 MMPLAYER_LOG_GST_CAPS_TYPE(player->v_stream_caps);
638 gst_caps_unref(caps);
642 return MM_ERROR_NONE;
646 __mmplayer_set_uri_type(mmplayer_t *player)
650 player->profile.uri_type = MM_PLAYER_URI_TYPE_MS_BUFF;
651 player->es_player_push_mode = TRUE;
658 _mmplayer_set_video_info(MMHandleType hplayer, media_format_h format)
660 mmplayer_t *player = MM_PLAYER_CAST(hplayer);
661 mmplayer_video_stream_info_t video = { 0, };
662 int ret = MM_ERROR_NONE;
663 gboolean drc = FALSE;
667 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
669 __mmplayer_set_uri_type(player);
671 ret = __parse_media_format(&video, NULL, format);
672 if (ret != MM_ERROR_NONE)
675 mm_attrs_get_int_by_name(player->attrs, MM_PLAYER_DRC_MODE, &drc);
677 if (strstr(video.mime, "video/mpeg")) {
678 __mmplayer_video_caps_new(hplayer, &video,
679 "mpegversion", G_TYPE_INT, video.version,
680 "systemstream", G_TYPE_BOOLEAN, FALSE,
681 "adaptive-streaming", G_TYPE_BOOLEAN, drc, NULL);
682 } else if (strstr(video.mime, "video/x-h264")) {
683 __mmplayer_video_caps_new(hplayer, &video,
684 "stream-format", G_TYPE_STRING, "byte-stream",
685 "alignment", G_TYPE_STRING, "au",
686 "adaptive-streaming", G_TYPE_BOOLEAN, drc, NULL);
688 g_free((char *)video.mime);
692 return MM_ERROR_NONE;
696 _mmplayer_set_audio_info(MMHandleType hplayer, media_format_h format)
698 mmplayer_t *player = MM_PLAYER_CAST(hplayer);
699 GstCaps *caps = NULL;
700 mmplayer_audio_stream_info_t audio = { 0, };
701 int ret = MM_ERROR_NONE;
705 MMPLAYER_RETURN_VAL_IF_FAIL(hplayer, MM_ERROR_PLAYER_NOT_INITIALIZED);
707 __mmplayer_set_uri_type(player);
709 ret = __parse_media_format(NULL, &audio, format);
710 if (ret != MM_ERROR_NONE)
714 LOGD("set audio player[%p] version=%d rate=%d channel=%d",
715 player, audio.version, audio.sample_rate, audio.channels);
717 if (strstr(audio.mime, "audio/mpeg")) {
718 if (audio.version == 2) { // aac
719 gchar *stream_format = NULL;
721 if (audio.user_info == 0)
722 stream_format = g_strdup("raw");
723 else if (audio.user_info == 1)
724 stream_format = g_strdup("adts");
725 else if (audio.user_info == 2)
726 stream_format = g_strdup("adif");
728 caps = gst_caps_new_simple("audio/mpeg",
729 "channels", G_TYPE_INT, audio.channels,
730 "rate", G_TYPE_INT, audio.sample_rate,
731 "mpegversion", G_TYPE_INT, audio.version,
732 "stream-format", G_TYPE_STRING, stream_format, NULL);
734 MMPLAYER_FREEIF(stream_format);
735 stream_format = NULL;
736 } else if (audio.version == 1 ) { // mp3
737 caps = gst_caps_new_simple("audio/mpeg",
738 "channels", G_TYPE_INT, audio.channels,
739 "rate", G_TYPE_INT, audio.sample_rate,
740 "mpegversion", G_TYPE_INT, audio.version,
741 "layer", G_TYPE_INT, audio.user_info, NULL);
745 else if (strstr(audio.mime, "audio/x-raw-int")) {
746 caps = gst_caps_new_simple("audio/x-raw-int",
747 "width", G_TYPE_INT, audio.width,
748 "depth", G_TYPE_INT, audio.depth,
749 "endianness", G_TYPE_INT, audio.endianness,
750 "signed", G_TYPE_BOOLEAN, audio.signedness,
751 "channels", G_TYPE_INT, audio.channels,
752 "rate", G_TYPE_INT, audio.sample_rate, NULL);
754 caps = gst_caps_new_simple(audio.mime,
755 "channels", G_TYPE_INT, audio.channels,
756 "rate", G_TYPE_INT, audio.sample_rate, NULL);
760 if (audio.extradata_size && audio.codec_extradata) {
761 GstBuffer *buf = NULL;
762 GstMapInfo buff_info = GST_MAP_INFO_INIT;
764 buf = gst_buffer_new_and_alloc(audio.extradata_size);
766 if (gst_buffer_map(buf, &buff_info, GST_MAP_READ)) {
767 memcpy(buff_info.data, audio.codec_extradata, audio.extradata_size);
768 gst_buffer_unmap(buf, &buff_info);
771 gst_caps_set_simple(caps, "codec_data", GST_TYPE_BUFFER, buf, NULL);
772 gst_buffer_unref(buf);
773 g_free((char *)audio.codec_extradata);
776 g_free((char *)audio.mime);
778 player->a_stream_caps = gst_caps_copy(caps);
779 gst_caps_unref(caps);
783 return MM_ERROR_NONE;
787 _mmplayer_set_subtitle_info(MMHandleType hplayer,
788 mmplayer_subtitle_stream_info_t *subtitle)
791 mmplayer_t *player = MM_PLAYER_CAST(hplayer);
792 GstCaps *caps = NULL;
796 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
797 MMPLAYER_RETURN_VAL_IF_FAIL(info, MM_ERROR_PLAYER_NOT_INITIALIZED);
799 LOGD("set subtitle player[%p] info [%p]", player, info);
802 caps = gst_caps_new_simple(info->mime, NULL, NULL); // TO CHECK
806 if (strstr(info->mime, "application/x-xsub")) {
807 gst_caps_set_simple(caps, "codec_tag", G_TYPE_UINT, info->codec_tag, NULL);
808 } else if (strstr(info->mime, "application/x-smpte-text")) {
810 gst_caps_set_simple(caps, "ttml_priv_data", G_TYPE_POINTER,
811 info->context, NULL);
815 player->s_stream_caps = gst_caps_copy(caps);
817 gst_caps_unref(caps);
822 return MM_ERROR_NONE;
826 _mmplayer_set_media_stream_dynamic_resolution(MMHandleType hplayer, bool drc)
828 mmplayer_t *player = MM_PLAYER_CAST(hplayer);
829 int ret = MM_ERROR_NONE;
833 MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
835 mm_player_set_attribute(hplayer, NULL, MM_PLAYER_DRC_MODE, (int)drc, NULL);
836 if (player->v_stream_caps) {
837 gst_caps_set_simple(player->v_stream_caps,
838 "adaptive-streaming", G_TYPE_BOOLEAN, drc, NULL);
839 MMPLAYER_LOG_GST_CAPS_TYPE(player->v_stream_caps);
848 __mm_player_is_codec_data_changed(mmplayer_t *player, media_packet_h packet,
849 mmplayer_stream_type_e streamtype)
851 GstCaps *cur_caps = NULL;
852 GstCaps *new_caps = NULL;
853 GstStructure *str = NULL;
854 const GValue *value = NULL;
855 GstBuffer *buffer = NULL;
856 GstMapInfo codec_data_map = GST_MAP_INFO_INIT;
857 GstBuffer *new_buffer = NULL;
858 char *codec_data = NULL;
859 unsigned int codec_data_size = 0;
861 MMPLAYER_RETURN_VAL_IF_FAIL(player, FALSE);
862 MMPLAYER_RETURN_VAL_IF_FAIL(packet, FALSE);
864 if (media_packet_get_codec_data(packet, (void **)&codec_data, &codec_data_size)
865 != MEDIA_PACKET_ERROR_NONE)
868 if (codec_data_size == 0) {
869 LOGW("codec_data_size is zero");
873 if (streamtype == MM_PLAYER_STREAM_TYPE_AUDIO) {
874 cur_caps = player->a_stream_caps;
875 } else if (streamtype == MM_PLAYER_STREAM_TYPE_VIDEO) {
876 cur_caps = player->v_stream_caps;
878 LOGW("streamtype is not audio or video");
883 LOGW("Current caps is NULL");
887 str = gst_caps_get_structure(cur_caps, 0);
889 LOGW("Failed to get caps info");
893 /* Check if the codec data in the saved caps have been changed */
894 value = gst_structure_get_value(str, "codec_data");
897 buffer = gst_value_get_buffer(value);
898 if (!gst_buffer_map(buffer, &codec_data_map, GST_MAP_READ)) {
899 LOGW("codec data buffer map failed");
902 if (codec_data_map.size == codec_data_size) {
903 for (i = 0; i <= codec_data_map.size; i++) {
904 if (codec_data_map.data[i] != codec_data[i])
907 gst_buffer_unmap(buffer, &codec_data_map);
910 gst_buffer_unmap(buffer, &codec_data_map);
913 new_caps = gst_caps_copy(cur_caps);
915 LOGW("Failed to copy caps");
919 new_buffer = gst_buffer_new_allocate(NULL, codec_data_size, NULL);
921 LOGW("Failed to alloc gst buffer for codec data");
922 gst_caps_unref(new_caps);
925 gst_buffer_fill(new_buffer, 0, codec_data, codec_data_size);
926 gst_caps_set_simple(new_caps, "codec_data", GST_TYPE_BUFFER, new_buffer, NULL);
927 gst_buffer_unref(new_buffer);
929 if (streamtype == MM_PLAYER_STREAM_TYPE_AUDIO)
930 player->a_stream_caps = new_caps;
931 else if (streamtype == MM_PLAYER_STREAM_TYPE_VIDEO)
932 player->v_stream_caps = new_caps;
934 gst_caps_unref(cur_caps);
936 LOGD("need to update caps due to codec data is changed");