AC_SUBST(DLOG_CFLAGS)
AC_SUBST(DLOG_LIBS)
-PKG_CHECK_MODULES(TZPLATFORM_CONFIG, libtzplatform-config)
-
AC_ARG_ENABLE(sdk, AC_HELP_STRING([--enable-sdk], [sdk build]),
[
case "${enableval}" in
Name: libmm-player
Summary: Multimedia Framework Player Library
-Version: 0.5.83
+Version: 0.5.84
Release: 0
Group: Multimedia/Libraries
License: Apache-2.0
BuildRequires: pkgconfig(capi-media-tool)
BuildRequires: pkgconfig(murphy-resource)
BuildRequires: pkgconfig(murphy-glib)
-BuildRequires: pkgconfig(libtzplatform-config)
%description
Multimedia Framework Player Library files.
if WAYLAND_SUPPORT
libmmfplayer_la_CFLAGS += $(GST_WAYLAND_CFLAGS)
libmmfplayer_la_LIBADD += $(GST_WAYLAND_LIBS)
-endif
-
-libmmfplayer_la_CFLAGS += $(TZPLATFORM_CONFIG_CFLAGS)
-libmmfplayer_la_LIBADD += $(TZPLATFORM_CONFIG_LIBS)
\ No newline at end of file
+endif
\ No newline at end of file
int mm_player_release_video_stream_bo(MMHandleType player, void* bo);
/**
+ * This function is to set mused temp file path.
+ *
+ * @param player [in] handle of player
+ * @param file_path [in] file path
+ * @return This function returns zero on success, or negative value with error code.
+ *
+ * @see
+ * @remark None
+ */
+int mm_player_set_temp_file_path(MMHandleType player, const char *file_path);
+
+/**
@}
*/
/* http streaming */
gchar httpsrc_element[PLAYER_INI_MAX_STRLEN];
- gchar http_file_buffer_path[PLAYER_INI_MAX_STRLEN];
+ gboolean http_use_file_buffer;
+ guint http_ring_buffer_size;
gdouble http_buffering_limit;
guint http_max_size_bytes;
gdouble http_buffering_time;
/* http streaming */
#define DEFAULT_HTTPSRC "souphttpsrc"
-#define DEFAULT_HTTP_FILE_BUFFER_PATH "/home/owner/content"
+#define DEFAULT_HTTP_USE_FILE_BUFFER FALSE
+#define DEFAULT_HTTP_RING_BUFFER_SIZE (20*1024*1024) /* bytes : 20MBytes */
#define DEFAULT_HTTP_BUFFERING_LIMIT 99.0 /* percent */
#define DEFAULT_HTTP_MAX_SIZE_BYTES 1048576 /* bytes : 1 MBytes */
#define DEFAULT_HTTP_BUFFERING_TIME 1.2 /* sec */
\n\
httppsrc element = souphttpsrc \n\
\n\
-; if set, use file or not use memory for buffering\n\
-http file buffer path = /opt/usr/media\n\
+; if yes, use file for buffering.\n\
+; if no, use memory for buffering.\n\
+http use file buffer = no\n\
+\n\
+; ring buffer size when use mem buffer \n\
+http ring buffer size = 20971520 ; 20MBytes \n\
\n\
http buffering limit = 99 ; percent\n\
\n\
/* streaming player */
mm_player_streaming_t *streamer;
+ gchar *http_file_buffer_path;
/* gstreamer pipeline */
MMPlayerGstPipelineInfo *pipeline;
int _mmplayer_get_video_share_master_clock(MMHandleType hplayer, long long *video_time, long long *media_clock, long long *audio_time);
int _mmplayer_get_video_rotate_angle(MMHandleType hplayer, int *angle);
int _mmplayer_enable_sync_handler(MMHandleType hplayer, bool enable);
+int _mmplayer_set_temp_file_path(MMHandleType hplayer, const char* file_path);
int _mmplayer_set_uri(MMHandleType hplayer, const char* uri);
int _mmplayer_set_next_uri(MMHandleType hplayer, const char* uri, bool is_first_path);
int _mmplayer_get_next_uri(MMHandleType hplayer, char** uri);
#define DEFAULT_BUFFERING_TIME 3.0 /* 3sec */
#define DEFAULT_BUFFER_LOW_PERCENT 1.0 /* 1% */
#define DEFAULT_BUFFER_HIGH_PERCENT 99.0 /* 15% */
+#define DEFAULT_RING_BUFFER_SIZE (20*1024*1024) /* 20MBytes */
#define STREAMING_USE_FILE_BUFFER
#define STREAMING_USE_MEMORY_BUFFER
BUFFER_TYPE_MAX,
} BufferType;
+typedef enum {
+ MUXED_BUFFER_TYPE_MEM_QUEUE, /* push mode in queue2 */
+ MUXED_BUFFER_TYPE_MEM_RING_BUFFER, /* pull mode in queue2 */
+ MUXED_BUFFER_TYPE_FILE, /* pull mode in queue2 */
+} muxed_buffer_type_e;
+
typedef struct
{
MMPlayerBufferingMode mode;
guint buffer_avg_bitrate;
gboolean need_update;
gboolean need_sync;
-
+ gint ring_buffer_size;
}mm_player_streaming_t;
gdouble buffering_time,
gdouble low_percent,
gdouble high_percent,
- gboolean use_file,
+ muxed_buffer_type_e type,
gchar* file_path,
guint64 content_size);
void __mm_player_streaming_set_multiqueue( mm_player_streaming_t* streamer,
// MMPLAYER_CMD_UNLOCK( player );
return result;
-}
\ No newline at end of file
+}
+
+int mm_player_set_temp_file_path(MMHandleType player, const char *file_path)
+{
+ int result = MM_ERROR_NONE;
+
+ MMPLAYER_RETURN_VAL_IF_FAIL(player, MM_ERROR_PLAYER_NOT_INITIALIZED);
+
+ MMPLAYER_CMD_LOCK( player );
+
+ result = _mmplayer_set_temp_file_path(player, file_path);
+
+ MMPLAYER_CMD_UNLOCK( player );
+
+ return result;
+}
/* http streaming */
MMPLAYER_INI_GET_STRING( dict, ini->httpsrc_element, "http streaming:httpsrc element", DEFAULT_HTTPSRC );
- MMPLAYER_INI_GET_STRING( dict, ini->http_file_buffer_path, "http streaming:http file buffer path", DEFAULT_HTTP_FILE_BUFFER_PATH );
+ ini->http_use_file_buffer = iniparser_getboolean(dict, "http streaming:http use file buffer", DEFAULT_HTTP_USE_FILE_BUFFER);
+ ini->http_ring_buffer_size = iniparser_getint(dict, "http streaming:http ring buffer size", DEFAULT_HTTP_RING_BUFFER_SIZE);
ini->http_buffering_limit = iniparser_getdouble(dict, "http streaming:http buffering high limit", DEFAULT_HTTP_BUFFERING_LIMIT);
ini->http_max_size_bytes = iniparser_getint(dict, "http streaming:http max size bytes", DEFAULT_HTTP_MAX_SIZE_BYTES);
ini->http_buffering_time = iniparser_getdouble(dict, "http streaming:http buffering time", DEFAULT_HTTP_BUFFERING_TIME);
/* http streaming */
strncpy( ini->httpsrc_element, DEFAULT_HTTPSRC, PLAYER_INI_MAX_STRLEN - 1 );
- strncpy( ini->http_file_buffer_path, DEFAULT_HTTP_FILE_BUFFER_PATH, PLAYER_INI_MAX_STRLEN - 1 );
ini->http_buffering_limit = DEFAULT_HTTP_BUFFERING_LIMIT;
+ ini->http_use_file_buffer = DEFAULT_HTTP_USE_FILE_BUFFER;
+ ini->http_ring_buffer_size = DEFAULT_HTTP_RING_BUFFER_SIZE;
ini->http_max_size_bytes = DEFAULT_HTTP_MAX_SIZE_BYTES;
ini->http_buffering_time = DEFAULT_HTTP_BUFFERING_TIME;
ini->http_timeout = DEFAULT_HTTP_TIMEOUT;
/* http streaming */
LOGD("httpsrc element : %s\n", ini->httpsrc_element);
- LOGD("http file buffer path : %s \n", ini->http_file_buffer_path);
LOGD("http buffering limit : %f \n", ini->http_buffering_limit);
+ LOGD("http use file buffer : %d \n", ini->http_use_file_buffer);
+ LOGD("http ring buffer size : %d \n", ini->http_ring_buffer_size);
LOGD("http max_size bytes : %d \n", ini->http_max_size_bytes);
LOGD("http buffering time : %f \n", ini->http_buffering_time);
LOGD("http timeout : %d \n", ini->http_timeout);
#define GST_QUEUE_DEFAULT_TIME 4
#define GST_QUEUE_HLS_TIME 8
-#define MMPLAYER_USE_FILE_FOR_BUFFERING(player) (((player)->profile.uri_type != MM_PLAYER_URI_TYPE_HLS) && (player->ini.http_file_buffer_path) && (strlen(player->ini.http_file_buffer_path) > 0) )
+#define MMPLAYER_USE_FILE_FOR_BUFFERING(player) \
+ (((player)->profile.uri_type != MM_PLAYER_URI_TYPE_HLS) && \
+ (player->ini.http_use_file_buffer) && \
+ (player->http_file_buffer_path) && \
+ (strlen(player->http_file_buffer_path) > 0) )
#define MM_PLAYER_NAME "mmplayer"
/*---------------------------------------------------------------------------
init_buffering_time,
1.0, // low percent
player->ini.http_buffering_limit, // high percent
- FALSE,
+ MUXED_BUFFER_TYPE_MEM_QUEUE,
NULL,
((dur_bytes>0)?((guint64)dur_bytes):0));
}
pre_buffering_time,
1.0,
player->ini.http_buffering_limit,
- FALSE,
+ MUXED_BUFFER_TYPE_MEM_QUEUE,
NULL,
0);
}
GstPad* qsrcpad= NULL;
gchar *caps_str = NULL;
gint64 dur_bytes = 0L;
- gboolean use_file_buffer = FALSE;
guint max_buffer_size_bytes = 0;
gdouble init_buffering_time = (gdouble)player->streamer->buffering_req.initial_second;
goto ERROR;
}
- // if ( !MMPLAYER_IS_HTTP_LIVE_STREAMING(player))
- {
- if ( !gst_element_query_duration(player->pipeline->mainbin[MMPLAYER_M_SRC].gst, GST_FORMAT_BYTES, &dur_bytes))
- LOGE("fail to get duration.\n");
+ if ( !gst_element_query_duration(player->pipeline->mainbin[MMPLAYER_M_SRC].gst, GST_FORMAT_BYTES, &dur_bytes))
+ LOGE("fail to get duration.\n");
- LOGD("dur_bytes = %lld\n", dur_bytes);
+ LOGD("dur_bytes = %lld\n", dur_bytes);
- if (dur_bytes > 0)
- use_file_buffer = MMPLAYER_USE_FILE_FOR_BUFFERING(player);
- else
- dur_bytes = 0;
+ muxed_buffer_type_e type = MUXED_BUFFER_TYPE_MEM_QUEUE;
+
+ if (dur_bytes > 0) {
+ if (MMPLAYER_USE_FILE_FOR_BUFFERING(player)) {
+ type = MUXED_BUFFER_TYPE_FILE;
+ } else {
+ type = MUXED_BUFFER_TYPE_MEM_RING_BUFFER;
+ player->streamer->ring_buffer_size = player->ini.http_ring_buffer_size;
+ }
+ } else {
+ dur_bytes = 0;
}
/* NOTE : we cannot get any duration info from ts container in case of streaming */
// if(!g_strrstr(GST_ELEMENT_NAME(sinkelement), "mpegtsdemux"))
if(!g_strrstr(player->type, "video/mpegts"))
{
- max_buffer_size_bytes = (use_file_buffer)?(player->ini.http_max_size_bytes):(5*1024*1024);
+ max_buffer_size_bytes = (type == MUXED_BUFFER_TYPE_FILE)?(player->ini.http_max_size_bytes):(5*1024*1024);
LOGD("max_buffer_size_bytes = %d\n", max_buffer_size_bytes);
__mm_player_streaming_set_queue2(player->streamer,
player->ini.http_buffering_time,
1.0, // no meaning
player->ini.http_buffering_limit, // no meaning
- use_file_buffer,
- player->ini.http_file_buffer_path,
+ type,
+ player->http_file_buffer_path,
(guint64)dur_bytes);
}
return;
}
+int _mmplayer_set_temp_file_path(MMHandleType hplayer, const char* file_path)
+{
+ int result = MM_ERROR_NONE;
+ mm_player_t* player = (mm_player_t*) hplayer;
+ MMPLAYER_FENTER();
+
+ MMPLAYER_RETURN_VAL_IF_FAIL (player, MM_ERROR_PLAYER_NOT_INITIALIZED);
+
+ if (file_path) {
+ player->http_file_buffer_path = (gchar*)file_path;
+ LOGD("temp file path: %s\n", player->http_file_buffer_path);
+ }
+ MMPLAYER_FLEAVE();
+ return result;
+}
+
int _mmplayer_set_uri(MMHandleType hplayer, const char* uri)
{
int result = MM_ERROR_NONE;
if (MMPLAYER_IS_HTTP_STREAMING(player))
{
gint64 dur_bytes = 0L;
- gboolean use_file_buffer = FALSE;
+ muxed_buffer_type_e type = MUXED_BUFFER_TYPE_MEM_QUEUE;
if ( !mainbin[MMPLAYER_M_MUXED_S_BUFFER].gst)
{
if ( !gst_element_query_duration(player->pipeline->mainbin[MMPLAYER_M_SRC].gst, GST_FORMAT_BYTES, &dur_bytes))
LOGE("fail to get duration.\n");
- if (dur_bytes > 0)
- use_file_buffer = MMPLAYER_USE_FILE_FOR_BUFFERING(player);
- else
+ if (dur_bytes > 0) {
+ if (MMPLAYER_USE_FILE_FOR_BUFFERING(player)) {
+ type = MUXED_BUFFER_TYPE_FILE;
+ } else {
+ type = MUXED_BUFFER_TYPE_MEM_RING_BUFFER;
+ if (player->streamer)
+ player->streamer->ring_buffer_size = player->ini.http_ring_buffer_size;
+ }
+ } else {
dur_bytes = 0;
+ }
}
/* NOTE : we cannot get any duration info from ts container in case of streaming */
player->ini.http_buffering_time,
1.0,
player->ini.http_buffering_limit,
- use_file_buffer,
- player->ini.http_file_buffer_path,
+ type,
+ player->http_file_buffer_path,
(guint64)dur_bytes);
}
}
#include <sys/vfs.h>
#include <dlog.h>
-#include <tzplatform_config.h>
#include "mm_player_utils.h"
#include "mm_player_streaming.h"
static void streaming_check_buffer_percent(gdouble in_low, gdouble in_high, gdouble *out_low, gdouble *out_high);
static void streaming_set_buffer_percent(mm_player_streaming_t* streamer, BufferType type, gdouble low_percent, gdouble high_percent_byte, gdouble high_percent_time);
-static void streaming_set_queue2_queue_type (mm_player_streaming_t* streamer, gboolean use_file, gchar * file_path, guint64 content_size);
+static void streaming_set_queue2_queue_type (mm_player_streaming_t* streamer, muxed_buffer_type_e type, gchar * file_path, guint64 content_size);
static void streaming_set_buffer_size(mm_player_streaming_t* streamer, BufferType type, guint buffering_bytes, gdouble buffering_time);
static void streaming_update_buffering_status(mm_player_streaming_t* streamer, GstMessage *buffering_msg, gint64 position);
static void streaming_get_current_bitrate_info( mm_player_streaming_t* streamer,
streamer->is_adaptive_streaming = FALSE;
streamer->buffering_percent = -1;
+ streamer->ring_buffer_size = DEFAULT_RING_BUFFER_SIZE;
MMPLAYER_FLEAVE();
return;
}
streamer->is_adaptive_streaming = FALSE;
streamer->buffering_percent = -1;
+ streamer->ring_buffer_size = DEFAULT_RING_BUFFER_SIZE;
MMPLAYER_FLEAVE();
return;
}
static void
-streaming_set_queue2_queue_type (mm_player_streaming_t* streamer, gboolean use_file, gchar * file_path, guint64 content_size)
+streaming_set_queue2_queue_type (mm_player_streaming_t* streamer, muxed_buffer_type_e type, gchar * file_path, guint64 content_size)
{
streaming_buffer_t* buffer_handle = NULL;
guint64 storage_available_size = 0L; //bytes
- guint64 file_buffer_size = 0L; //bytes
+ guint64 buffer_size = 0L; //bytes
gchar file_buffer_name[MM_MAX_URL_LEN] = {0};
struct statfs buf = {0};
gchar* factory_name = NULL;
return;
}
- if ((!use_file) || (!g_strrstr(factory_name, "queue2")))
+ if ((type == MUXED_BUFFER_TYPE_MEM_QUEUE) || (!g_strrstr(factory_name, "queue2")))
{
- LOGD("use memory for buffering. streaming is played on push-based. \n"
+ LOGD("use memory queue for buffering. streaming is played on push-based. \n"
"buffering position would not be updated.\n"
"buffered data would be flushed after played.\n"
"seeking and getting duration could be failed due to file format.");
return;
}
- LOGD("[Queue2] use file for buffering. streaming is played on pull-based. \n");
+ LOGD("[Queue2] buffering type : %d. streaming is played on pull-based. \n", type);
+ if (type == MUXED_BUFFER_TYPE_FILE && file_path && strlen(file_path)>0) {
+ if (statfs((const char *)file_path, &buf) < 0)
+ {
+ LOGW ("[Queue2] fail to get available storage capacity. set mem ring buffer instead of file buffer.\n");
+ buffer_size = (guint64)((streamer->ring_buffer_size>0)?(streamer->ring_buffer_size):DEFAULT_RING_BUFFER_SIZE);
+ }
+ else
+ {
+ storage_available_size = (guint64)buf.f_bavail * (guint64)buf.f_bsize; //bytes
- if (!file_path || strlen(file_path) <= 0)
- file_path = (gchar *)tzplatform_getenv(TZ_SYS_DATA);
+ LOGD ("[Queue2] the number of available blocks : %"G_GUINT64_FORMAT
+ ", the block size is %"G_GUINT64_FORMAT".\n",
+ (guint64)buf.f_bavail, (guint64)buf.f_bsize);
- if (statfs((const char *)file_path, &buf) < 0)
- {
- LOGW ("[Queue2] fail to get availabe storage capacity. just use file buffer.\n");
- file_buffer_size = 0L;
- }
- else
- {
- storage_available_size = (guint64)buf.f_bavail * (guint64)buf.f_bsize; //bytes
+ LOGD ("[Queue2] calculated available storage size is %"
+ G_GUINT64_FORMAT" Bytes.\n", storage_available_size);
- LOGD ("[Queue2] the number of available blocks : %"G_GUINT64_FORMAT
- ", the block size is %"G_GUINT64_FORMAT".\n",
- (guint64)buf.f_bavail, (guint64)buf.f_bsize);
+ if (content_size <= 0 || content_size >= storage_available_size)
+ buffer_size = storage_available_size;
+ else
+ buffer_size = 0L;
- LOGD ("[Queue2] calculated availabe storage size is %"
- G_GUINT64_FORMAT" Bytes.\n", storage_available_size);
+ g_snprintf(file_buffer_name, MM_MAX_URL_LEN, "%sXXXXXX", file_path);
+ SECURE_LOGD("[Queue2] the buffering file name is %s.\n", file_buffer_name);
- if (content_size <= 0 || content_size >= storage_available_size)
- file_buffer_size = storage_available_size;
- else
- file_buffer_size = 0L;
+ g_object_set (G_OBJECT(buffer_handle->buffer), "temp-template", file_buffer_name, NULL);
+ }
+ } else {
+ buffer_size = (guint64)((streamer->ring_buffer_size>0)?(streamer->ring_buffer_size):DEFAULT_RING_BUFFER_SIZE);
}
- if (file_buffer_size>0)
- LOGD("[Queue2] use file ring buffer for buffering.");
-
- g_snprintf(file_buffer_name, MM_MAX_URL_LEN, "%s/XXXXXX", file_path);
- SECURE_LOGD("[Queue2] the buffering file name is %s.\n", file_buffer_name);
-
- g_object_set (G_OBJECT(buffer_handle->buffer), "temp-template", file_buffer_name, NULL);
- g_object_set (G_OBJECT(buffer_handle->buffer), "ring-buffer-max-size", file_buffer_size, NULL);
+ LOGW ("[Queue2] set ring buffer size: %lld\n", buffer_size);
+ g_object_set (G_OBJECT(buffer_handle->buffer), "ring-buffer-max-size", buffer_size, NULL);
MMPLAYER_FLEAVE();
return;
gdouble buffering_time,
gdouble low_percent,
gdouble high_percent,
- gboolean use_file,
+ muxed_buffer_type_e type,
gchar* file_path,
guint64 content_size)
{
streaming_set_buffer_size (streamer, BUFFER_TYPE_MUXED, buffering_bytes, buffering_time);
streaming_set_buffer_percent (streamer, BUFFER_TYPE_MUXED, low_percent, high_percent, 0);
- streaming_set_queue2_queue_type (streamer, use_file, file_path, content_size);
+ streaming_set_queue2_queue_type (streamer, type, file_path, content_size);
MMPLAYER_FLEAVE();
return;