FS-7656 fix various edge cases with video and non video files mixed into a source, fix a typo bug in file_read_video and fix same bug in mod_vlc, add a new flag to file_read_video to check if the handle is has active video, make mod_conference move the video in and out of a layer when the stream has video or not
This commit is contained in:
parent
434d39d450
commit
385a3b545c
|
@ -916,6 +916,7 @@ SWITCH_DECLARE(switch_status_t) switch_dir_make_recursive(const char *path, swit
|
||||||
SWITCH_DECLARE(switch_status_t) switch_dir_open(switch_dir_t ** new_dir, const char *dirname, switch_memory_pool_t *pool);
|
SWITCH_DECLARE(switch_status_t) switch_dir_open(switch_dir_t ** new_dir, const char *dirname, switch_memory_pool_t *pool);
|
||||||
SWITCH_DECLARE(switch_status_t) switch_dir_close(switch_dir_t *thedir);
|
SWITCH_DECLARE(switch_status_t) switch_dir_close(switch_dir_t *thedir);
|
||||||
SWITCH_DECLARE(const char *) switch_dir_next_file(switch_dir_t *thedir, char *buf, switch_size_t len);
|
SWITCH_DECLARE(const char *) switch_dir_next_file(switch_dir_t *thedir, char *buf, switch_size_t len);
|
||||||
|
SWITCH_DECLARE(uint32_t) switch_dir_count(switch_dir_t *thedir);
|
||||||
|
|
||||||
/** @} */
|
/** @} */
|
||||||
|
|
||||||
|
|
|
@ -2558,7 +2558,8 @@ typedef struct switch_frame_buffer_s switch_frame_buffer_t;
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
SVR_BLOCK = (1 << 0),
|
SVR_BLOCK = (1 << 0),
|
||||||
SVR_FLUSH = (1 << 1)
|
SVR_FLUSH = (1 << 1),
|
||||||
|
SVR_CHECK = (1 << 2)
|
||||||
} switch_video_read_flag_t;
|
} switch_video_read_flag_t;
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
|
|
|
@ -1578,6 +1578,10 @@ static switch_status_t av_file_read(switch_file_handle_t *handle, void *data, si
|
||||||
av_file_context_t *context = (av_file_context_t *)handle->private_info;
|
av_file_context_t *context = (av_file_context_t *)handle->private_info;
|
||||||
int size;
|
int size;
|
||||||
|
|
||||||
|
if ((flags & SVR_CHECK)) {
|
||||||
|
return SWITCH_STATUS_BREAK;
|
||||||
|
}
|
||||||
|
|
||||||
if (!context->has_audio && context->has_video && switch_queue_size(context->eh.video_queue) > 0) {
|
if (!context->has_audio && context->has_video && switch_queue_size(context->eh.video_queue) > 0) {
|
||||||
memset(data, 0, *len * handle->channels * 2);
|
memset(data, 0, *len * handle->channels * 2);
|
||||||
return SWITCH_STATUS_SUCCESS;
|
return SWITCH_STATUS_SUCCESS;
|
||||||
|
|
|
@ -1906,19 +1906,43 @@ static void check_flush(conference_member_t *member)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void patch_fnode(conference_obj_t *conference, conference_file_node_t *fnode, switch_frame_t *write_frame)
|
static void patch_fnode(conference_obj_t *conference, conference_file_node_t *fnode)
|
||||||
{
|
{
|
||||||
if (fnode && fnode->layer_id > -1) {
|
if (fnode && fnode->layer_id > -1) {
|
||||||
mcu_layer_t *layer = &conference->canvas->layers[fnode->layer_id];
|
mcu_layer_t *layer = &conference->canvas->layers[fnode->layer_id];
|
||||||
|
switch_frame_t file_frame = { 0 };
|
||||||
if (switch_core_file_read_video(&fnode->fh, write_frame, SVR_FLUSH) == SWITCH_STATUS_SUCCESS) {
|
switch_status_t status = switch_core_file_read_video(&fnode->fh, &file_frame, SVR_FLUSH);
|
||||||
|
|
||||||
|
if (status == SWITCH_STATUS_SUCCESS) {
|
||||||
switch_img_free(&layer->cur_img);
|
switch_img_free(&layer->cur_img);
|
||||||
layer->cur_img = write_frame->img;
|
layer->cur_img = file_frame.img;
|
||||||
layer->tagged = 1;
|
layer->tagged = 1;
|
||||||
|
} else if (status == SWITCH_STATUS_IGNORE) {
|
||||||
|
if (conference->canvas && fnode->layer_id > -1 ) {
|
||||||
|
canvas_del_fnode_layer(conference, fnode);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void fnode_check_video(conference_obj_t *conference, conference_file_node_t *fnode) {
|
||||||
|
if (switch_core_file_has_video(&fnode->fh) && switch_core_file_read_video(&fnode->fh, NULL, SVR_CHECK) == SWITCH_STATUS_BREAK) {
|
||||||
|
int full_screen = 0;
|
||||||
|
|
||||||
|
if (fnode->fh.params) {
|
||||||
|
full_screen = switch_true(switch_event_get_header(fnode->fh.params, "full-screen"));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (full_screen) {
|
||||||
|
conference->canvas->play_file = 1;
|
||||||
|
conference->playing_video_file = 1;
|
||||||
|
} else {
|
||||||
|
canvas_set_fnode_layer(conference, fnode, -1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static void *SWITCH_THREAD_FUNC conference_video_muxing_thread_run(switch_thread_t *thread, void *obj)
|
static void *SWITCH_THREAD_FUNC conference_video_muxing_thread_run(switch_thread_t *thread, void *obj)
|
||||||
{
|
{
|
||||||
conference_obj_t *conference = (conference_obj_t *) obj;
|
conference_obj_t *conference = (conference_obj_t *) obj;
|
||||||
|
@ -2275,12 +2299,20 @@ static void *SWITCH_THREAD_FUNC conference_video_muxing_thread_run(switch_thread
|
||||||
|
|
||||||
switch_mutex_unlock(conference->member_mutex);
|
switch_mutex_unlock(conference->member_mutex);
|
||||||
|
|
||||||
if (conference->async_fnode && conference->async_fnode->layer_id > -1) {
|
if (conference->async_fnode) {
|
||||||
patch_fnode(conference, conference->async_fnode, &write_frame);
|
if (conference->async_fnode->layer_id > -1) {
|
||||||
}
|
patch_fnode(conference, conference->async_fnode);
|
||||||
|
} else {
|
||||||
|
fnode_check_video(conference, conference->async_fnode);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (conference->fnode && conference->fnode->layer_id > -1) {
|
if (conference->fnode) {
|
||||||
patch_fnode(conference, conference->fnode, &write_frame);
|
if (conference->fnode->layer_id > -1) {
|
||||||
|
patch_fnode(conference, conference->fnode);
|
||||||
|
} else {
|
||||||
|
fnode_check_video(conference, conference->fnode);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!conference->playing_video_file) {
|
if (!conference->playing_video_file) {
|
||||||
|
@ -4989,24 +5021,6 @@ static switch_status_t video_thread_callback(switch_core_session_t *session, swi
|
||||||
return SWITCH_STATUS_SUCCESS;
|
return SWITCH_STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void fnode_check_video(conference_obj_t *conference, conference_file_node_t *fnode) {
|
|
||||||
|
|
||||||
if (switch_core_file_has_video(&fnode->fh)) {
|
|
||||||
int full_screen = 0;
|
|
||||||
|
|
||||||
if (fnode->fh.params) {
|
|
||||||
full_screen = switch_true(switch_event_get_header(fnode->fh.params, "full-screen"));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (full_screen) {
|
|
||||||
conference->canvas->play_file = 1;
|
|
||||||
conference->playing_video_file = 1;
|
|
||||||
} else {
|
|
||||||
canvas_set_fnode_layer(conference, fnode, -1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void conference_command_handler(switch_live_array_t *la, const char *cmd, const char *sessid, cJSON *jla, void *user_data)
|
static void conference_command_handler(switch_live_array_t *la, const char *cmd, const char *sessid, cJSON *jla, void *user_data)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
|
@ -102,25 +102,45 @@ struct local_stream_source {
|
||||||
switch_file_handle_t chime_fh;
|
switch_file_handle_t chime_fh;
|
||||||
switch_queue_t *video_q;
|
switch_queue_t *video_q;
|
||||||
int has_video;
|
int has_video;
|
||||||
|
switch_image_t *blank_img;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef struct local_stream_source local_stream_source_t;
|
typedef struct local_stream_source local_stream_source_t;
|
||||||
|
|
||||||
static int do_rand(void)
|
static int do_rand(uint32_t count)
|
||||||
{
|
{
|
||||||
double r;
|
double r;
|
||||||
int index;
|
int index;
|
||||||
|
|
||||||
|
if (count < 3) return 0;
|
||||||
|
|
||||||
r = ((double) rand() / ((double) (RAND_MAX) + (double) (1)));
|
r = ((double) rand() / ((double) (RAND_MAX) + (double) (1)));
|
||||||
index = (int) (r * 9) + 1;
|
index = (int) (r * count) + 1;
|
||||||
|
|
||||||
return index;
|
return index;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void flush_video_queue(switch_queue_t *q)
|
||||||
|
{
|
||||||
|
void *pop;
|
||||||
|
|
||||||
|
if (switch_queue_size(q) == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (switch_queue_trypop(q, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||||
|
switch_image_t *img = (switch_image_t *) pop;
|
||||||
|
switch_img_free(&img);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void *obj)
|
static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void *obj)
|
||||||
{
|
{
|
||||||
local_stream_source_t *source = obj;
|
local_stream_source_t *source = obj;
|
||||||
switch_file_handle_t fh = { 0 };
|
switch_file_handle_t fh = { 0 };
|
||||||
local_stream_context_t *cp;
|
local_stream_context_t *cp;
|
||||||
char file_buf[128] = "", path_buf[512] = "";
|
char file_buf[128] = "", path_buf[512] = "", last_path[512];
|
||||||
switch_timer_t timer = { 0 };
|
switch_timer_t timer = { 0 };
|
||||||
int fd = -1;
|
int fd = -1;
|
||||||
switch_buffer_t *audio_buffer;
|
switch_buffer_t *audio_buffer;
|
||||||
|
@ -128,6 +148,7 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
switch_size_t used;
|
switch_size_t used;
|
||||||
int skip = 0;
|
int skip = 0;
|
||||||
switch_memory_pool_t *temp_pool = NULL;
|
switch_memory_pool_t *temp_pool = NULL;
|
||||||
|
uint32_t dir_count = 0, do_shuffle = 0;
|
||||||
|
|
||||||
switch_mutex_lock(globals.mutex);
|
switch_mutex_lock(globals.mutex);
|
||||||
THREADS++;
|
THREADS++;
|
||||||
|
@ -137,14 +158,14 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
source->prebuf = DEFAULT_PREBUFFER_SIZE;
|
source->prebuf = DEFAULT_PREBUFFER_SIZE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (source->shuffle) {
|
||||||
|
do_shuffle = 1;
|
||||||
|
}
|
||||||
|
|
||||||
switch_queue_create(&source->video_q, 500, source->pool);
|
switch_queue_create(&source->video_q, 500, source->pool);
|
||||||
switch_buffer_create_dynamic(&audio_buffer, 1024, source->prebuf + 10, 0);
|
switch_buffer_create_dynamic(&audio_buffer, 1024, source->prebuf + 10, 0);
|
||||||
dist_buf = switch_core_alloc(source->pool, source->prebuf + 10);
|
dist_buf = switch_core_alloc(source->pool, source->prebuf + 10);
|
||||||
|
|
||||||
if (source->shuffle) {
|
|
||||||
skip = do_rand();
|
|
||||||
}
|
|
||||||
|
|
||||||
switch_thread_rwlock_create(&source->rwlock, source->pool);
|
switch_thread_rwlock_create(&source->rwlock, source->pool);
|
||||||
|
|
||||||
if (RUNNING) {
|
if (RUNNING) {
|
||||||
|
@ -171,6 +192,21 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (fd > -1) {
|
||||||
|
dir_count = 0;
|
||||||
|
while (switch_fd_read_line(fd, path_buf, sizeof(path_buf))) {
|
||||||
|
dir_count++;
|
||||||
|
}
|
||||||
|
lseek(fd, 0, SEEK_SET);
|
||||||
|
} else {
|
||||||
|
dir_count = switch_dir_count(source->dir_handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (do_shuffle) {
|
||||||
|
skip = do_rand(dir_count);
|
||||||
|
do_shuffle = 0;
|
||||||
|
}
|
||||||
|
|
||||||
switch_yield(1000000);
|
switch_yield(1000000);
|
||||||
|
|
||||||
while (RUNNING && !source->stopped) {
|
while (RUNNING && !source->stopped) {
|
||||||
|
@ -204,11 +240,17 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (dir_count > 1 && !strcmp(last_path, path_buf)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
if (skip > 0) {
|
if (skip > 0) {
|
||||||
skip--;
|
skip--;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
switch_set_string(last_path, path_buf);
|
||||||
|
|
||||||
fname = path_buf;
|
fname = path_buf;
|
||||||
fh.prebuf = source->prebuf;
|
fh.prebuf = source->prebuf;
|
||||||
fh.pre_buffer_datalen = source->prebuf;
|
fh.pre_buffer_datalen = source->prebuf;
|
||||||
|
@ -221,6 +263,7 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (switch_core_timer_init(&timer, source->timer_name, source->interval, (int)source->samples, temp_pool) != SWITCH_STATUS_SUCCESS) {
|
if (switch_core_timer_init(&timer, source->timer_name, source->interval, (int)source->samples, temp_pool) != SWITCH_STATUS_SUCCESS) {
|
||||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CONSOLE, "Can't start timer.\n");
|
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CONSOLE, "Can't start timer.\n");
|
||||||
switch_dir_close(source->dir_handle);
|
switch_dir_close(source->dir_handle);
|
||||||
|
@ -265,6 +308,8 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
|
|
||||||
retry:
|
retry:
|
||||||
|
|
||||||
|
source->has_video = switch_core_file_has_video(use_fh);
|
||||||
|
|
||||||
is_open = switch_test_flag(use_fh, SWITCH_FILE_OPEN);
|
is_open = switch_test_flag(use_fh, SWITCH_FILE_OPEN);
|
||||||
|
|
||||||
if (source->hup) {
|
if (source->hup) {
|
||||||
|
@ -281,8 +326,7 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (is_open) {
|
if (is_open) {
|
||||||
if (switch_core_has_video() && switch_core_file_has_video(use_fh)) {
|
if (switch_core_has_video() && switch_core_file_has_video(use_fh)) {
|
||||||
switch_frame_t vid_frame = { 0 };
|
switch_frame_t vid_frame = { 0 };
|
||||||
|
@ -290,13 +334,21 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
if (switch_core_file_read_video(use_fh, &vid_frame, SVR_FLUSH) == SWITCH_STATUS_SUCCESS) {
|
if (switch_core_file_read_video(use_fh, &vid_frame, SVR_FLUSH) == SWITCH_STATUS_SUCCESS) {
|
||||||
if (vid_frame.img) {
|
if (vid_frame.img) {
|
||||||
source->has_video = 1;
|
source->has_video = 1;
|
||||||
switch_queue_push(source->video_q, vid_frame.img);
|
|
||||||
|
if (source->total) {
|
||||||
|
switch_queue_push(source->video_q, vid_frame.img);
|
||||||
|
} else {
|
||||||
|
flush_video_queue(source->video_q);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
source->has_video = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (switch_core_file_read(use_fh, abuf, &olen) != SWITCH_STATUS_SUCCESS || !olen) {
|
if (switch_core_file_read(use_fh, abuf, &olen) != SWITCH_STATUS_SUCCESS || !olen) {
|
||||||
switch_core_file_close(use_fh);
|
switch_core_file_close(use_fh);
|
||||||
|
|
||||||
if (use_fh == &source->chime_fh) {
|
if (use_fh == &source->chime_fh) {
|
||||||
source->chime_counter = source->rate * source->chime_freq;
|
source->chime_counter = source->rate * source->chime_freq;
|
||||||
}
|
}
|
||||||
|
@ -333,15 +385,7 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
used = switch_buffer_read(audio_buffer, dist_buf, source->samples * 2 * source->channels);
|
used = switch_buffer_read(audio_buffer, dist_buf, source->samples * 2 * source->channels);
|
||||||
|
|
||||||
if (!source->total) {
|
if (!source->total) {
|
||||||
switch_mutex_lock(source->mutex);
|
flush_video_queue(source->video_q);
|
||||||
|
|
||||||
while (switch_queue_trypop(source->video_q, &pop) == SWITCH_STATUS_SUCCESS) {
|
|
||||||
switch_image_t *img = (switch_image_t *) pop;
|
|
||||||
switch_img_free(&img);
|
|
||||||
}
|
|
||||||
|
|
||||||
switch_mutex_unlock(source->mutex);
|
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
uint32_t bused = 0;
|
uint32_t bused = 0;
|
||||||
|
|
||||||
|
@ -371,7 +415,7 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
}
|
}
|
||||||
switch_mutex_unlock(source->mutex);
|
switch_mutex_unlock(source->mutex);
|
||||||
|
|
||||||
switch_mutex_lock(source->mutex);
|
|
||||||
while (switch_queue_trypop(source->video_q, &pop) == SWITCH_STATUS_SUCCESS) {
|
while (switch_queue_trypop(source->video_q, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||||
switch_image_t *img = (switch_image_t *) pop;
|
switch_image_t *img = (switch_image_t *) pop;
|
||||||
switch_image_t *imgcp = NULL;
|
switch_image_t *imgcp = NULL;
|
||||||
|
@ -380,6 +424,7 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
switch_queue_push(source->context_list->video_q, img);
|
switch_queue_push(source->context_list->video_q, img);
|
||||||
} else {
|
} else {
|
||||||
if (source->context_list) {
|
if (source->context_list) {
|
||||||
|
switch_mutex_lock(source->mutex);
|
||||||
for (cp = source->context_list; cp && RUNNING; cp = cp->next) {
|
for (cp = source->context_list; cp && RUNNING; cp = cp->next) {
|
||||||
if (cp->video_q) {
|
if (cp->video_q) {
|
||||||
imgcp = NULL;
|
imgcp = NULL;
|
||||||
|
@ -389,19 +434,18 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
switch_mutex_unlock(source->mutex);
|
||||||
}
|
}
|
||||||
switch_img_free(&img);
|
switch_img_free(&img);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
switch_mutex_unlock(source->mutex);
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
switch_core_timer_destroy(&timer);
|
switch_core_timer_destroy(&timer);
|
||||||
if (RUNNING && source->shuffle) {
|
if (RUNNING && source->shuffle) {
|
||||||
skip = do_rand();
|
skip = do_rand(dir_count);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -484,14 +528,7 @@ static void *SWITCH_THREAD_FUNC read_stream_thread(switch_thread_t *thread, void
|
||||||
|
|
||||||
switch_buffer_destroy(&audio_buffer);
|
switch_buffer_destroy(&audio_buffer);
|
||||||
|
|
||||||
if (source->video_q) {
|
flush_video_queue(source->video_q);
|
||||||
void *pop;
|
|
||||||
|
|
||||||
while (switch_queue_trypop(source->video_q, &pop) == SWITCH_STATUS_SUCCESS) {
|
|
||||||
switch_image_t *img = (switch_image_t *) pop;
|
|
||||||
switch_img_free(&img);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fd > -1) {
|
if (fd > -1) {
|
||||||
close(fd);
|
close(fd);
|
||||||
|
@ -649,7 +686,22 @@ static switch_status_t local_stream_file_read_video(switch_file_handle_t *handle
|
||||||
if (!(context->ready && context->source->ready)) {
|
if (!(context->ready && context->source->ready)) {
|
||||||
return SWITCH_STATUS_FALSE;
|
return SWITCH_STATUS_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!context->source->has_video) {
|
||||||
|
if (frame && context->source->blank_img) {
|
||||||
|
switch_image_t *img = NULL;
|
||||||
|
|
||||||
|
switch_img_copy(context->source->blank_img, &img);
|
||||||
|
frame->img = img;
|
||||||
|
return SWITCH_STATUS_SUCCESS;
|
||||||
|
}
|
||||||
|
return SWITCH_STATUS_IGNORE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((flags & SVR_CHECK)) {
|
||||||
|
return SWITCH_STATUS_BREAK;
|
||||||
|
}
|
||||||
|
|
||||||
while(context->ready && context->source->ready && (flags & SVR_FLUSH) && switch_queue_size(context->video_q) > 1) {
|
while(context->ready && context->source->ready && (flags & SVR_FLUSH) && switch_queue_size(context->video_q) > 1) {
|
||||||
if (switch_queue_trypop(context->video_q, &pop) == SWITCH_STATUS_SUCCESS) {
|
if (switch_queue_trypop(context->video_q, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||||
switch_image_t *img = (switch_image_t *) pop;
|
switch_image_t *img = (switch_image_t *) pop;
|
||||||
|
@ -661,7 +713,7 @@ static switch_status_t local_stream_file_read_video(switch_file_handle_t *handle
|
||||||
return SWITCH_STATUS_FALSE;
|
return SWITCH_STATUS_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((flags && SVR_BLOCK)) {
|
if ((flags & SVR_BLOCK)) {
|
||||||
status = switch_queue_pop(context->video_q, &pop);
|
status = switch_queue_pop(context->video_q, &pop);
|
||||||
} else {
|
} else {
|
||||||
status = switch_queue_trypop(context->video_q, &pop);
|
status = switch_queue_trypop(context->video_q, &pop);
|
||||||
|
@ -673,6 +725,7 @@ static switch_status_t local_stream_file_read_video(switch_file_handle_t *handle
|
||||||
}
|
}
|
||||||
|
|
||||||
frame->img = (switch_image_t *) pop;
|
frame->img = (switch_image_t *) pop;
|
||||||
|
|
||||||
return SWITCH_STATUS_SUCCESS;
|
return SWITCH_STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -694,10 +747,13 @@ static switch_status_t local_stream_file_read(switch_file_handle_t *handle, void
|
||||||
if ((bytes = switch_buffer_read(context->audio_buffer, data, need))) {
|
if ((bytes = switch_buffer_read(context->audio_buffer, data, need))) {
|
||||||
*len = bytes / 2 / handle->real_channels;
|
*len = bytes / 2 / handle->real_channels;
|
||||||
} else {
|
} else {
|
||||||
if (need > 2560) {
|
size_t blank = (handle->samplerate / 20) * 2 * handle->real_channels;
|
||||||
need = 2560;
|
|
||||||
|
if (need > blank) {
|
||||||
|
need = blank;
|
||||||
}
|
}
|
||||||
memset(data, 255, need);
|
|
||||||
|
memset(data, 0, need);
|
||||||
*len = need / 2 / handle->real_channels;
|
*len = need / 2 / handle->real_channels;
|
||||||
}
|
}
|
||||||
switch_mutex_unlock(context->audio_mutex);
|
switch_mutex_unlock(context->audio_mutex);
|
||||||
|
@ -780,6 +836,8 @@ static void launch_thread(const char *name, const char *path, switch_xml_t direc
|
||||||
}
|
}
|
||||||
} else if (!strcasecmp(var, "timer-name")) {
|
} else if (!strcasecmp(var, "timer-name")) {
|
||||||
source->timer_name = switch_core_strdup(source->pool, val);
|
source->timer_name = switch_core_strdup(source->pool, val);
|
||||||
|
} else if (!strcasecmp(var, "blank-img") && !zstr(val)) {
|
||||||
|
source->blank_img = switch_img_read_png(val, SWITCH_IMG_FMT_I420);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1063,6 +1063,10 @@ static switch_status_t vlc_file_read(switch_file_handle_t *handle, void *data, s
|
||||||
size_t bytes = *len * sizeof(int16_t) * handle->channels, read;
|
size_t bytes = *len * sizeof(int16_t) * handle->channels, read;
|
||||||
libvlc_state_t status;
|
libvlc_state_t status;
|
||||||
|
|
||||||
|
if ((flags & SVR_CHECK)) {
|
||||||
|
return SWITCH_STATUS_BREAK;
|
||||||
|
}
|
||||||
|
|
||||||
if (switch_test_flag(handle, SWITCH_FILE_FLAG_VIDEO)) {
|
if (switch_test_flag(handle, SWITCH_FILE_FLAG_VIDEO)) {
|
||||||
return vlc_file_av_read(handle, data, len);
|
return vlc_file_av_read(handle, data, len);
|
||||||
}
|
}
|
||||||
|
@ -1143,7 +1147,7 @@ static switch_status_t vlc_file_read_video(switch_file_handle_t *handle, switch_
|
||||||
return SWITCH_STATUS_FALSE;
|
return SWITCH_STATUS_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((flags && SVR_BLOCK)) {
|
if ((flags & SVR_BLOCK)) {
|
||||||
status = switch_queue_pop(vcontext->video_queue, &pop);
|
status = switch_queue_pop(vcontext->video_queue, &pop);
|
||||||
} else {
|
} else {
|
||||||
status = switch_queue_trypop(vcontext->video_queue, &pop);
|
status = switch_queue_trypop(vcontext->video_queue, &pop);
|
||||||
|
|
|
@ -559,6 +559,34 @@ SWITCH_DECLARE(switch_status_t) switch_dir_close(switch_dir_t *thedir)
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SWITCH_DECLARE(uint32_t) switch_dir_count(switch_dir_t *thedir)
|
||||||
|
{
|
||||||
|
const char *name;
|
||||||
|
apr_int32_t finfo_flags = APR_FINFO_DIRENT | APR_FINFO_TYPE | APR_FINFO_NAME;
|
||||||
|
uint32_t count = 0;
|
||||||
|
|
||||||
|
apr_dir_rewind(thedir->dir_handle);
|
||||||
|
|
||||||
|
while (apr_dir_read(&(thedir->finfo), finfo_flags, thedir->dir_handle) == SWITCH_STATUS_SUCCESS) {
|
||||||
|
|
||||||
|
if (thedir->finfo.filetype != APR_REG && thedir->finfo.filetype != APR_LNK) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(name = thedir->finfo.fname)) {
|
||||||
|
name = thedir->finfo.name;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (name) {
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
apr_dir_rewind(thedir->dir_handle);
|
||||||
|
|
||||||
|
return count;
|
||||||
|
}
|
||||||
|
|
||||||
SWITCH_DECLARE(const char *) switch_dir_next_file(switch_dir_t *thedir, char *buf, switch_size_t len)
|
SWITCH_DECLARE(const char *) switch_dir_next_file(switch_dir_t *thedir, char *buf, switch_size_t len)
|
||||||
{
|
{
|
||||||
const char *fname = NULL;
|
const char *fname = NULL;
|
||||||
|
|
Loading…
Reference in New Issue