Building GStreamer from source - Docker

I am trying to use NVIDIA DeepStream (>=6.2) with an upgraded GStreamer (>=1.20). I want to create a Dockerfile that essentially loads up this image: nvcr.io/nvidia/deepstream:6.2-devel, uninstalls the base gstreamer (1.16.3) and then install gstreamer from source (in this case 1.22). Here is my Dockerfile:

# NOTE: this image contains user_deepstream_python_apps_install.sh, which could be used for pyds install
FROM nvcr.io/nvidia/deepstream:6.2-devel
# To get video driver libraries at runtime (libnvidia-encode.so/libnvcuvid.so)
ENV NVIDIA_DRIVER_CAPABILITIES $NVIDIA_DRIVER_CAPABILITIES,video
# Prepare PIP
RUN python3 -m pip install --upgrade pip
RUN apt update
RUN apt-get update
RUN apt-get update && apt-get install -y zlib1g-dev libffi-dev libssl-dev

# =========== RM and REBUILD GST ============ #
RUN pip3 install meson==0.62
RUN apt-get install -y libmount-dev
RUN apt-get install -y flex
RUN apt-get install -y flex bison
RUN apt-get install -y libglib2.0-dev
# Base Gst that comes with the image is /lib/x86.../gstreamer-1.0
RUN apt-get remove -y *gstreamer*
RUN mkdir /tmp/gst-1.22
WORKDIR /tmp/gst-1.22
#Clone the repository
RUN git clone https://gitlab.freedesktop.org/gstreamer/gstreamer
#Select the gstreamer version to checkout
RUN cd gstreamer && git checkout 1.22
WORKDIR /tmp/gst-1.22/gstreamer
#Build Gst
#RUN meson build --prefix=/usr
RUN meson --prefix=/usr -Dgpl=enabled build
RUN ninja -C build/
WORKDIR /tmp/gst-1.22/gstreamer/build/
RUN ninja install

# =============== PYDS Build =============== #
# Python DeepStream Bindings
WORKDIR /opt/nvidia/deepstream/deepstream/
RUN ./user_deepstream_python_apps_install.sh --version 1.1.6
WORKDIR /

# ============== Gst Rust Plugins ============== #
# RUST PLUGINS
RUN mkdir /tmp/gst-1.22/rs
WORKDIR /tmp/gst-1.22/rs
RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y
ENV PATH "/root/.cargo/bin:${PATH}"
RUN git clone https://gitlab.freedesktop.org/gstreamer/gst-plugins-rs.git
RUN cargo install cargo-c
WORKDIR /tmp/gst-1.22/rs/gst-plugins-rs
#gst-plugins-rs/utils/fallbackswitch
RUN cargo cbuild -p gst-plugin-fallbackswitch --prefix=/usr
RUN cargo cinstall -p gst-plugin-fallbackswitch --pregix=/usr

