FreeRDP/channels/tsmf/client/tsmf_media.c

1553 lines
38 KiB
C
Raw Normal View History

2011-09-19 18:54:09 +04:00
/**
2012-10-09 07:02:04 +04:00
* FreeRDP: A Remote Desktop Protocol Implementation
2011-09-19 18:54:09 +04:00
* Video Redirection Virtual Channel - Media Container
*
* Copyright 2010-2011 Vic Lee
* Copyright 2012 Hewlett-Packard Development Company, L.P.
* Copyright 2015 Thincast Technologies GmbH
* Copyright 2015 DI (FH) Martin Haimberger <martin.haimberger@thincast.com>
2011-09-19 18:54:09 +04:00
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
2011-09-19 18:54:09 +04:00
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <signal.h>
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif
#ifndef _WIN32
2011-09-19 18:54:09 +04:00
#include <sys/time.h>
#endif
#include <winpr/crt.h>
#include <winpr/synch.h>
2015-07-03 14:26:15 +03:00
#include <winpr/string.h>
#include <winpr/thread.h>
#include <winpr/stream.h>
#include <winpr/collections.h>
#include <freerdp/client/tsmf.h>
2011-09-19 18:54:09 +04:00
#include "tsmf_constants.h"
#include "tsmf_types.h"
#include "tsmf_decoder.h"
#include "tsmf_audio.h"
#include "tsmf_main.h"
#include "tsmf_codec.h"
#include "tsmf_media.h"
#define AUDIO_TOLERANCE 10000000LL
/* 1 second = 10,000,000 100ns units*/
2019-11-06 17:24:51 +03:00
#define VIDEO_ADJUST_MAX 10 * 1000 * 1000
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
#define MAX_ACK_TIME 666667
#define AUDIO_MIN_BUFFER_LEVEL 3
#define AUDIO_MAX_BUFFER_LEVEL 6
#define VIDEO_MIN_BUFFER_LEVEL 10
#define VIDEO_MAX_BUFFER_LEVEL 30
2011-09-19 18:54:09 +04:00
struct _TSMF_PRESENTATION
{
BYTE presentation_id[GUID_SIZE];
2011-09-19 18:54:09 +04:00
const char* audio_name;
const char* audio_device;
2011-09-19 18:54:09 +04:00
IWTSVirtualChannelCallback* channel_callback;
2011-09-19 18:54:09 +04:00
2012-10-09 11:26:39 +04:00
UINT64 audio_start_time;
UINT64 audio_end_time;
2011-09-19 18:54:09 +04:00
UINT32 volume;
UINT32 muted;
wArrayList* stream_list;
int x;
int y;
int width;
int height;
int nr_rects;
void* rects;
2011-09-19 18:54:09 +04:00
};
struct _TSMF_STREAM
{
2012-10-09 11:26:39 +04:00
UINT32 stream_id;
2011-09-19 18:54:09 +04:00
2014-11-10 22:02:54 +03:00
TSMF_PRESENTATION* presentation;
2011-09-19 18:54:09 +04:00
ITSMFDecoder* decoder;
2011-09-19 18:54:09 +04:00
int major_type;
int eos;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
UINT32 eos_message_id;
IWTSVirtualChannelCallback* eos_channel_callback;
int delayed_stop;
2012-10-09 11:26:39 +04:00
UINT32 width;
UINT32 height;
2011-09-19 18:54:09 +04:00
ITSMFAudioDevice* audio;
2012-10-09 11:26:39 +04:00
UINT32 sample_rate;
UINT32 channels;
UINT32 bits_per_sample;
2011-09-19 18:54:09 +04:00
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
/* The start time of last played sample */
UINT64 last_start_time;
2011-09-19 18:54:09 +04:00
/* The end_time of last played sample */
2012-10-09 11:26:39 +04:00
UINT64 last_end_time;
2011-09-19 18:54:09 +04:00
/* Next sample should not start before this system time. */
2012-10-09 11:26:39 +04:00
UINT64 next_start_time;
2011-09-19 18:54:09 +04:00
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
UINT32 minBufferLevel;
UINT32 maxBufferLevel;
UINT32 currentBufferLevel;
HANDLE play_thread;
HANDLE ack_thread;
HANDLE stopEvent;
HANDLE ready;
2011-09-19 18:54:09 +04:00
wQueue* sample_list;
wQueue* sample_ack_list;
rdpContext* rdpcontext;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
BOOL seeking;
2011-09-19 18:54:09 +04:00
};
struct _TSMF_SAMPLE
{
2012-10-09 11:26:39 +04:00
UINT32 sample_id;
UINT64 start_time;
UINT64 end_time;
UINT64 duration;
UINT32 extensions;
UINT32 data_size;
BYTE* data;
2012-10-09 11:26:39 +04:00
UINT32 decoded_size;
UINT32 pixfmt;
2011-09-19 18:54:09 +04:00
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
BOOL invalidTimestamps;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
IWTSVirtualChannelCallback* channel_callback;
2012-10-09 11:26:39 +04:00
UINT64 ack_time;
2011-09-19 18:54:09 +04:00
};
static wArrayList* presentation_list = NULL;
static int TERMINATING = 0;
2011-09-19 18:54:09 +04:00
static void _tsmf_presentation_free(void* obj);
static void _tsmf_stream_free(void* obj);
2012-10-09 11:26:39 +04:00
static UINT64 get_current_time(void)
2011-09-19 18:54:09 +04:00
{
struct timeval tp;
gettimeofday(&tp, 0);
2012-10-09 11:26:39 +04:00
return ((UINT64)tp.tv_sec) * 10000000LL + ((UINT64)tp.tv_usec) * 10LL;
2011-09-19 18:54:09 +04:00
}
2014-11-10 22:02:54 +03:00
static TSMF_SAMPLE* tsmf_stream_pop_sample(TSMF_STREAM* stream, int sync)
2011-09-19 18:54:09 +04:00
{
UINT32 index;
UINT32 count;
TSMF_STREAM* s;
2014-11-10 22:02:54 +03:00
TSMF_SAMPLE* sample;
BOOL pending = FALSE;
make cppcheck even more happier: [channels/tsmf/client/gstreamer/tsmf_X11.c:317] -> [channels/tsmf/client/gstreamer/tsmf_X11.c:322]: (warning) Either the condition '!decoder' is redundant or there is possible null pointer dereference: decoder. [channels/tsmf/client/gstreamer/tsmf_X11.c:470] -> [channels/tsmf/client/gstreamer/tsmf_X11.c:475]: (warning) Either the condition '!decoder' is redundant or there is possible null pointer dereference: decoder. [channels/tsmf/client/gstreamer/tsmf_X11.c:472] -> [channels/tsmf/client/gstreamer/tsmf_X11.c:475]: (warning) Either the condition '!decoder' is redundant or there is possible null pointer dereference: decoder. [channels/tsmf/client/tsmf_media.c:179] -> [channels/tsmf/client/tsmf_media.c:181]: (warning) Either the condition '!stream' is redundant or there is possible null pointer dereference: stream. [client/Windows/wf_cliprdr.c:2219] -> [client/Windows/wf_cliprdr.c:2222]: (warning) Either the condition '!formatDataResponse' is redundant or there is possible null pointer dereference: formatDataResponse [client/Windows/wf_cliprdr.c:2445] -> [client/Windows/wf_cliprdr.c:2448]: (warning) Either the condition '!fileContentsResponse' is redundant or there is possible null pointer dereference: fileContentsResponse. [client/X11/xf_cliprdr.c:911] -> [client/X11/xf_cliprdr.c:913]: (warning) Either the condition '!clipboard' is redundant or there is possible null pointer dereference: clipboard. [client/X11/xf_graphics.c:504] -> [client/X11/xf_graphics.c:506]: (warning) Either the condition '!xfc' is redundant or there is possible null pointer dereference: xfc. [libfreerdp/core/transport.c:861] -> [libfreerdp/core/transport.c:863]: (warning) Either the condition '!transport' is redundant or there is possible null pointer dereference: transport. [server/shadow/shadow_server.c:777] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:778] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:779] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:781] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:782] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:783] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:784] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:785] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:787] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:789] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server.
2017-01-26 12:44:19 +03:00
TSMF_PRESENTATION* presentation = NULL;
2014-11-10 22:02:54 +03:00
if (!stream)
return NULL;
make cppcheck even more happier: [channels/tsmf/client/gstreamer/tsmf_X11.c:317] -> [channels/tsmf/client/gstreamer/tsmf_X11.c:322]: (warning) Either the condition '!decoder' is redundant or there is possible null pointer dereference: decoder. [channels/tsmf/client/gstreamer/tsmf_X11.c:470] -> [channels/tsmf/client/gstreamer/tsmf_X11.c:475]: (warning) Either the condition '!decoder' is redundant or there is possible null pointer dereference: decoder. [channels/tsmf/client/gstreamer/tsmf_X11.c:472] -> [channels/tsmf/client/gstreamer/tsmf_X11.c:475]: (warning) Either the condition '!decoder' is redundant or there is possible null pointer dereference: decoder. [channels/tsmf/client/tsmf_media.c:179] -> [channels/tsmf/client/tsmf_media.c:181]: (warning) Either the condition '!stream' is redundant or there is possible null pointer dereference: stream. [client/Windows/wf_cliprdr.c:2219] -> [client/Windows/wf_cliprdr.c:2222]: (warning) Either the condition '!formatDataResponse' is redundant or there is possible null pointer dereference: formatDataResponse [client/Windows/wf_cliprdr.c:2445] -> [client/Windows/wf_cliprdr.c:2448]: (warning) Either the condition '!fileContentsResponse' is redundant or there is possible null pointer dereference: fileContentsResponse. [client/X11/xf_cliprdr.c:911] -> [client/X11/xf_cliprdr.c:913]: (warning) Either the condition '!clipboard' is redundant or there is possible null pointer dereference: clipboard. [client/X11/xf_graphics.c:504] -> [client/X11/xf_graphics.c:506]: (warning) Either the condition '!xfc' is redundant or there is possible null pointer dereference: xfc. [libfreerdp/core/transport.c:861] -> [libfreerdp/core/transport.c:863]: (warning) Either the condition '!transport' is redundant or there is possible null pointer dereference: transport. [server/shadow/shadow_server.c:777] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:778] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:779] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:781] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:782] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:783] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:784] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:785] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:787] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server. [server/shadow/shadow_server.c:789] -> [server/shadow/shadow_server.c:791]: (warning) Either the condition '!server' is redundant or there is possible null pointer dereference: server.
2017-01-26 12:44:19 +03:00
presentation = stream->presentation;
if (Queue_Count(stream->sample_list) < 1)
2011-09-19 18:54:09 +04:00
return NULL;
if (sync)
2011-09-19 18:54:09 +04:00
{
if (stream->decoder)
2011-09-19 18:54:09 +04:00
{
if (stream->decoder->GetDecodedData)
2011-09-19 18:54:09 +04:00
{
if (stream->major_type == TSMF_MAJOR_TYPE_AUDIO)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
/* Check if some other stream has earlier sample that needs to be played first
*/
/* Start time is more reliable than end time as some stream types seem to have
* incorrect end times from the server
*/
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->last_start_time > AUDIO_TOLERANCE)
2011-09-19 18:54:09 +04:00
{
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
{
2019-11-06 17:24:51 +03:00
s = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
2019-11-06 17:24:51 +03:00
/* Start time is more reliable than end time as some stream types seem
* to have incorrect end times from the server
*/
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (s != stream && !s->eos && s->last_start_time &&
s->last_start_time < stream->last_start_time - AUDIO_TOLERANCE)
{
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
DEBUG_TSMF("Pending due to audio tolerance");
pending = TRUE;
break;
}
}
ArrayList_Unlock(presentation->stream_list);
2011-09-19 18:54:09 +04:00
}
}
else
{
2019-11-06 17:24:51 +03:00
/* Start time is more reliable than end time as some stream types seem to have
* incorrect end times from the server
*/
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->last_start_time > presentation->audio_start_time)
{
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
DEBUG_TSMF("Pending due to stream start time > audio start time");
pending = TRUE;
}
}
2011-09-19 18:54:09 +04:00
}
}
}
if (pending)
2011-09-19 18:54:09 +04:00
return NULL;
2019-11-06 17:24:51 +03:00
sample = (TSMF_SAMPLE*)Queue_Dequeue(stream->sample_list);
2019-11-06 17:24:51 +03:00
/* Only update stream last end time if the sample end time is valid and greater than the current
* stream end time */
if (sample && (sample->end_time > stream->last_end_time) && (!sample->invalidTimestamps))
2011-09-19 18:54:09 +04:00
stream->last_end_time = sample->end_time;
2019-11-06 17:24:51 +03:00
/* Only update stream last start time if the sample start time is valid and greater than the
* current stream start time */
if (sample && (sample->start_time > stream->last_start_time) && (!sample->invalidTimestamps))
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->last_start_time = sample->start_time;
2011-09-19 18:54:09 +04:00
return sample;
}
static void tsmf_sample_free(void* arg)
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
TSMF_SAMPLE* sample = arg;
if (!sample)
return;
2015-05-11 10:07:39 +03:00
free(sample->data);
free(sample);
2011-09-19 18:54:09 +04:00
}
static BOOL tsmf_sample_ack(TSMF_SAMPLE* sample)
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
if (!sample)
return FALSE;
2014-11-10 22:02:54 +03:00
2019-11-06 17:24:51 +03:00
return tsmf_playback_ack(sample->channel_callback, sample->sample_id, sample->duration,
sample->data_size);
2011-09-19 18:54:09 +04:00
}
static BOOL tsmf_sample_queue_ack(TSMF_SAMPLE* sample)
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
if (!sample)
return FALSE;
2014-11-10 22:02:54 +03:00
if (!sample->stream)
return FALSE;
2014-11-10 22:02:54 +03:00
return Queue_Enqueue(sample->stream->sample_ack_list, sample);
2011-09-19 18:54:09 +04:00
}
/* Returns TRUE if no more samples are currently available
* Returns FALSE otherwise
*/
2014-11-10 22:02:54 +03:00
static BOOL tsmf_stream_process_ack(void* arg, BOOL force)
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream = arg;
TSMF_SAMPLE* sample;
2012-10-09 11:26:39 +04:00
UINT64 ack_time;
BOOL rc = FALSE;
2014-11-10 22:02:54 +03:00
if (!stream)
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
return TRUE;
2014-11-10 22:02:54 +03:00
Queue_Lock(stream->sample_ack_list);
2019-11-06 17:24:51 +03:00
sample = (TSMF_SAMPLE*)Queue_Peek(stream->sample_ack_list);
if (!sample)
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
{
rc = TRUE;
goto finally;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
}
if (!force)
{
/* Do some min/max ack limiting if we have access to Buffer level information */
2016-10-19 12:10:35 +03:00
if (stream->decoder && stream->decoder->BufferLevel)
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
{
/* Try to keep buffer level below max by withholding acks */
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->currentBufferLevel > stream->maxBufferLevel)
goto finally;
/* Try to keep buffer level above min by pushing acks through quickly */
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
else if (stream->currentBufferLevel < stream->minBufferLevel)
goto dequeue;
}
/* Time based acks only */
ack_time = get_current_time();
if (sample->ack_time > ack_time)
goto finally;
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
dequeue:
sample = Queue_Dequeue(stream->sample_ack_list);
if (sample)
{
tsmf_sample_ack(sample);
tsmf_sample_free(sample);
}
2014-11-10 22:02:54 +03:00
finally:
Queue_Unlock(stream->sample_ack_list);
return rc;
}
TSMF_PRESENTATION* tsmf_presentation_new(const BYTE* guid,
2019-11-06 17:24:51 +03:00
IWTSVirtualChannelCallback* pChannelCallback)
{
2014-11-10 22:02:54 +03:00
TSMF_PRESENTATION* presentation;
if (!guid || !pChannelCallback)
return NULL;
2019-11-06 17:24:51 +03:00
presentation = (TSMF_PRESENTATION*)calloc(1, sizeof(TSMF_PRESENTATION));
if (!presentation)
{
WLog_ERR(TAG, "calloc failed");
return NULL;
}
CopyMemory(presentation->presentation_id, guid, GUID_SIZE);
2011-09-19 18:54:09 +04:00
presentation->channel_callback = pChannelCallback;
presentation->volume = 5000; /* 50% */
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
presentation->muted = 0;
if (!(presentation->stream_list = ArrayList_New(TRUE)))
goto error_stream_list;
2019-11-06 17:24:51 +03:00
ArrayList_Object(presentation->stream_list)->fnObjectFree = _tsmf_stream_free;
2014-11-10 22:02:54 +03:00
if (ArrayList_Add(presentation_list, presentation) < 0)
goto error_add;
2014-11-10 22:02:54 +03:00
2011-09-19 18:54:09 +04:00
return presentation;
error_add:
ArrayList_Free(presentation->stream_list);
error_stream_list:
free(presentation);
return NULL;
2011-09-19 18:54:09 +04:00
}
2014-11-10 22:02:54 +03:00
static char* guid_to_string(const BYTE* guid, char* str, size_t len)
2011-09-19 18:54:09 +04:00
{
2019-02-07 16:32:55 +03:00
size_t i;
2014-11-10 22:02:54 +03:00
if (!guid || !str)
return NULL;
2019-02-07 16:32:55 +03:00
for (i = 0; i < GUID_SIZE && (len > 2 * i); i++)
2019-11-06 17:24:51 +03:00
sprintf_s(str + (2 * i), len - 2 * i, "%02" PRIX8 "", guid[i]);
return str;
}
TSMF_PRESENTATION* tsmf_presentation_find_by_id(const BYTE* guid)
{
UINT32 index;
UINT32 count;
BOOL found = FALSE;
2014-11-10 22:02:54 +03:00
char guid_str[GUID_SIZE * 2 + 1];
TSMF_PRESENTATION* presentation;
ArrayList_Lock(presentation_list);
count = ArrayList_Count(presentation_list);
for (index = 0; index < count; index++)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
presentation = (TSMF_PRESENTATION*)ArrayList_GetItem(presentation_list, index);
if (memcmp(presentation->presentation_id, guid, GUID_SIZE) == 0)
{
found = TRUE;
break;
}
2011-09-19 18:54:09 +04:00
}
ArrayList_Unlock(presentation_list);
if (!found)
2019-11-06 17:24:51 +03:00
WLog_WARN(TAG, "presentation id %s not found",
guid_to_string(guid, guid_str, sizeof(guid_str)));
return (found) ? presentation : NULL;
2011-09-19 18:54:09 +04:00
}
static BOOL tsmf_sample_playback_video(TSMF_SAMPLE* sample)
2011-09-19 18:54:09 +04:00
{
2012-10-09 11:26:39 +04:00
UINT64 t;
TSMF_VIDEO_FRAME_EVENT event;
TSMF_STREAM* stream = sample->stream;
TSMF_PRESENTATION* presentation = stream->presentation;
2019-11-06 17:24:51 +03:00
TSMF_CHANNEL_CALLBACK* callback = (TSMF_CHANNEL_CALLBACK*)sample->channel_callback;
TsmfClientContext* tsmf = (TsmfClientContext*)callback->plugin->pInterface;
DEBUG_TSMF("MessageId %" PRIu32 " EndTime %" PRIu64 " data_size %" PRIu32 " consumed.",
sample->sample_id, sample->end_time, sample->data_size);
if (sample->data)
2011-09-19 18:54:09 +04:00
{
t = get_current_time();
/* Start time is more reliable than end time as some stream types seem to have incorrect
* end times from the server
*/
if (stream->next_start_time > t &&
((sample->start_time >= presentation->audio_start_time) ||
2019-11-06 17:24:51 +03:00
((sample->start_time < stream->last_start_time) && (!sample->invalidTimestamps))))
2011-09-19 18:54:09 +04:00
{
USleep((stream->next_start_time - t) / 10);
2011-09-19 18:54:09 +04:00
}
2011-09-19 18:54:09 +04:00
stream->next_start_time = t + sample->duration - 50000;
ZeroMemory(&event, sizeof(TSMF_VIDEO_FRAME_EVENT));
event.frameData = sample->data;
event.frameSize = sample->decoded_size;
event.framePixFmt = sample->pixfmt;
event.frameWidth = sample->stream->width;
event.frameHeight = sample->stream->height;
event.x = presentation->x;
event.y = presentation->y;
event.width = presentation->width;
event.height = presentation->height;
if (presentation->nr_rects > 0)
{
event.numVisibleRects = presentation->nr_rects;
2019-11-06 17:24:51 +03:00
event.visibleRects = (RECTANGLE_16*)calloc(event.numVisibleRects, sizeof(RECTANGLE_16));
if (!event.visibleRects)
2015-04-15 14:08:51 +03:00
{
WLog_ERR(TAG, "can't allocate memory for copy rectangles");
2017-01-18 14:39:40 +03:00
return FALSE;
2015-04-15 14:08:51 +03:00
}
2019-11-06 17:24:51 +03:00
memcpy(event.visibleRects, presentation->rects,
presentation->nr_rects * sizeof(RDP_RECT));
2015-05-14 16:57:37 +03:00
presentation->nr_rects = 0;
}
2011-09-19 18:54:09 +04:00
#if 0
/* Dump a .ppm image for every 30 frames. Assuming the frame is in YUV format, we
extract the Y values to create a grayscale image. */
static int frame_id = 0;
char buf[100];
FILE* fp;
if ((frame_id % 30) == 0)
2011-09-19 18:54:09 +04:00
{
2015-07-03 14:26:15 +03:00
sprintf_s(buf, sizeof(buf), "/tmp/FreeRDP_Frame_%d.ppm", frame_id);
2011-09-19 18:54:09 +04:00
fp = fopen(buf, "wb");
fwrite("P5\n", 1, 3, fp);
sprintf_s(buf, sizeof(buf), "%"PRIu32" %"PRIu32"\n", sample->stream->width,
sample->stream->height);
fwrite(buf, 1, strnlen(buf, sizeof(buf)), fp);
2011-09-19 18:54:09 +04:00
fwrite("255\n", 1, 4, fp);
fwrite(sample->data, 1, sample->stream->width * sample->stream->height, fp);
fflush(fp);
fclose(fp);
}
2011-09-19 18:54:09 +04:00
frame_id++;
#endif
2019-11-06 17:24:51 +03:00
/* The frame data ownership is passed to the event object, and is freed after the event is
* processed. */
2015-03-26 13:38:09 +03:00
sample->data = NULL;
sample->decoded_size = 0;
if (tsmf->FrameEvent)
tsmf->FrameEvent(tsmf, &event);
free(event.frameData);
if (event.visibleRects != NULL)
2015-05-14 16:57:37 +03:00
free(event.visibleRects);
2011-09-19 18:54:09 +04:00
}
return TRUE;
2011-09-19 18:54:09 +04:00
}
static BOOL tsmf_sample_playback_audio(TSMF_SAMPLE* sample)
2011-09-19 18:54:09 +04:00
{
2012-10-09 11:26:39 +04:00
UINT64 latency = 0;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream = sample->stream;
BOOL ret;
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("MessageId %" PRIu32 " EndTime %" PRIu64 " consumed.", sample->sample_id,
sample->end_time);
if (stream->audio && sample->data)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
ret =
sample->stream->audio->Play(sample->stream->audio, sample->data, sample->decoded_size);
free(sample->data);
2011-09-19 18:54:09 +04:00
sample->data = NULL;
sample->decoded_size = 0;
if (stream->audio->GetLatency)
2011-09-19 18:54:09 +04:00
latency = stream->audio->GetLatency(stream->audio);
}
else
{
ret = TRUE;
2011-09-19 18:54:09 +04:00
latency = 0;
}
2011-09-19 18:54:09 +04:00
sample->ack_time = latency + get_current_time();
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
/* Only update stream times if the sample timestamps are valid */
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (!sample->invalidTimestamps)
{
stream->last_start_time = sample->start_time + latency;
stream->last_end_time = sample->end_time + latency;
stream->presentation->audio_start_time = sample->start_time + latency;
stream->presentation->audio_end_time = sample->end_time + latency;
}
return ret;
2011-09-19 18:54:09 +04:00
}
static BOOL tsmf_sample_playback(TSMF_SAMPLE* sample)
2011-09-19 18:54:09 +04:00
{
BOOL ret = FALSE;
2012-10-09 11:26:39 +04:00
UINT32 width;
UINT32 height;
UINT32 pixfmt = 0;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream = sample->stream;
if (stream->decoder)
{
if (stream->decoder->DecodeEx)
2014-11-10 22:02:54 +03:00
{
2019-11-06 17:24:51 +03:00
/* Try to "sync" video buffers to audio buffers by looking at the running time for each
* stream The difference between the two running times causes an offset between audio
* and video actual render times. So, we try to adjust timestamps on the video buffer to
* match those on the audio buffer.
*/
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->major_type == TSMF_MAJOR_TYPE_VIDEO)
{
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
TSMF_STREAM* temp_stream = NULL;
TSMF_PRESENTATION* presentation = stream->presentation;
ArrayList_Lock(presentation->stream_list);
int count = ArrayList_Count(presentation->stream_list);
int index = 0;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
for (index = 0; index < count; index++)
{
2016-02-03 13:30:15 +03:00
UINT64 time_diff;
2019-11-06 17:24:51 +03:00
temp_stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
2016-02-03 13:30:15 +03:00
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (temp_stream->major_type == TSMF_MAJOR_TYPE_AUDIO)
{
2019-11-06 17:24:51 +03:00
UINT64 video_time =
(UINT64)stream->decoder->GetRunningTime(stream->decoder);
UINT64 audio_time =
(UINT64)temp_stream->decoder->GetRunningTime(temp_stream->decoder);
UINT64 max_adjust = VIDEO_ADJUST_MAX;
if (video_time < audio_time)
max_adjust = -VIDEO_ADJUST_MAX;
2016-02-03 13:30:15 +03:00
if (video_time > audio_time)
time_diff = video_time - audio_time;
else
time_diff = audio_time - video_time;
time_diff = time_diff < VIDEO_ADJUST_MAX ? time_diff : max_adjust;
sample->start_time += time_diff;
sample->end_time += time_diff;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
break;
}
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
ArrayList_Unlock(presentation->stream_list);
}
2019-11-06 17:24:51 +03:00
ret = stream->decoder->DecodeEx(stream->decoder, sample->data, sample->data_size,
sample->extensions, sample->start_time,
sample->end_time, sample->duration);
2014-11-10 22:02:54 +03:00
}
else
2014-11-10 22:02:54 +03:00
{
ret = stream->decoder->Decode(stream->decoder, sample->data, sample->data_size,
sample->extensions);
2014-11-10 22:02:54 +03:00
}
}
if (!ret)
2011-09-19 18:54:09 +04:00
{
WLog_ERR(TAG, "decode error, queue ack anyways");
if (!tsmf_sample_queue_ack(sample))
{
WLog_ERR(TAG, "error queuing sample for ack");
return FALSE;
}
return TRUE;
2011-09-19 18:54:09 +04:00
}
free(sample->data);
2011-09-19 18:54:09 +04:00
sample->data = NULL;
if (stream->major_type == TSMF_MAJOR_TYPE_VIDEO)
2011-09-19 18:54:09 +04:00
{
if (stream->decoder->GetDecodedFormat)
2011-09-19 18:54:09 +04:00
{
pixfmt = stream->decoder->GetDecodedFormat(stream->decoder);
2019-11-06 17:24:51 +03:00
if (pixfmt == ((UINT32)-1))
2011-09-19 18:54:09 +04:00
{
WLog_ERR(TAG, "unable to decode video format");
if (!tsmf_sample_queue_ack(sample))
{
WLog_ERR(TAG, "error queuing sample for ack");
}
return FALSE;
2011-09-19 18:54:09 +04:00
}
2011-09-19 18:54:09 +04:00
sample->pixfmt = pixfmt;
}
if (stream->decoder->GetDecodedDimension)
2011-09-19 18:54:09 +04:00
{
ret = stream->decoder->GetDecodedDimension(stream->decoder, &width, &height);
if (ret && (width != stream->width || height != stream->height))
{
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("video dimension changed to %" PRIu32 " x %" PRIu32 "", width, height);
stream->width = width;
stream->height = height;
}
2011-09-19 18:54:09 +04:00
}
}
if (stream->decoder->GetDecodedData)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
sample->data = stream->decoder->GetDecodedData(stream->decoder, &sample->decoded_size);
switch (sample->stream->major_type)
{
case TSMF_MAJOR_TYPE_VIDEO:
2019-11-06 17:24:51 +03:00
ret = tsmf_sample_playback_video(sample) && tsmf_sample_queue_ack(sample);
break;
case TSMF_MAJOR_TYPE_AUDIO:
2019-11-06 17:24:51 +03:00
ret = tsmf_sample_playback_audio(sample) && tsmf_sample_queue_ack(sample);
break;
}
2011-09-19 18:54:09 +04:00
}
else
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream = sample->stream;
2012-10-09 11:26:39 +04:00
UINT64 ack_anticipation_time = get_current_time();
BOOL buffer_filled = TRUE;
/* Classify the buffer as filled once it reaches minimum level */
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->decoder->BufferLevel)
{
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->currentBufferLevel < stream->minBufferLevel)
buffer_filled = FALSE;
}
2019-11-06 17:24:51 +03:00
ack_anticipation_time +=
(sample->duration / 2 < MAX_ACK_TIME) ? sample->duration / 2 : MAX_ACK_TIME;
switch (sample->stream->major_type)
{
case TSMF_MAJOR_TYPE_VIDEO:
2019-11-06 17:24:51 +03:00
{
break;
}
case TSMF_MAJOR_TYPE_AUDIO:
2019-11-06 17:24:51 +03:00
{
break;
}
}
sample->ack_time = ack_anticipation_time;
if (!tsmf_sample_queue_ack(sample))
{
WLog_ERR(TAG, "error queuing sample for ack");
ret = FALSE;
}
}
return ret;
2011-09-19 18:54:09 +04:00
}
static DWORD WINAPI tsmf_stream_ack_func(LPVOID arg)
2011-09-19 18:54:09 +04:00
{
HANDLE hdl[2];
2019-11-06 17:24:51 +03:00
TSMF_STREAM* stream = (TSMF_STREAM*)arg;
UINT error = CHANNEL_RC_OK;
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("in %" PRIu32 "", stream->stream_id);
hdl[0] = stream->stopEvent;
hdl[1] = Queue_Event(stream->sample_ack_list);
while (1)
{
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
DWORD ev = WaitForMultipleObjects(2, hdl, FALSE, 1000);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (ev == WAIT_FAILED)
{
error = GetLastError();
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForMultipleObjects failed with error %" PRIu32 "!", error);
break;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->decoder)
if (stream->decoder->BufferLevel)
stream->currentBufferLevel = stream->decoder->BufferLevel(stream->decoder);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->eos)
{
2019-11-06 17:24:51 +03:00
while ((stream->currentBufferLevel > 0) && !(tsmf_stream_process_ack(stream, TRUE)))
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
{
DEBUG_TSMF("END OF STREAM PROCESSING!");
2016-10-19 12:10:35 +03:00
if (stream->decoder && stream->decoder->BufferLevel)
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->currentBufferLevel = stream->decoder->BufferLevel(stream->decoder);
else
stream->currentBufferLevel = 1;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
USleep(1000);
}
tsmf_send_eos_response(stream->eos_channel_callback, stream->eos_message_id);
stream->eos = 0;
if (stream->delayed_stop)
{
DEBUG_TSMF("Finishing delayed stream stop, now that eos has processed.");
tsmf_stream_flush(stream);
2016-10-19 12:10:35 +03:00
if (stream->decoder && stream->decoder->Control)
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->decoder->Control(stream->decoder, Control_Stop, NULL);
}
}
/* Stream stopped force all of the acks to happen */
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (ev == WAIT_OBJECT_0)
{
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
DEBUG_TSMF("ack: Stream stopped!");
while (1)
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
{
if (tsmf_stream_process_ack(stream, TRUE))
break;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
USleep(1000);
}
break;
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (tsmf_stream_process_ack(stream, FALSE))
continue;
if (stream->currentBufferLevel > stream->minBufferLevel)
USleep(1000);
}
if (error && stream->rdpcontext)
2019-11-06 17:24:51 +03:00
setChannelError(stream->rdpcontext, error, "tsmf_stream_ack_func reported an error");
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("out %" PRIu32 "", stream->stream_id);
ExitThread(error);
return error;
}
2011-09-19 18:54:09 +04:00
static DWORD WINAPI tsmf_stream_playback_func(LPVOID arg)
{
2014-05-24 17:55:55 +04:00
HANDLE hdl[2];
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
TSMF_SAMPLE* sample = NULL;
2019-11-06 17:24:51 +03:00
TSMF_STREAM* stream = (TSMF_STREAM*)arg;
2014-11-10 22:02:54 +03:00
TSMF_PRESENTATION* presentation = stream->presentation;
UINT error = CHANNEL_RC_OK;
DWORD status;
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("in %" PRIu32 "", stream->stream_id);
2019-11-06 17:24:51 +03:00
if (stream->major_type == TSMF_MAJOR_TYPE_AUDIO && stream->sample_rate && stream->channels &&
stream->bits_per_sample)
2011-09-19 18:54:09 +04:00
{
if (stream->decoder)
2011-09-19 18:54:09 +04:00
{
if (stream->decoder->GetDecodedData)
{
stream->audio = tsmf_load_audio_device(
2019-11-06 17:24:51 +03:00
presentation->audio_name && presentation->audio_name[0]
? presentation->audio_name
: NULL,
presentation->audio_device && presentation->audio_device[0]
? presentation->audio_device
: NULL);
if (stream->audio)
{
stream->audio->SetFormat(stream->audio, stream->sample_rate, stream->channels,
stream->bits_per_sample);
}
}
2011-09-19 18:54:09 +04:00
}
}
2014-05-24 17:55:55 +04:00
hdl[0] = stream->stopEvent;
hdl[1] = Queue_Event(stream->sample_list);
while (1)
2011-09-19 18:54:09 +04:00
{
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
status = WaitForMultipleObjects(2, hdl, FALSE, 1000);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (status == WAIT_FAILED)
{
error = GetLastError();
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForMultipleObjects failed with error %" PRIu32 "!", error);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
break;
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
status = WaitForSingleObject(stream->stopEvent, 0);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (status == WAIT_FAILED)
{
error = GetLastError();
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForSingleObject failed with error %" PRIu32 "!", error);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
break;
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (status == WAIT_OBJECT_0)
break;
if (stream->decoder)
if (stream->decoder->BufferLevel)
stream->currentBufferLevel = stream->decoder->BufferLevel(stream->decoder);
sample = tsmf_stream_pop_sample(stream, 0);
if (sample && !tsmf_sample_playback(sample))
{
WLog_ERR(TAG, "error playing sample");
error = ERROR_INTERNAL_ERROR;
break;
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->currentBufferLevel > stream->minBufferLevel)
USleep(1000);
2011-09-19 18:54:09 +04:00
}
if (stream->audio)
2011-09-19 18:54:09 +04:00
{
stream->audio->Free(stream->audio);
stream->audio = NULL;
}
if (error && stream->rdpcontext)
2019-11-06 17:24:51 +03:00
setChannelError(stream->rdpcontext, error, "tsmf_stream_playback_func reported an error");
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("out %" PRIu32 "", stream->stream_id);
ExitThread(error);
return error;
2011-09-19 18:54:09 +04:00
}
static BOOL tsmf_stream_start(TSMF_STREAM* stream)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
if (!stream || !stream->presentation || !stream->decoder || !stream->decoder->Control)
return TRUE;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->eos = 0;
return stream->decoder->Control(stream->decoder, Control_Restart, NULL);
2011-09-19 18:54:09 +04:00
}
static BOOL tsmf_stream_stop(TSMF_STREAM* stream)
2011-09-19 18:54:09 +04:00
{
if (!stream || !stream->decoder || !stream->decoder->Control)
return TRUE;
/* If stopping after eos - we delay until the eos has been processed
* this allows us to process any buffers that have been acked even though
* they have not actually been completely processes by the decoder
*/
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if (stream->eos)
{
DEBUG_TSMF("Setting up a delayed stop for once the eos has been processed.");
stream->delayed_stop = 1;
return TRUE;
}
/* Otherwise force stop immediately */
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
else
{
DEBUG_TSMF("Stop with no pending eos response, so do it immediately.");
tsmf_stream_flush(stream);
return stream->decoder->Control(stream->decoder, Control_Stop, NULL);
}
}
static BOOL tsmf_stream_pause(TSMF_STREAM* stream)
{
if (!stream || !stream->decoder || !stream->decoder->Control)
return TRUE;
return stream->decoder->Control(stream->decoder, Control_Pause, NULL);
}
static BOOL tsmf_stream_restart(TSMF_STREAM* stream)
{
if (!stream || !stream->decoder || !stream->decoder->Control)
return TRUE;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->eos = 0;
return stream->decoder->Control(stream->decoder, Control_Restart, NULL);
}
2019-11-06 17:24:51 +03:00
static BOOL tsmf_stream_change_volume(TSMF_STREAM* stream, UINT32 newVolume, UINT32 muted)
{
if (!stream || !stream->decoder)
return TRUE;
if (stream->decoder != NULL && stream->decoder->ChangeVolume)
{
return stream->decoder->ChangeVolume(stream->decoder, newVolume, muted);
}
else if (stream->audio != NULL && stream->audio->ChangeVolume)
{
return stream->audio->ChangeVolume(stream->audio, newVolume, muted);
}
return TRUE;
}
2019-11-06 17:24:51 +03:00
BOOL tsmf_presentation_volume_changed(TSMF_PRESENTATION* presentation, UINT32 newVolume,
UINT32 muted)
{
UINT32 index;
UINT32 count;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
BOOL ret = TRUE;
presentation->volume = newVolume;
presentation->muted = muted;
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
{
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
ret &= tsmf_stream_change_volume(stream, newVolume, muted);
}
ArrayList_Unlock(presentation->stream_list);
return ret;
}
BOOL tsmf_presentation_paused(TSMF_PRESENTATION* presentation)
{
UINT32 index;
UINT32 count;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
BOOL ret = TRUE;
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
{
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
ret &= tsmf_stream_pause(stream);
}
ArrayList_Unlock(presentation->stream_list);
return ret;
}
BOOL tsmf_presentation_restarted(TSMF_PRESENTATION* presentation)
{
UINT32 index;
UINT32 count;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
BOOL ret = TRUE;
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
{
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
ret &= tsmf_stream_restart(stream);
}
ArrayList_Unlock(presentation->stream_list);
return ret;
2011-09-19 18:54:09 +04:00
}
BOOL tsmf_presentation_start(TSMF_PRESENTATION* presentation)
2011-09-19 18:54:09 +04:00
{
UINT32 index;
UINT32 count;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
BOOL ret = TRUE;
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
ret &= tsmf_stream_start(stream);
2011-09-19 18:54:09 +04:00
}
ArrayList_Unlock(presentation->stream_list);
return ret;
2011-09-19 18:54:09 +04:00
}
/**
* Function description
*
* @return 0 on success, otherwise a Win32 error code
*/
UINT tsmf_presentation_sync(TSMF_PRESENTATION* presentation)
2011-09-19 18:54:09 +04:00
{
UINT32 index;
UINT32 count;
UINT error;
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
TSMF_STREAM* stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
if (WaitForSingleObject(stream->ready, 500) == WAIT_FAILED)
{
error = GetLastError();
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForSingleObject failed with error %" PRIu32 "!", error);
return error;
}
2011-09-19 18:54:09 +04:00
}
ArrayList_Unlock(presentation->stream_list);
return CHANNEL_RC_OK;
}
BOOL tsmf_presentation_stop(TSMF_PRESENTATION* presentation)
{
UINT32 index;
UINT32 count;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
BOOL ret = TRUE;
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
ret &= tsmf_stream_stop(stream);
2011-09-19 18:54:09 +04:00
}
ArrayList_Unlock(presentation->stream_list);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
presentation->audio_start_time = 0;
presentation->audio_end_time = 0;
return ret;
2011-09-19 18:54:09 +04:00
}
2019-11-06 17:24:51 +03:00
BOOL tsmf_presentation_set_geometry_info(TSMF_PRESENTATION* presentation, UINT32 x, UINT32 y,
UINT32 width, UINT32 height, int num_rects,
RDP_RECT* rects)
2011-09-19 18:54:09 +04:00
{
UINT32 index;
UINT32 count;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
void* tmp_rects = NULL;
BOOL ret = TRUE;
/* The server may send messages with invalid width / height.
* Ignore those messages. */
if (!width || !height)
return TRUE;
2019-11-06 17:24:51 +03:00
/* Streams can be added/removed from the presentation and the server will resend geometry info
* when a new stream is added to the presentation. Also, num_rects is used to indicate whether
* or not the window is visible. So, always process a valid message with unchanged position/size
* and/or no visibility rects.
*/
presentation->x = x;
presentation->y = y;
presentation->width = width;
presentation->height = height;
tmp_rects = realloc(presentation->rects, sizeof(RDP_RECT) * num_rects);
if (!tmp_rects && num_rects)
2017-01-18 14:39:40 +03:00
return FALSE;
presentation->nr_rects = num_rects;
presentation->rects = tmp_rects;
2019-02-07 16:32:55 +03:00
if (presentation->rects)
CopyMemory(presentation->rects, rects, sizeof(RDP_RECT) * num_rects);
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
{
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
if (!stream->decoder)
continue;
if (stream->decoder->UpdateRenderingArea)
{
ret = stream->decoder->UpdateRenderingArea(stream->decoder, x, y, width, height,
2019-11-06 17:24:51 +03:00
num_rects, rects);
}
}
ArrayList_Unlock(presentation->stream_list);
return ret;
2011-09-19 18:54:09 +04:00
}
2019-11-06 17:24:51 +03:00
void tsmf_presentation_set_audio_device(TSMF_PRESENTATION* presentation, const char* name,
const char* device)
2011-09-19 18:54:09 +04:00
{
presentation->audio_name = name;
presentation->audio_device = device;
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
BOOL tsmf_stream_flush(TSMF_STREAM* stream)
2011-09-19 18:54:09 +04:00
{
BOOL ret = TRUE;
2019-11-06 17:24:51 +03:00
// TSMF_SAMPLE* sample;
/* TODO: free lists */
if (stream->audio)
ret = stream->audio->Flush(stream->audio);
2011-09-19 18:54:09 +04:00
stream->eos = 0;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->eos_message_id = 0;
stream->eos_channel_callback = NULL;
stream->delayed_stop = 0;
2011-09-19 18:54:09 +04:00
stream->last_end_time = 0;
stream->next_start_time = 0;
if (stream->major_type == TSMF_MAJOR_TYPE_AUDIO)
2011-09-19 18:54:09 +04:00
{
stream->presentation->audio_start_time = 0;
stream->presentation->audio_end_time = 0;
}
return TRUE;
2011-09-19 18:54:09 +04:00
}
void _tsmf_presentation_free(void* obj)
2011-09-19 18:54:09 +04:00
{
TSMF_PRESENTATION* presentation = (TSMF_PRESENTATION*)obj;
if (presentation)
{
tsmf_presentation_stop(presentation);
ArrayList_Clear(presentation->stream_list);
ArrayList_Free(presentation->stream_list);
free(presentation->rects);
ZeroMemory(presentation, sizeof(TSMF_PRESENTATION));
free(presentation);
}
2011-09-19 18:54:09 +04:00
}
2014-11-10 22:02:54 +03:00
void tsmf_presentation_free(TSMF_PRESENTATION* presentation)
2011-09-19 18:54:09 +04:00
{
ArrayList_Remove(presentation_list, presentation);
}
2011-09-19 18:54:09 +04:00
TSMF_STREAM* tsmf_stream_new(TSMF_PRESENTATION* presentation, UINT32 stream_id,
rdpContext* rdpcontext)
{
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
2011-09-19 18:54:09 +04:00
stream = tsmf_stream_find_by_id(presentation, stream_id);
if (stream)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "duplicated stream id %" PRIu32 "!", stream_id);
2011-09-19 18:54:09 +04:00
return NULL;
}
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)calloc(1, sizeof(TSMF_STREAM));
if (!stream)
{
WLog_ERR(TAG, "Calloc failed");
return NULL;
}
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->minBufferLevel = VIDEO_MIN_BUFFER_LEVEL;
stream->maxBufferLevel = VIDEO_MAX_BUFFER_LEVEL;
stream->currentBufferLevel = 1;
stream->seeking = FALSE;
stream->eos = 0;
stream->eos_message_id = 0;
stream->eos_channel_callback = NULL;
2011-09-19 18:54:09 +04:00
stream->stream_id = stream_id;
stream->presentation = presentation;
stream->stopEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
if (!stream->stopEvent)
goto error_stopEvent;
stream->ready = CreateEvent(NULL, TRUE, TRUE, NULL);
if (!stream->ready)
goto error_ready;
stream->sample_list = Queue_New(TRUE, -1, -1);
if (!stream->sample_list)
goto error_sample_list;
stream->sample_list->object.fnObjectFree = tsmf_sample_free;
stream->sample_ack_list = Queue_New(TRUE, -1, -1);
if (!stream->sample_ack_list)
goto error_sample_ack_list;
stream->sample_ack_list->object.fnObjectFree = tsmf_sample_free;
2019-11-06 17:24:51 +03:00
stream->play_thread =
CreateThread(NULL, 0, tsmf_stream_playback_func, stream, CREATE_SUSPENDED, NULL);
if (!stream->play_thread)
goto error_play_thread;
2019-11-06 17:24:51 +03:00
stream->ack_thread =
CreateThread(NULL, 0, tsmf_stream_ack_func, stream, CREATE_SUSPENDED, NULL);
if (!stream->ack_thread)
goto error_ack_thread;
2014-11-10 22:02:54 +03:00
if (ArrayList_Add(presentation->stream_list, stream) < 0)
goto error_add;
2014-11-10 22:02:54 +03:00
stream->rdpcontext = rdpcontext;
2011-09-19 18:54:09 +04:00
return stream;
error_add:
SetEvent(stream->stopEvent);
if (WaitForSingleObject(stream->ack_thread, INFINITE) == WAIT_FAILED)
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForSingleObject failed with error %" PRIu32 "!", GetLastError());
error_ack_thread:
SetEvent(stream->stopEvent);
if (WaitForSingleObject(stream->play_thread, INFINITE) == WAIT_FAILED)
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForSingleObject failed with error %" PRIu32 "!", GetLastError());
error_play_thread:
Queue_Free(stream->sample_ack_list);
error_sample_ack_list:
Queue_Free(stream->sample_list);
error_sample_list:
CloseHandle(stream->ready);
error_ready:
CloseHandle(stream->stopEvent);
error_stopEvent:
free(stream);
return NULL;
2011-09-19 18:54:09 +04:00
}
void tsmf_stream_start_threads(TSMF_STREAM* stream)
2015-05-14 16:57:37 +03:00
{
ResumeThread(stream->play_thread);
ResumeThread(stream->ack_thread);
}
2019-11-06 17:24:51 +03:00
TSMF_STREAM* tsmf_stream_find_by_id(TSMF_PRESENTATION* presentation, UINT32 stream_id)
2011-09-19 18:54:09 +04:00
{
UINT32 index;
UINT32 count;
BOOL found = FALSE;
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream;
ArrayList_Lock(presentation->stream_list);
count = ArrayList_Count(presentation->stream_list);
for (index = 0; index < count; index++)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
stream = (TSMF_STREAM*)ArrayList_GetItem(presentation->stream_list, index);
if (stream->stream_id == stream_id)
{
found = TRUE;
break;
}
2011-09-19 18:54:09 +04:00
}
ArrayList_Unlock(presentation->stream_list);
return (found) ? stream : NULL;
2011-09-19 18:54:09 +04:00
}
static void tsmf_stream_resync(void* arg)
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
TSMF_STREAM* stream = arg;
ResetEvent(stream->ready);
}
2011-09-19 18:54:09 +04:00
BOOL tsmf_stream_set_format(TSMF_STREAM* stream, const char* name, wStream* s)
{
TS_AM_MEDIA_TYPE mediatype;
BOOL ret = TRUE;
if (stream->decoder)
2011-09-19 18:54:09 +04:00
{
WLog_ERR(TAG, "duplicated call");
return FALSE;
2011-09-19 18:54:09 +04:00
}
if (!tsmf_codec_parse_media_type(&mediatype, s))
{
WLog_ERR(TAG, "unable to parse media type");
return FALSE;
}
if (mediatype.MajorType == TSMF_MAJOR_TYPE_VIDEO)
2011-09-19 18:54:09 +04:00
{
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("video width %" PRIu32 " height %" PRIu32 " bit_rate %" PRIu32
" frame_rate %f codec_data %" PRIu32 "",
mediatype.Width, mediatype.Height, mediatype.BitRate,
2019-11-06 17:24:51 +03:00
(double)mediatype.SamplesPerSecond.Numerator /
(double)mediatype.SamplesPerSecond.Denominator,
mediatype.ExtraDataSize);
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->minBufferLevel = VIDEO_MIN_BUFFER_LEVEL;
stream->maxBufferLevel = VIDEO_MAX_BUFFER_LEVEL;
2011-09-19 18:54:09 +04:00
}
else if (mediatype.MajorType == TSMF_MAJOR_TYPE_AUDIO)
{
2019-11-06 17:24:51 +03:00
DEBUG_TSMF("audio channel %" PRIu32 " sample_rate %" PRIu32 " bits_per_sample %" PRIu32
" codec_data %" PRIu32 "",
mediatype.Channels, mediatype.SamplesPerSecond.Numerator,
2019-11-06 17:24:51 +03:00
mediatype.BitsPerSample, mediatype.ExtraDataSize);
stream->sample_rate = mediatype.SamplesPerSecond.Numerator;
stream->channels = mediatype.Channels;
stream->bits_per_sample = mediatype.BitsPerSample;
if (stream->bits_per_sample == 0)
stream->bits_per_sample = 16;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->minBufferLevel = AUDIO_MIN_BUFFER_LEVEL;
stream->maxBufferLevel = AUDIO_MAX_BUFFER_LEVEL;
}
2011-09-19 18:54:09 +04:00
stream->major_type = mediatype.MajorType;
stream->width = mediatype.Width;
stream->height = mediatype.Height;
stream->decoder = tsmf_load_decoder(name, &mediatype);
ret &= tsmf_stream_change_volume(stream, stream->presentation->volume,
stream->presentation->muted);
if (!stream->decoder)
return FALSE;
if (stream->decoder->SetAckFunc)
2019-11-06 17:24:51 +03:00
ret &= stream->decoder->SetAckFunc(stream->decoder, tsmf_stream_process_ack, stream);
if (stream->decoder->SetSyncFunc)
2019-11-06 17:24:51 +03:00
ret &= stream->decoder->SetSyncFunc(stream->decoder, tsmf_stream_resync, stream);
return ret;
2011-09-19 18:54:09 +04:00
}
void tsmf_stream_end(TSMF_STREAM* stream, UINT32 message_id,
IWTSVirtualChannelCallback* pChannelCallback)
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
if (!stream)
return;
2011-09-19 18:54:09 +04:00
stream->eos = 1;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
stream->eos_message_id = message_id;
stream->eos_channel_callback = pChannelCallback;
2011-09-19 18:54:09 +04:00
}
void _tsmf_stream_free(void* obj)
2011-09-19 18:54:09 +04:00
{
TSMF_STREAM* stream = (TSMF_STREAM*)obj;
2014-11-10 22:02:54 +03:00
if (!stream)
return;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
tsmf_stream_stop(stream);
SetEvent(stream->stopEvent);
if (stream->play_thread)
{
if (WaitForSingleObject(stream->play_thread, INFINITE) == WAIT_FAILED)
{
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForSingleObject failed with error %" PRIu32 "!", GetLastError());
return;
}
CloseHandle(stream->play_thread);
stream->play_thread = NULL;
}
if (stream->ack_thread)
{
if (WaitForSingleObject(stream->ack_thread, INFINITE) == WAIT_FAILED)
{
2019-11-06 17:24:51 +03:00
WLog_ERR(TAG, "WaitForSingleObject failed with error %" PRIu32 "!", GetLastError());
return;
}
CloseHandle(stream->ack_thread);
stream->ack_thread = NULL;
}
Queue_Free(stream->sample_list);
Queue_Free(stream->sample_ack_list);
if (stream->decoder && stream->decoder->Free)
{
2011-09-19 18:54:09 +04:00
stream->decoder->Free(stream->decoder);
stream->decoder = NULL;
}
CloseHandle(stream->stopEvent);
CloseHandle(stream->ready);
2014-11-10 22:02:54 +03:00
ZeroMemory(stream, sizeof(TSMF_STREAM));
free(stream);
2011-09-19 18:54:09 +04:00
}
2014-11-10 22:02:54 +03:00
void tsmf_stream_free(TSMF_STREAM* stream)
2011-09-19 18:54:09 +04:00
{
2014-11-10 22:02:54 +03:00
TSMF_PRESENTATION* presentation = stream->presentation;
ArrayList_Remove(presentation->stream_list, stream);
}
2019-11-06 17:24:51 +03:00
BOOL tsmf_stream_push_sample(TSMF_STREAM* stream, IWTSVirtualChannelCallback* pChannelCallback,
UINT32 sample_id, UINT64 start_time, UINT64 end_time, UINT64 duration,
2019-11-06 17:24:51 +03:00
UINT32 extensions, UINT32 data_size, BYTE* data)
{
2014-11-10 22:02:54 +03:00
TSMF_SAMPLE* sample;
SetEvent(stream->ready);
if (TERMINATING)
return TRUE;
2019-11-06 17:24:51 +03:00
sample = (TSMF_SAMPLE*)calloc(1, sizeof(TSMF_SAMPLE));
if (!sample)
{
WLog_ERR(TAG, "calloc sample failed!");
return FALSE;
}
2011-09-19 18:54:09 +04:00
sample->sample_id = sample_id;
sample->start_time = start_time;
sample->end_time = end_time;
sample->duration = duration;
sample->extensions = extensions;
- Use decodebin2 instead of old decodebin - decodebin has issues - Use autovideosink - xvimagesink does not work with cards with no xv ports available and cant be used if wanted to use the fluendo hardware accelerated playback codec - Use autoaudiosink - let gstreamer choose best audio playback plugin - Catch when autosinks add known elements so that we can manipulate properties on them - Adjust caps of various media types to work better with gstreamer, some codecs are picky about having certain fields available - Remove unneeded plugins such as "ffmpegcolorspace" and "videoscale" - these do not work correctly with fluendo hardware accelerated playback codec - Name audio/video gstreamer elements better for easier debugging - Update gstreamer pipeline and element properties to handle playback better - Detect when valid timestamps are available for buffer from server and try to account for when they are not valid - Start time is much more reliable then end time from server for various media formats, so use it when possible to make decisions instead of end time - Do not rebuild gstreamer pipeline for a seek(very expensive), instead reset gstreamer time to 0 and maintain offset between real time and gstreamer time - Change buffer filled function back to a buffer level function, so that we can use buffer level to make better choices above gstreamer decoder in tsmf - Remove ack function from gstreamer, instead rely on ack thread to handle acks - Rework X11 gstreamer code to handle various videosinks which implement the XOverlayInterface and to keep more detailed information on the sub-window that is used for display - Add check to see if a decoder is available for telling the server the client various media types - Add in support for M4S2 and WMA1 media types - Fix flush message handling, they are for individual streams and not the entire presentation - Delay eos response to try to allow more time for buffers to be loaded into decoder, as we anticipate acks to server and the server will issue stop as soon as we ack eos. - Fix issue with geometry info being ignored when resent for new streams within existing presentation - Fixed volume level initialization issue when a stream is stopped and restarted - Attempt to sync video/audio streams...because we run two different gstreamer pipelines - they can enter pause/playing states at different times and are thus not synchronized. Attempt to adjust video buffer timestamps based on difference between audio/video running time to account for this difference. This logic accounts for a huge improvement in audio/video sync(ie. lip sync to words)
2015-07-08 00:39:29 +03:00
if ((sample->extensions & 0x00000080) || (sample->extensions & 0x00000040))
sample->invalidTimestamps = TRUE;
else
sample->invalidTimestamps = FALSE;
2011-09-19 18:54:09 +04:00
sample->stream = stream;
sample->channel_callback = pChannelCallback;
sample->data_size = data_size;
sample->data = calloc(1, data_size + TSMF_BUFFER_PADDING_SIZE);
if (!sample->data)
{
WLog_ERR(TAG, "calloc sample->data failed!");
free(sample);
return FALSE;
}
CopyMemory(sample->data, data, data_size);
return Queue_Enqueue(stream->sample_list, sample);
2011-09-19 18:54:09 +04:00
}
#ifndef _WIN32
static void tsmf_signal_handler(int s)
{
TERMINATING = 1;
ArrayList_Free(presentation_list);
if (s == SIGINT)
{
signal(s, SIG_DFL);
kill(getpid(), s);
}
else if (s == SIGUSR1)
{
signal(s, SIG_DFL);
}
}
#endif
BOOL tsmf_media_init(void)
2011-09-19 18:54:09 +04:00
{
#ifndef _WIN32
struct sigaction sigtrap;
sigtrap.sa_handler = tsmf_signal_handler;
sigemptyset(&sigtrap.sa_mask);
sigtrap.sa_flags = 0;
sigaction(SIGINT, &sigtrap, 0);
sigaction(SIGUSR1, &sigtrap, 0);
#endif
if (!presentation_list)
{
presentation_list = ArrayList_New(TRUE);
if (!presentation_list)
return FALSE;
ArrayList_Object(presentation_list)->fnObjectFree = _tsmf_presentation_free;
}
return TRUE;
2011-09-19 18:54:09 +04:00
}