FS-7505: train video a little in beginning and make play file wait for it to train

This commit is contained in:
Anthony Minessale 2015-03-02 18:05:59 -06:00 committed by Michael Jerris
parent d5f67d46db
commit 5b509a72ef
4 changed files with 82 additions and 38 deletions

View File

@ -931,10 +931,6 @@ static switch_status_t vlc_file_av_read(switch_file_handle_t *handle, void *data
switch_mutex_unlock(vcontext->cond_mutex); switch_mutex_unlock(vcontext->cond_mutex);
} }
while(!switch_buffer_inuse(vcontext->audio_buffer) && !vcontext->err && vcontext->playing) {
switch_cond_next();
}
switch_mutex_lock(vcontext->audio_mutex); switch_mutex_lock(vcontext->audio_mutex);
read = switch_buffer_read(vcontext->audio_buffer, data, bytes); read = switch_buffer_read(vcontext->audio_buffer, data, bytes);
switch_mutex_unlock(vcontext->audio_mutex); switch_mutex_unlock(vcontext->audio_mutex);
@ -944,7 +940,7 @@ static switch_status_t vlc_file_av_read(switch_file_handle_t *handle, void *data
if (!read && (status == libvlc_Stopped || status == libvlc_Ended || status == libvlc_Error)) { if (!read && (status == libvlc_Stopped || status == libvlc_Ended || status == libvlc_Error)) {
return SWITCH_STATUS_FALSE; return SWITCH_STATUS_FALSE;
} else if (!read) { } else if (!read) {
read = 2; read = bytes;
memset(data, 0, read); memset(data, 0, read);
} }
@ -1030,6 +1026,11 @@ static switch_status_t vlc_file_read_video(switch_file_handle_t *handle, switch_
} }
if (switch_queue_pop(vcontext->video_queue, &pop) == SWITCH_STATUS_SUCCESS) { if (switch_queue_pop(vcontext->video_queue, &pop) == SWITCH_STATUS_SUCCESS) {
if (!pop) {
vcontext->err = 1;
return SWITCH_STATUS_FALSE;
}
if (!vcontext->vid_ready) { if (!vcontext->vid_ready) {
vcontext->vid_ready = 1; vcontext->vid_ready = 1;
@ -1039,10 +1040,7 @@ static switch_status_t vlc_file_read_video(switch_file_handle_t *handle, switch_
} }
} }
if (!pop) {
vcontext->err = 1;
return SWITCH_STATUS_FALSE;
}
frame->img = (switch_image_t *) pop; frame->img = (switch_image_t *) pop;
return SWITCH_STATUS_SUCCESS; return SWITCH_STATUS_SUCCESS;
} }
@ -1378,6 +1376,9 @@ SWITCH_STANDARD_APP(play_video_function)
libvlc_video_set_format_callbacks(context->mp, video_format_setup_callback, video_format_clean_callback); libvlc_video_set_format_callbacks(context->mp, video_format_setup_callback, video_format_clean_callback);
libvlc_video_set_callbacks(context->mp, vlc_video_lock_callback, vlc_video_unlock_callback, vlc_video_display_callback, context); libvlc_video_set_callbacks(context->mp, vlc_video_lock_callback, vlc_video_unlock_callback, vlc_video_display_callback, context);
switch_channel_set_flag(channel, CF_VIDEO_DECODED_READ);
switch_channel_wait_for_flag(channel, CF_VIDEO_READY, SWITCH_TRUE, 10000, NULL);
// start play // start play
if (-1 == libvlc_media_player_play(context->mp)) { if (-1 == libvlc_media_player_play(context->mp)) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "VLC error playing %s\n", path); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "VLC error playing %s\n", path);

View File

@ -222,7 +222,7 @@ SWITCH_DECLARE(switch_status_t) switch_core_perform_file_open(const char *file,
} }
} }
if (switch_test_flag(fh, SWITCH_FILE_FLAG_VIDEO) && (flags & SWITCH_FILE_FLAG_WRITE)) { if (switch_test_flag(fh, SWITCH_FILE_FLAG_VIDEO)) {
fh->pre_buffer_datalen = 0; fh->pre_buffer_datalen = 0;
} }

