This topic explains how to integrate the Native RTS SDK with an FFmpeg-based player on Windows to enable RTS.
Procedure
This procedure uses MSYS2 to compile FFmpeg 4.2. In the MSYS2 installation directory, open the mingw64.exe command line.
-
Download and decompress the Native RTS SDK for Windows. You can find the download URL in the release notes.
-
Copy the rtsdec.c and rtsenc.c files to the libavformat directory of the FFmpeg source code.
Modify the Makefile. Add rtsdec.o and rtsenc.o as shown in the following example:
NAME = avformat DESC = FFmpeg container format library HEADERS = avformat.h avio.h version.h OBJS = allformats.o \ avio.o \ aviobuf.o \ cutils.o \ dump.o \ format.o \ id3v1.o \ id3v2.o \ metadata.o \ mux.o \ options.o \ os_support.o \ qtpalette.o \ protocols.o \ riff.o \ sdp.o \ url.o \ utils.o \ rtsdec.o \ rtsenc.o OBJS-$(HAVE_LIBC_MSVCRT) += file_open.o rtsenc.o \ OBJS-$(HAVE_LIBC_MSVCRT) += file_open.o -
Modify allformats.c to enable support for the ARTC protocol by default.
/* external libraries */ extern AVOutputFormat ff_chromaprint_muxer; extern AVInputFormat ff_libgme_demuxer; extern AVInputFormat ff_libmodplug_demuxer; extern AVInputFormat ff_libopenmpt_demuxer; extern AVInputFormat ff_vapoursynth_demuxer; extern AVInputFormat ff_rtc_demuxer; extern AVOutputFormat ff_rtc_muxer;extern AVInputFormat ff_rtc_demuxer; -
Modify ffplay.c.
# include "libavfilter/buffersrc.h" #endif #include <SDL.h> #include <SDL_thread.h> #include "cmdutils.h" #include <assert.h> /* connect rts library to rts plugin */ struct rts_glue_funcs; extern const struct rts_glue_funcs *get_rts_funcs(int version); extern void av_set_rts_demuxer_funcs(const struct rts_glue_funcs *funcs); const char program_name[] = "ffplay"; const int program_birth_year = 2003; #define MAX_QUEUE_SIZE (15 * 1024 * 1024) #define MIN_FRAMES 1 #define EXTERNAL_CLOCK_MIN_FRAMES 2 #define EXTERNAL_CLOCK_MAX_FRAMES 10/* connect rts library to rts plugin */ struct rts_glue_funcs; extern const struct rts_glue_funcs *get_rts_funcs(int version); extern void av_set_rts_demuxer_funcs(const struct rts_glue_funcs *funcs);static int is_realtime(AVFormatContext *s) { if( !strcmp(s->iformat->name, "rtp") || !strcmp(s->iformat->name, "rtsp") || !strcmp(s->iformat->name, "sdp") // Added || !strcmp(s->iformat->name, "artc") // Added ) return 1; if(s->pb && ( !strncmp(s->url, "rtp:", 4) || !strncmp(s->url, "udp:", 4) ) ) return 1; return 0; }|| !strcmp(s->iformat->name, "artc")); } /* called from the main */ int main(int argc, char **argv) { int flags; VideoState *is; init_dynload(); av_log_set_flags(AV_LOG_SKIP_REPEATED); parse_loglevel(argc, argv, options); /* register all codecs, demux and protocols */ #if CONFIG_AVDEVICE avdevice_register_all(); #endif avformat_network_init(); init_opts(); signal(SIGINT , sigterm_handler); /* Interrupt (ANSI). */ signal(SIGTERM, sigterm_handler); /* Termination (ANSI). */ av_set_rts_demuxer_funcs(get_rts_funcs(2)); show_banner(argc, argv, options); }av_set_rts_demuxer_funcs(get_rts_funcs(2)); -
Modify the Makefile in the same directory as ffplay.c.
$(1)$(PROGSSUF)_g$(EXESUF): FF_EXTRALIBS += $(EXTRALIBS-$(1)) -lRtsSDK --verbose ifeq ($(TARGET_OS),windows) LDFLAGS += -L../../release/windows/x86_64/RtsSDK/lib/ -lRtsSDK endif ifeq ($(TARGET_OS),mac) LDFLAGS += -L../../release/mac/x86_64/RtsSDK/lib -lRtsSDK endif -
Compile and run the project.
./ffplay "artc://<streaming URL>"
NoteTo achieve the lowest latency, run the following command: ./ffplay -fflags nobuffer -flags low_delay "artc://<streaming URL>".
PREFIX_DIR=`pwd`/"build-out-windows" CFLAGS="$CFLAGS -DWIN32 -D_WIN32 -DNDEBUG" ./configure \ --prefix=$PREFIX_DIR \ --extra-cflags="$CFLAGS" \ --enable-shared \ --disable-static \ --enable-gpl \ --enable-nonfree \ --enable-libfdk-aac \ --disable-decoder=hevc \ --disable-parser=hevc \ --disable-encoders || exit 1 make TARGET_OS=windows -j8 && make install || exit 1 cp /mingw64/bin/SDL2.dll ${PREFIX_DIR}/bin cp ../../release/windows/x86_64/RtsSDK/lib/RtsSDK.dll ${PREFIX_DIR}/bin echo "FFmpeg created in $PREFIX_DIR"