Things seem to be succesful until I attempt: RUN cargo cbuild -p gst-plugin-fallbackswitch --prefix=/usr
I get the following error:

   ...
   Compiling gstreamer-audio-sys v0.22.0 (https://gitlab.freedesktop.org/gstreamer/gstreamer-rs#4a015d94)
   Compiling gstreamer-video-sys v0.22.0 (https://gitlab.freedesktop.org/gstreamer/gstreamer-rs#4a015d94)
   Compiling gst-plugin-fallbackswitch v0.12.0-alpha.1 (/tmp/gst-1.22/rs/gst-plugins-rs/utils/fallbackswitch)
The following warnings were emitted during compilation:

warning: `PKG_CONFIG_ALLOW_SYSTEM_CFLAGS="1" "pkg-config" "--libs" "--cflags" "gstreamer-1.0" "gstreamer-1.0 >= 1.20"` did not exit successfully: exit status: 1

error: failed to run custom build command for `gstreamer-sys v0.22.0 (https://gitlab.freedesktop.org/gstreamer/gstreamer-rs#4a015d94)`

Caused by:
  process didn't exit successfully: `/tmp/gst-1.22/rs/gst-plugins-rs/target/debug/build/gstreamer-sys-7a1b658778e79f59/build-script-build` (exit status: 1)
  --- stdout
  cargo:rerun-if-env-changed=GSTREAMER_1.0_NO_PKG_CONFIG
  cargo:rerun-if-env-changed=PKG_CONFIG_x86_64-unknown-linux-gnu
  cargo:rerun-if-env-changed=PKG_CONFIG_x86_64_unknown_linux_gnu
  cargo:rerun-if-env-changed=HOST_PKG_CONFIG
  cargo:rerun-if-env-changed=PKG_CONFIG
  cargo:rerun-if-env-changed=PKG_CONFIG_PATH_x86_64-unknown-linux-gnu
  cargo:rerun-if-env-changed=PKG_CONFIG_PATH_x86_64_unknown_linux_gnu
  cargo:rerun-if-env-changed=HOST_PKG_CONFIG_PATH
  cargo:rerun-if-env-changed=PKG_CONFIG_PATH
  cargo:rerun-if-env-changed=PKG_CONFIG_LIBDIR_x86_64-unknown-linux-gnu
  cargo:rerun-if-env-changed=PKG_CONFIG_LIBDIR_x86_64_unknown_linux_gnu
  cargo:rerun-if-env-changed=HOST_PKG_CONFIG_LIBDIR
  cargo:rerun-if-env-changed=PKG_CONFIG_LIBDIR
  cargo:rerun-if-env-changed=PKG_CONFIG_SYSROOT_DIR_x86_64-unknown-linux-gnu
  cargo:rerun-if-env-changed=PKG_CONFIG_SYSROOT_DIR_x86_64_unknown_linux_gnu
  cargo:rerun-if-env-changed=HOST_PKG_CONFIG_SYSROOT_DIR
  cargo:rerun-if-env-changed=PKG_CONFIG_SYSROOT_DIR
  cargo:warning=`PKG_CONFIG_ALLOW_SYSTEM_CFLAGS="1" "pkg-config" "--libs" "--cflags" "gstreamer-1.0" "gstreamer-1.0 >= 1.20"` did not exit successfully: exit status: 1
  error: could not find system library 'gstreamer-1.0' required by the 'gstreamer-sys' crate

  --- stderr
  Requested 'gstreamer-1.0 >= 1.20' but version of GStreamer is 1.16.3

warning: build failed, waiting for other jobs to finish...
Error: CliError { error: Some(1 job failed), exit_code: 101 }

I’m guessing I may need some sort of PATH variable change?
Also, I’m uncertain as to why it still seems to find GStreamer 1.16.3, it would seem I’m also not uninstalling gstreamer properly…

The goal of this is to be able to use the NVIDIA DeepStream hardware acceleration elements along with the later version of gstreamer for access to new features + plugins.

There’s still libgstreamer1.0-dev installed at least from the old version. Also I would expect that simply removing all system GStreamer packages will also remove half of deepstream.

If you want to use Ubuntu the correct approach forward here would be to create updated Ubuntu packages with the new GStreamer version, and then install those.

Alternatively you could install GStreamer into a different prefix and hope that having the two different versions somehow works out. You’ll at least have to set PKG_CONFIG_PATH to the lib/pkgconfig directory of your newer GStreamer installation though, and make sure that the LD_LIBRARY_PATH is also configured correctly.

What do you mean here? If I were to start with just a base ubuntu:20.04 image, install GStreamer 1.22 based on (GStreamer / gstreamer · GitLab), would that suffice?
Or with the existing image that I’m using do you mean there is a way to just upgrade GStream 1.16 → 1.22?

I mean native Ubuntu .deb packages.

1 Like

Thanks for the help, really appreciate it!
Ok, so attempting this method:

I can edit my Dockerfile to:

ENV PKG_CONFIG_PATH=/tmp/gst-1.22/gstreamer/lib/x86_64-linux-gnu/pkgconfig
RUN meson setup --prefix=/tmp/gst-1.22/gstreamer -Dgpl=enabled build
RUN meson compile -C build
ENV LD_LIBRARY_PATH "/tmp/gst-1.22/gstreamer/lib/":$LD_LIBRARY_PATH
RUN ldconfig

Along with getting rid of the remove gstreamer step, this leaves /usr/lib/x86_64-linux-gnu/gstreamer-1.0/ as the GStreamer 1.16 that comes with the image (gst-inspect-1.0 still points to 1.16 etc.). The LD_LIBRARY_PATH is now /tmp/gst-1.22/gstreamer/lib/:/usr/local/nvidia/lib:/usr/local/nvidia/lib64

Is this right, based on what you had suggested?

Something like that, yes. It might need a bit more, you’ll have to test and see what happens. Getting such setups to work is always a bit tricky.

/opt may be a better place for installation. You may want to add `/tmp/gst-1.22/gstreamer/bin path to $PATH as well like

ENV PATH "/tmp/gst-1.22/gstreamer/bin":$PATH

You may likely want to build the drivers of video cards at the same time if they are old. If yes, do not forget to set new path for the drivers.

1 Like

Updating here as I’ve had some success with my Docker setup. I can now build from source GStreamer 1.22, build the rust plugins, link Deepstream to Gst 1.22, and actually run the sample python gst applications that come with Deepstream. I am attaching it here incase it is useful to others- also I have a couple questions!

Note: this is still a rough copy…

# RUN ME: 	docker run --gpus device=0 -it {tag}
# NOTE: 	this image contains some .sh scripts for installations inside /opt/nvidia/deepstream/deepstream/ 
FROM nvcr.io/nvidia/deepstream:6.2-devel
# To get video driver libraries at runtime (libnvidia-encode.so/libnvcuvid.so)
ENV NVIDIA_DRIVER_CAPABILITIES $NVIDIA_DRIVER_CAPABILITIES,video
# Prepare PIP
RUN python3 -m pip install --upgrade pip
RUN apt update
RUN apt-get update && apt-get install -y zlib1g-dev libffi-dev libssl-dev

# =============== PYDS Build =============== #
# Python DeepStream Bindings
WORKDIR /opt/nvidia/deepstream/deepstream/
RUN ./user_deepstream_python_apps_install.sh --version 1.1.6
WORKDIR /

# =========== RM and REBUILD GST ============ #
RUN pip3 install meson==0.62
RUN apt-get install -y libmount-dev
RUN apt-get install -y flex
RUN apt-get install -y flex bison
RUN apt-get install -y libglib2.0-dev
# Base Gst that comes with the image is /usr/lib/x86.../gstreamer-1.0
# RUN apt-get remove -y *gstreamer*
RUN mkdir /opt/gst-1.22
WORKDIR /opt/gst-1.22
#Clone the repository
RUN git clone https://gitlab.freedesktop.org/gstreamer/gstreamer
#Select the gstreamer version to checkout
RUN cd gstreamer && git checkout 1.22
WORKDIR /opt/gst-1.22/gstreamer
#Build Gst
#RUN meson build --prefix=/usr
RUN meson --prefix=/opt/gst-1.22/gstreamer -Dgpl=enabled build
RUN ninja -C build/
WORKDIR /opt/gst-1.22/gstreamer/build/
RUN ninja install

# ============== Gst Rust Plugins ============== #
# RUST PLUGINS
RUN mkdir /opt/gst-1.22/rs
WORKDIR /opt/gst-1.22/rs
RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y
ENV PATH "/root/.cargo/bin:${PATH}"
RUN git clone https://gitlab.freedesktop.org/gstreamer/gst-plugins-rs.git
RUN cargo install cargo-c
WORKDIR /opt/gst-1.22/rs/gst-plugins-rs
ENV PKG_CONFIG_PATH /opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu/pkgconfig
#gst-plugins-rs/utils/fallbackswitch
RUN cargo cbuild -p gst-plugin-fallbackswitch --prefix=/opt/gst-1.22/gstreamer
RUN cargo cinstall -p gst-plugin-fallbackswitch --prefix=/opt/gst-1.22/gstreamer

# Link new gstreamer with deepstream
RUN update-alternatives --install /opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu/gstreamer-1.0/deepstream deepstream-plugins /opt/nvidia/deepstream/deepstream-6.2/lib/gst-plugins 62
ENV LD_LIBRARY_PATH $LD_LIBRARY_PATH:/opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu
# Incase nvvideo4linux2 decoder etc. is blacklisted try:
#RUN rm ~/.cache/gstreamer/x86_64-linux-gnu
WORKDIR /


# ============== pip-installs ================ #
#WORKDIR /opt/my_installs/pip_installs
#COPY ./requirements.txt ./
#RUN pip install --upgrade pip && \
#    pip install -r ./requirements.txt

# ================= CLEAN UP ================= #
#WORKDIR /
#RUN rm -r /opt/my_installs/pip_installs
#RUN rm -rf /tmp/gst-1.22
#e.g. rm -rf /tmp/gst-1.18.6

The key seemed to be in the update-alternatives step- as far as I can tell things seem to be functioning (nvv4l2decoder, nvstreammux, etc.) with gst-1.22. Even when I run the python samples and add a print to verify the Gst version being used it is 1.22.

  1. I am wondering how to properly link the rust plugins though. I have tried running with --prefix and with --libdir /opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu, however, I can’t seem to get gst-inspect-1.0 to find fallbacksrc or fallbackswitch. I assume there is just a simple link I have to make somewhere. Any advice here?
    Currently the lib/ directory looks like:
/opt/gst-1.22/gstreamer/lib/ {gstreamer-1.0/, pkgconfig/, python3/, x86_64-linux-gnu/}

Really, I can fix it with a simple copy of the files in /opt/gst-1.22/gstreamer/lib/gstreamer-1.0/ to /opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu//gstreamer-1.0/ …doing this allows me to run gst-inspect-1.0 on fallbacksrc and fallbackswitch. However, I’d like to do it properly on the cbuild/cinstall step (?).

  1. Also, outside of just confirming that the python applications are able to run properly. Are there any other tests I should try running to make sure things are stable?
1 Like

Fixed the issue I was having with my first point (1.)!

Can you please share how you fixed point #1? I did just like you did with adding: --prefix /opt/gst-1.22/gstreamer, but it still can’t find the plugin
@ConnorM

Hey @omerts it should just be a matter of carefully managing where you are installing the plug-ins + setting up your environment paths (maybe enter the docker container in -it mode and try to make sure paths are setup properly and everything is installing where you expect it). Here is my latest Dockerfile that I had success with:

*Also note that as of DS 6.4 it runs natively with Gst 1.20.3 ([Quickstart Guide — DeepStream documentation 6.4 documentation](https://DS6.4 dGPU Installation))

# RUN ME: 	docker run --gpus device=0 -it {tag}
# NOTE: 	this image contains some .sh scripts for installations inside /opt/nvidia/deepstream/deepstream/ 
FROM nvcr.io/nvidia/deepstream:6.2-devel
# To get video driver libraries at runtime (libnvidia-encode.so/libnvcuvid.so)
ENV NVIDIA_DRIVER_CAPABILITIES $NVIDIA_DRIVER_CAPABILITIES,video


# Prepare PIP
RUN python3 -m pip install --upgrade pip
RUN apt update
RUN apt-get update
RUN apt-get install -y zlib1g-dev libffi-dev libssl-dev


# =========== CREATE INSTALL DIRs ============ #
RUN mkdir -p /opt/pip_installs
RUN mkdir -p /outputs/logs && mkdir -p /outputs/graphs && mkdir -p /outputs/engines 


# =============== PYDS Build =============== #
# Python DeepStream Bindings
WORKDIR /opt/nvidia/deepstream/deepstream/
RUN ./user_deepstream_python_apps_install.sh --version 1.1.6
WORKDIR /


# =========== RM and REBUILD GST ============ #
RUN pip3 install meson==0.62
RUN apt-get install -y libmount-dev
RUN apt-get install -y flex
RUN apt-get install -y flex bison
RUN apt-get install -y libglib2.0-dev
# Base Gst that comes with the image is /usr/lib/x86.../gstreamer-1.0
RUN mkdir /opt/gst-1.22
WORKDIR /opt/gst-1.22
#Clone the repository
RUN git clone https://gitlab.freedesktop.org/gstreamer/gstreamer
#Select the gstreamer version to checkout
RUN cd gstreamer && git checkout 1.22
WORKDIR /opt/gst-1.22/gstreamer
#Build Gst
#RUN meson build --prefix=/usr
RUN meson --prefix=/opt/gst-1.22/gstreamer -Dgpl=enabled build
RUN ninja -C build/
WORKDIR /opt/gst-1.22/gstreamer/build/
RUN ninja install


# ============== Gst Rust Plugins ============== #
# RUST PLUGINS
RUN mkdir /opt/gst-1.22/rs
WORKDIR /opt/gst-1.22/rs
RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y
ENV PATH "/root/.cargo/bin:${PATH}"
RUN git clone https://gitlab.freedesktop.org/gstreamer/gst-plugins-rs.git
RUN cargo install cargo-c
WORKDIR /opt/gst-1.22/rs/gst-plugins-rs
ENV PKG_CONFIG_PATH /opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu/pkgconfig
#gst-plugins-rs/utils/fallbackswitch
RUN cargo cbuild -p gst-plugin-fallbackswitch --libdir=/opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu
RUN cargo cinstall -p gst-plugin-fallbackswitch --libdir=/opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu


# =============== LINK GSt and DS =============== #
# Link new gstreamer with deepstream
RUN update-alternatives --install /opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu/gstreamer-1.0/deepstream deepstream-plugins /opt/nvidia/deepstream/deepstream-6.2/lib/gst-plugins 62
ENV LD_LIBRARY_PATH $LD_LIBRARY_PATH:/opt/gst-1.22/gstreamer/lib/x86_64-linux-gnu
# Incase nvvideo4linux2 decoder etc. is blacklisted try:
#RUN rm ~/.cache/gstreamer/x86_64-linux-gnu