View File

@ -72,6 +72,7 @@ struct media_helper {
switch_core_session_t *session; switch_core_session_t *session;
switch_thread_cond_t *cond; switch_thread_cond_t *cond;
switch_mutex_t *cond_mutex; switch_mutex_t *cond_mutex;
switch_mutex_t *file_mutex;
int up; int up;
}; };
@ -4604,6 +4605,8 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_set_video_file(switch_core_ses
return SWITCH_STATUS_FALSE; return SWITCH_STATUS_FALSE;
} }
switch_mutex_lock(v_engine->mh.file_mutex);
if (rw == SWITCH_RW_READ) { if (rw == SWITCH_RW_READ) {
smh->video_read_fh = fh; smh->video_read_fh = fh;
if (fh) { if (fh) {
@ -4616,6 +4619,8 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_set_video_file(switch_core_ses
smh->video_write_fh = fh; smh->video_write_fh = fh;
} }
switch_mutex_unlock(v_engine->mh.file_mutex);
return SWITCH_STATUS_SUCCESS; return SWITCH_STATUS_SUCCESS;
} }
@ -4627,9 +4632,16 @@ static void *SWITCH_THREAD_FUNC video_helper_thread(switch_thread_t *thread, voi
switch_status_t status; switch_status_t status;
switch_frame_t *read_frame; switch_frame_t *read_frame;
switch_media_handle_t *smh; switch_media_handle_t *smh;
uint32_t loops = 0, xloops = 0; uint32_t loops = 0, xloops = 0, vloops = 0;
switch_frame_t fr = { 0 }; switch_frame_t fr = { 0 };
unsigned char *buf = NULL; unsigned char *buf = NULL;
switch_image_t *blank_img = NULL;
switch_rgb_color_t bgcolor;
switch_color_set_rgb(&bgcolor, "#000000");
blank_img = switch_img_alloc(NULL, SWITCH_IMG_FMT_I420, 640, 480, 1);
switch_img_fill(blank_img, 0, 0, blank_img->d_w, blank_img->d_h, &bgcolor);
//switch_rtp_engine_t *v_engine = NULL; //switch_rtp_engine_t *v_engine = NULL;
if (!(smh = session->media_handle)) { if (!(smh = session->media_handle)) {
@ -4713,15 +4725,20 @@ static void *SWITCH_THREAD_FUNC video_helper_thread(switch_thread_t *thread, voi
} }
if (read_frame->img) { if (read_frame->img) {
if (++vloops > 5) {
switch_channel_set_flag(channel, CF_VIDEO_READY); switch_channel_set_flag(channel, CF_VIDEO_READY);
smh->vid_params.width = read_frame->img->d_w; smh->vid_params.width = read_frame->img->d_w;
smh->vid_params.height = read_frame->img->d_h; smh->vid_params.height = read_frame->img->d_h;
} else if (read_frame->datalen > 2 && !switch_channel_test_flag(channel, CF_VIDEO_DECODED_READ)) { } else {
switch_img_free(&blank_img);
blank_img = switch_img_alloc(NULL, SWITCH_IMG_FMT_I420, read_frame->img->d_w, read_frame->img->d_h, 1);
switch_img_fill(blank_img, 0, 0, blank_img->d_w, blank_img->d_h, &bgcolor);
}
} else if (read_frame->datalen > 2 && !switch_channel_test_flag(channel, CF_VIDEO_DECODED_READ) && ++vloops > 20) {
switch_channel_set_flag(channel, CF_VIDEO_READY); switch_channel_set_flag(channel, CF_VIDEO_READY);
} }
} }
if (smh->video_write_fh) {
if (!buf) { if (!buf) {
int buflen = SWITCH_RECOMMENDED_BUFFER_SIZE * 4; int buflen = SWITCH_RECOMMENDED_BUFFER_SIZE * 4;
buf = switch_core_session_alloc(session, buflen); buf = switch_core_session_alloc(session, buflen);
@ -4729,22 +4746,37 @@ static void *SWITCH_THREAD_FUNC video_helper_thread(switch_thread_t *thread, voi
fr.packetlen = buflen; fr.packetlen = buflen;
fr.data = buf + 12; fr.data = buf + 12;
fr.buflen = buflen - 12; fr.buflen = buflen - 12;
switch_core_media_gen_key_frame(session);
} }
if (switch_core_file_read_video(smh->video_write_fh, &fr) == SWITCH_STATUS_SUCCESS) { if (switch_channel_test_flag(channel, CF_VIDEO_READY)) {
switch_mutex_lock(mh->file_mutex);
if (smh->video_write_fh) {
switch_core_media_gen_key_frame(session);
while (smh->video_write_fh &&
switch_channel_ready(session->channel) && switch_core_file_read_video(smh->video_write_fh, &fr) == SWITCH_STATUS_SUCCESS) {
switch_core_session_write_video_frame(session, &fr, SWITCH_IO_FLAG_NONE, 0); switch_core_session_write_video_frame(session, &fr, SWITCH_IO_FLAG_NONE, 0);
switch_img_free(&fr.img); switch_img_free(&fr.img);
switch_mutex_unlock(mh->file_mutex);
switch_mutex_lock(mh->file_mutex);
} }
} else if (smh->video_read_fh && read_frame->img) { } else if (smh->video_read_fh && read_frame->img) {
switch_core_file_write_video(smh->video_read_fh, read_frame); switch_core_file_write_video(smh->video_read_fh, read_frame);
} }
switch_mutex_unlock(mh->file_mutex);
} else if (switch_channel_test_flag(channel, CF_VIDEO_DECODED_READ)) {
fr.img = blank_img;
switch_core_session_write_video_frame(session, &fr, SWITCH_IO_FLAG_NONE, 0);
}
if (read_frame && switch_channel_test_flag(channel, CF_VIDEO_ECHO)) { if (read_frame && (switch_channel_test_flag(channel, CF_VIDEO_ECHO))) {
switch_core_session_write_video_frame(session, read_frame, SWITCH_IO_FLAG_NONE, 0); switch_core_session_write_video_frame(session, read_frame, SWITCH_IO_FLAG_NONE, 0);
} }
} }
switch_img_free(&blank_img);
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "%s Video thread ended\n", switch_channel_get_name(session->channel)); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "%s Video thread ended\n", switch_channel_get_name(session->channel));
switch_mutex_unlock(mh->cond_mutex); switch_mutex_unlock(mh->cond_mutex);
@ -4783,6 +4815,7 @@ SWITCH_DECLARE(switch_status_t) switch_core_session_start_video_thread(switch_co
switch_thread_cond_create(&v_engine->mh.cond, pool); switch_thread_cond_create(&v_engine->mh.cond, pool);
switch_mutex_init(&v_engine->mh.cond_mutex, SWITCH_MUTEX_NESTED, pool); switch_mutex_init(&v_engine->mh.cond_mutex, SWITCH_MUTEX_NESTED, pool);
switch_mutex_init(&v_engine->mh.file_mutex, SWITCH_MUTEX_NESTED, pool);
switch_mutex_init(&v_engine->read_mutex[SWITCH_MEDIA_TYPE_VIDEO], SWITCH_MUTEX_NESTED, pool); switch_mutex_init(&v_engine->read_mutex[SWITCH_MEDIA_TYPE_VIDEO], SWITCH_MUTEX_NESTED, pool);
switch_thread_create(&v_engine->media_thread, thd_attr, video_helper_thread, &v_engine->mh, switch_core_session_get_pool(session)); switch_thread_create(&v_engine->media_thread, thd_attr, video_helper_thread, &v_engine->mh, switch_core_session_get_pool(session));

View File

@ -525,6 +525,8 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_record_file(switch_core_session_t *se
if (switch_channel_test_flag(channel, CF_VIDEO)) { if (switch_channel_test_flag(channel, CF_VIDEO)) {
file_flags |= SWITCH_FILE_FLAG_VIDEO; file_flags |= SWITCH_FILE_FLAG_VIDEO;
switch_channel_set_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_channel_wait_for_flag(channel, CF_VIDEO_READY, SWITCH_TRUE, 10000, NULL);
} }
if (switch_core_file_open(fh, file, fh->channels, read_impl.actual_samples_per_second, file_flags, NULL) != SWITCH_STATUS_SUCCESS) { if (switch_core_file_open(fh, file, fh->channels, read_impl.actual_samples_per_second, file_flags, NULL) != SWITCH_STATUS_SUCCESS) {
@ -606,7 +608,8 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_record_file(switch_core_session_t *se
"Raw Codec Activation Failed %s@%uhz %u channels %dms\n", codec_name, fh->samplerate, "Raw Codec Activation Failed %s@%uhz %u channels %dms\n", codec_name, fh->samplerate,
fh->channels, read_impl.microseconds_per_packet / 1000); fh->channels, read_impl.microseconds_per_packet / 1000);
if (switch_core_file_has_video(fh)) { if (switch_core_file_has_video(fh)) {
switch_channel_set_flag(channel, CF_VIDEO_ECHO); switch_channel_clear_flag(channel, CF_VIDEO_ECHO);
switch_channel_clear_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_core_media_set_video_file(session, NULL, SWITCH_RW_READ); switch_core_media_set_video_file(session, NULL, SWITCH_RW_READ);
} }
switch_core_file_close(fh); switch_core_file_close(fh);
@ -782,7 +785,8 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_record_file(switch_core_session_t *se
} }
if (switch_core_file_has_video(fh)) { if (switch_core_file_has_video(fh)) {
switch_channel_set_flag(channel, CF_VIDEO_ECHO); switch_channel_clear_flag(channel, CF_VIDEO_ECHO);
switch_channel_clear_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_core_media_set_video_file(session, NULL, SWITCH_RW_READ); switch_core_media_set_video_file(session, NULL, SWITCH_RW_READ);
} }
switch_core_file_close(fh); switch_core_file_close(fh);
@ -1259,6 +1263,8 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_play_file(switch_core_session_t *sess
if (switch_channel_test_flag(channel, CF_VIDEO)) { if (switch_channel_test_flag(channel, CF_VIDEO)) {
flags |= SWITCH_FILE_FLAG_VIDEO; flags |= SWITCH_FILE_FLAG_VIDEO;
switch_channel_set_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_channel_wait_for_flag(channel, CF_VIDEO_READY, SWITCH_TRUE, 10000, NULL);
} }
if (switch_core_file_open(fh, if (switch_core_file_open(fh,
@ -1352,6 +1358,7 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_play_file(switch_core_session_t *sess
switch_core_session_io_rwunlock(session); switch_core_session_io_rwunlock(session);
if (switch_core_file_has_video(fh)) { if (switch_core_file_has_video(fh)) {
switch_channel_clear_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE); switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE);
} }
@ -1377,6 +1384,7 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_play_file(switch_core_session_t *sess
switch_core_session_io_rwunlock(session); switch_core_session_io_rwunlock(session);
if (switch_core_file_has_video(fh)) { if (switch_core_file_has_video(fh)) {
switch_channel_clear_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE); switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE);
} }
switch_core_file_close(fh); switch_core_file_close(fh);
@ -1405,6 +1413,7 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_play_file(switch_core_session_t *sess
switch_channel_set_private(channel, "__fh", NULL); switch_channel_set_private(channel, "__fh", NULL);
switch_core_session_io_rwunlock(session); switch_core_session_io_rwunlock(session);
if (switch_core_file_has_video(fh)) { if (switch_core_file_has_video(fh)) {
switch_channel_clear_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE); switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE);
} }
switch_core_file_close(fh); switch_core_file_close(fh);
@ -1815,6 +1824,7 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_play_file(switch_core_session_t *sess
switch_core_session_io_rwunlock(session); switch_core_session_io_rwunlock(session);
if (switch_core_file_has_video(fh)) { if (switch_core_file_has_video(fh)) {
switch_channel_clear_flag_recursive(channel, CF_VIDEO_DECODED_READ);
switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE); switch_core_media_set_video_file(session, NULL, SWITCH_RW_WRITE);
} }
switch_core_file_close(fh); switch_core_file_close(fh);