From 962525c1e7e72ba00cb68190c2259412a7899643 Mon Sep 17 00:00:00 2001 From: Jared Baur Date: Sat, 3 May 2025 20:23:45 -0700 Subject: [PATCH] kodi: package build-time tools separately Packaging buid-time tools internal to Kodi in separate derivations allow for cross-compiling Kodi without mixing which dependencies are needed for those build-time tools vs the Kodi runtime programs. --- pkgs/applications/video/kodi/unwrapped.nix | 589 +++++++++++---------- 1 file changed, 319 insertions(+), 270 deletions(-) diff --git a/pkgs/applications/video/kodi/unwrapped.nix b/pkgs/applications/video/kodi/unwrapped.nix index 4012b94eb450..937a2274548f 100644 --- a/pkgs/applications/video/kodi/unwrapped.nix +++ b/pkgs/applications/video/kodi/unwrapped.nix @@ -186,294 +186,343 @@ let lib.optional gbmSupport "gbm" ++ lib.optional waylandSupport "wayland" ++ lib.optional x11Support "x11"; - in -stdenv.mkDerivation (finalAttrs: { - pname = "kodi"; - version = "21.2"; - kodiReleaseName = "Omega"; +stdenv.mkDerivation ( + finalAttrs: + let + texturePacker = buildPackages.callPackage ( + { + cmake, + giflib, + libjpeg, + libpng, + lzo, + stdenv, + zlib, + pkg-config, + }: + stdenv.mkDerivation { + pname = finalAttrs.pname + "-build-tool-texture-packer"; + inherit (finalAttrs) version src; - src = fetchFromGitHub { - owner = "xbmc"; - repo = "xbmc"; - rev = "${finalAttrs.version}-${finalAttrs.kodiReleaseName}"; - hash = "sha256-RdTJcq6FPerQx05dU3r8iyaorT4L7162hg5RdywsA88="; - }; + sourceRoot = "${finalAttrs.src.name}/tools/depends/native/TexturePacker/src"; - patches = [ - # Backport to fix build with Pipewire 1.4 - # FIXME: remove in the next update - (fetchpatch { - url = "https://github.com/xbmc/xbmc/commit/269053ebbfd3cc4a3156a511f54ab7f08a09a730.patch"; - hash = "sha256-JzzrMJvAufrxTxtWnzknUS9JLJEed+qdtVnIYYe9LCw="; - }) - ]; + nativeBuildInputs = [ + pkg-config + cmake + ]; - # make derivations declared in the let binding available here, so - # they can be overridden - inherit - libdvdcss - libdvdnav - libdvdread - groovy - apache_commons_lang - apache_commons_text - ; + buildInputs = [ + giflib + libjpeg + libpng + lzo + zlib + ]; - buildInputs = - [ - gnutls - libidn2 - libtasn1 - nasm - p11-kit - libxml2 - python3Packages.python - boost - libmicrohttpd - gettext - pcre-cpp - yajl - fribidi - libva - libdrm - openssl - gperf - tinyxml2 - tinyxml-2 - taglib - libssh - gtest - ncurses - spdlog - alsa-lib - libGL - libGLU - fontconfig - freetype - ftgl - libjpeg - libpng - libtiff - libmpeg2 - libsamplerate - libmad - libogg - libvorbis - flac - libxslt - systemd - lzo - libcdio - libmodplug - libass - libbluray - libudfread - sqlite - libmysqlclient - avahi - lame - curl - bzip2 - zip - unzip - mesa-demos - libcec - libcec_platform - dcadec - libuuid - libxcrypt - libgcrypt - libgpg-error - libunistring - libcrossguid - libplist - bluez - giflib - glib - harfbuzz - lcms2 - libpthreadstubs - ffmpeg - flatbuffers - fstrcmp - rapidjson - lirc - mesa-gl-headers - ] - ++ lib.optionals x11Support [ - libX11 - xorgproto - libXt - libXmu - libXext.dev - libXdmcp - libXinerama - libXrandr.dev - libXtst - libXfixes - ] - ++ lib.optional dbusSupport dbus - ++ lib.optional joystickSupport cwiid - ++ lib.optional nfsSupport libnfs - ++ lib.optional pulseSupport libpulseaudio - ++ lib.optional pipewireSupport pipewire - ++ lib.optional rtmpSupport rtmpdump - ++ lib.optional sambaSupport samba - ++ lib.optional udevSupport udev - ++ lib.optional usbSupport libusb-compat-0_1 - ++ lib.optional vdpauSupport libvdpau - ++ lib.optionals waylandSupport [ - wayland - waylandpp.dev - wayland-protocols - # Not sure why ".dev" is needed here, but CMake doesn't find libxkbcommon otherwise - libxkbcommon.dev - ] - ++ lib.optionals gbmSupport [ - libxkbcommon.dev - libgbm - libinput.dev - libdisplay-info + env.NIX_CFLAGS_COMPILE = lib.optionalString (!stdenv.hostPlatform.isWindows) "-DTARGET_POSIX"; + + preConfigure = '' + cmakeFlagsArray+=(-DKODI_SOURCE_DIR=$src -DCMAKE_MODULE_PATH=$src/cmake/modules) + ''; + + meta.mainProgram = "TexturePacker"; + } + ) { }; + + jsonSchemaBuilder = buildPackages.callPackage ( + { stdenv, cmake }: + stdenv.mkDerivation { + pname = finalAttrs.pname + "-build-tool-json-schema-builder"; + inherit (finalAttrs) version src; + + sourceRoot = "${finalAttrs.src.name}/tools/depends/native/JsonSchemaBuilder/src"; + + nativeBuildInputs = [ cmake ]; + + meta.mainProgram = "JsonSchemaBuilder"; + } + ) { }; + in + { + pname = "kodi"; + version = "21.2"; + kodiReleaseName = "Omega"; + + src = fetchFromGitHub { + owner = "xbmc"; + repo = "xbmc"; + rev = "${finalAttrs.version}-${finalAttrs.kodiReleaseName}"; + hash = "sha256-RdTJcq6FPerQx05dU3r8iyaorT4L7162hg5RdywsA88="; + }; + + patches = [ + # Backport to fix build with Pipewire 1.4 + # FIXME: remove in the next update + (fetchpatch { + url = "https://github.com/xbmc/xbmc/commit/269053ebbfd3cc4a3156a511f54ab7f08a09a730.patch"; + hash = "sha256-JzzrMJvAufrxTxtWnzknUS9JLJEed+qdtVnIYYe9LCw="; + }) ]; - nativeBuildInputs = - [ - cmake - doxygen - makeWrapper - which - pkg-config - autoconf - automake - libtool # still needed for some components. Check if that is the case with 19.0 - jre_headless - yasm - gettext - python3Packages.python - flatbuffers + # make derivations declared in the let binding available here, so + # they can be overridden + inherit + libdvdcss + libdvdnav + libdvdread + groovy + apache_commons_lang + apache_commons_text + ; - # for TexturePacker - giflib - zlib - libpng - libjpeg - lzo - ] - ++ lib.optionals waylandSupport [ - wayland-protocols - waylandpp.bin + buildInputs = + [ + gnutls + libidn2 + libtasn1 + nasm + p11-kit + libxml2 + python3Packages.python + boost + libmicrohttpd + gettext + pcre-cpp + yajl + fribidi + libva + libdrm + openssl + gperf + tinyxml2 + tinyxml-2 + taglib + libssh + gtest + ncurses + spdlog + alsa-lib + libGL + libGLU + fontconfig + freetype + ftgl + libjpeg + libpng + libtiff + libmpeg2 + libsamplerate + libmad + libogg + libvorbis + flac + libxslt + systemd + lzo + libcdio + libmodplug + libass + libbluray + libudfread + sqlite + libmysqlclient + avahi + lame + curl + bzip2 + zip + unzip + mesa-demos + libcec + libcec_platform + dcadec + libuuid + libxcrypt + libgcrypt + libgpg-error + libunistring + libcrossguid + libplist + bluez + glib + harfbuzz + lcms2 + libpthreadstubs + ffmpeg + flatbuffers + fstrcmp + rapidjson + lirc + mesa-gl-headers + + # Deps needed by TexturePacker, which is built and installed in normal + # kodi build, however the one used during the build is not this one + # in order to support cross-compilation. + giflib + zlib + ] + ++ lib.optionals x11Support [ + libX11 + xorgproto + libXt + libXmu + libXext.dev + libXdmcp + libXinerama + libXrandr.dev + libXtst + libXfixes + ] + ++ lib.optional dbusSupport dbus + ++ lib.optional joystickSupport cwiid + ++ lib.optional nfsSupport libnfs + ++ lib.optional pulseSupport libpulseaudio + ++ lib.optional pipewireSupport pipewire + ++ lib.optional rtmpSupport rtmpdump + ++ lib.optional sambaSupport samba + ++ lib.optional udevSupport udev + ++ lib.optional usbSupport libusb-compat-0_1 + ++ lib.optional vdpauSupport libvdpau + ++ lib.optionals waylandSupport [ + wayland + waylandpp.dev + wayland-protocols + # Not sure why ".dev" is needed here, but CMake doesn't find libxkbcommon otherwise + libxkbcommon.dev + ] + ++ lib.optionals gbmSupport [ + libxkbcommon.dev + libgbm + libinput.dev + libdisplay-info + ]; + + nativeBuildInputs = + [ + cmake + doxygen + makeWrapper + which + pkg-config + autoconf + automake + libtool # still needed for some components. Check if that is the case with 19.0 + jre_headless + yasm + gettext + python3Packages.python + flatbuffers + ] + ++ lib.optionals waylandSupport [ + wayland-protocols + waylandpp.bin + ]; + + depsBuildBuild = [ + buildPackages.stdenv.cc ]; - depsBuildBuild = [ - buildPackages.stdenv.cc - ]; + cmakeFlags = + [ + "-DAPP_RENDER_SYSTEM=${if gbmSupport then "gles" else "gl"}" + "-Dlibdvdcss_URL=${finalAttrs.libdvdcss}" + "-Dlibdvdnav_URL=${finalAttrs.libdvdnav}" + "-Dlibdvdread_URL=${finalAttrs.libdvdread}" + "-Dgroovy_SOURCE_DIR=${finalAttrs.groovy}" + "-Dapache-commons-lang_SOURCE_DIR=${finalAttrs.apache_commons_lang}" + "-Dapache-commons-text_SOURCE_DIR=${finalAttrs.apache_commons_text}" + # Upstream derives this from the git HEADs hash and date. + # LibreElec (minimal distro for kodi) uses the equivalent to this. + "-DGIT_VERSION=${finalAttrs.version}-${finalAttrs.kodiReleaseName}" + "-DENABLE_EVENTCLIENTS=ON" + "-DENABLE_INTERNAL_CROSSGUID=OFF" + "-DENABLE_INTERNAL_RapidJSON=OFF" + "-DENABLE_OPTICAL=${if opticalSupport then "ON" else "OFF"}" + "-DENABLE_VDPAU=${if vdpauSupport then "ON" else "OFF"}" + "-DLIRC_DEVICE=/run/lirc/lircd" + "-DSWIG_EXECUTABLE=${buildPackages.swig}/bin/swig" + "-DFLATBUFFERS_FLATC_EXECUTABLE=${buildPackages.flatbuffers}/bin/flatc" + "-DPYTHON_EXECUTABLE=${buildPackages.python3Packages.python}/bin/python" + "-DPYTHON_LIB_PATH=${python3Packages.python.sitePackages}" + "-DWITH_JSONSCHEMABUILDER=${lib.getExe jsonSchemaBuilder}" + # When wrapped KODI_HOME will likely contain symlinks to static assets + # that Kodi's built in webserver will cautiously refuse to serve up + # (because their realpaths are outside of KODI_HOME and the other + # whitelisted directories). This adds the entire nix store to the Kodi + # webserver whitelist to avoid this problem. + "-DKODI_WEBSERVER_EXTRA_WHITELIST=${builtins.storeDir}" + ] + ++ lib.optionals waylandSupport [ + "-DWAYLANDPP_SCANNER=${buildPackages.waylandpp}/bin/wayland-scanner++" + ] + ++ lib.optionals (stdenv.hostPlatform != stdenv.buildPlatform) [ + "-DWITH_TEXTUREPACKER=${lib.getExe texturePacker}" + ]; - cmakeFlags = - [ - "-DAPP_RENDER_SYSTEM=${if gbmSupport then "gles" else "gl"}" - "-Dlibdvdcss_URL=${finalAttrs.libdvdcss}" - "-Dlibdvdnav_URL=${finalAttrs.libdvdnav}" - "-Dlibdvdread_URL=${finalAttrs.libdvdread}" - "-Dgroovy_SOURCE_DIR=${finalAttrs.groovy}" - "-Dapache-commons-lang_SOURCE_DIR=${finalAttrs.apache_commons_lang}" - "-Dapache-commons-text_SOURCE_DIR=${finalAttrs.apache_commons_text}" - # Upstream derives this from the git HEADs hash and date. - # LibreElec (minimal distro for kodi) uses the equivalent to this. - "-DGIT_VERSION=${finalAttrs.version}-${finalAttrs.kodiReleaseName}" - "-DENABLE_EVENTCLIENTS=ON" - "-DENABLE_INTERNAL_CROSSGUID=OFF" - "-DENABLE_INTERNAL_RapidJSON=OFF" - "-DENABLE_OPTICAL=${if opticalSupport then "ON" else "OFF"}" - "-DENABLE_VDPAU=${if vdpauSupport then "ON" else "OFF"}" - "-DLIRC_DEVICE=/run/lirc/lircd" - "-DSWIG_EXECUTABLE=${buildPackages.swig}/bin/swig" - "-DFLATBUFFERS_FLATC_EXECUTABLE=${buildPackages.flatbuffers}/bin/flatc" - "-DPYTHON_EXECUTABLE=${buildPackages.python3Packages.python}/bin/python" - "-DPYTHON_LIB_PATH=${python3Packages.python.sitePackages}" - # When wrapped KODI_HOME will likely contain symlinks to static assets - # that Kodi's built in webserver will cautiously refuse to serve up - # (because their realpaths are outside of KODI_HOME and the other - # whitelisted directories). This adds the entire nix store to the Kodi - # webserver whitelist to avoid this problem. - "-DKODI_WEBSERVER_EXTRA_WHITELIST=${builtins.storeDir}" - ] - ++ lib.optionals waylandSupport [ - "-DWAYLANDPP_SCANNER=${buildPackages.waylandpp}/bin/wayland-scanner++" - ]; + # 14 tests fail but the biggest issue is that every test takes 30 seconds - + # I'm guessing there is a thing waiting to time out + doCheck = false; - # 14 tests fail but the biggest issue is that every test takes 30 seconds - - # I'm guessing there is a thing waiting to time out - doCheck = false; - - preConfigure = - '' + preConfigure = '' cmakeFlagsArray+=("-DCORE_PLATFORM_NAME=${lib.concatStringsSep " " kodi_platforms}") - '' - + lib.optionalString (stdenv.hostPlatform != stdenv.buildPlatform) '' - # Need these tools on the build system when cross compiling, - # hacky, but have found no other way. - CXX=$CXX_FOR_BUILD LD=ld make -C tools/depends/native/JsonSchemaBuilder - appendToVar cmakeFlags "-DWITH_JSONSCHEMABUILDER=$PWD/tools/depends/native/JsonSchemaBuilder/bin" - - CXX=$CXX_FOR_BUILD LD=ld make EXTRA_CONFIGURE= -C tools/depends/native/TexturePacker - appendToVar cmakeFlags "-DWITH_TEXTUREPACKER=$PWD/tools/depends/native/TexturePacker/bin" ''; - postInstall = '' - # TODO: figure out which binaries should be wrapped this way and which shouldn't - for p in $(ls --ignore=kodi-send $out/bin/) ; do - wrapProgram $out/bin/$p \ - --prefix PATH ":" "${ - lib.makeBinPath ( - [ - python3Packages.python - mesa-demos - ] - ++ lib.optional x11Support xdpyinfo - ++ lib.optional sambaSupport samba - ) - }" \ - --prefix LD_LIBRARY_PATH ":" "${ - lib.makeLibraryPath ( - [ - curl - systemd - libmad - libcec - libcec_platform - libass - ] - ++ lib.optional vdpauSupport libvdpau - ++ lib.optional nfsSupport libnfs - ++ lib.optional rtmpSupport rtmpdump - ) - }" - done + postInstall = '' + # TODO: figure out which binaries should be wrapped this way and which shouldn't + for p in $(ls --ignore=kodi-send $out/bin/) ; do + wrapProgram $out/bin/$p \ + --prefix PATH ":" "${ + lib.makeBinPath ( + [ + python3Packages.python + mesa-demos + ] + ++ lib.optional x11Support xdpyinfo + ++ lib.optional sambaSupport samba + ) + }" \ + --prefix LD_LIBRARY_PATH ":" "${ + lib.makeLibraryPath ( + [ + curl + systemd + libmad + libcec + libcec_platform + libass + ] + ++ lib.optional vdpauSupport libvdpau + ++ lib.optional nfsSupport libnfs + ++ lib.optional rtmpSupport rtmpdump + ) + }" + done - wrapProgram $out/bin/kodi-send \ - --prefix PYTHONPATH : $out/${python3Packages.python.sitePackages} + wrapProgram $out/bin/kodi-send \ + --prefix PYTHONPATH : $out/${python3Packages.python.sitePackages} - substituteInPlace $out/share/xsessions/kodi.desktop \ - --replace kodi-standalone $out/bin/kodi-standalone - ''; + substituteInPlace $out/share/xsessions/kodi.desktop \ + --replace kodi-standalone $out/bin/kodi-standalone + ''; - doInstallCheck = true; + doInstallCheck = true; - installCheckPhase = "$out/bin/kodi --version"; + installCheckPhase = "$out/bin/kodi --version"; - passthru = { - pythonPackages = python3Packages; - ffmpeg = ffmpeg; - kodi = finalAttrs.finalPackage; - }; + passthru = { + pythonPackages = python3Packages; + ffmpeg = ffmpeg; + kodi = finalAttrs.finalPackage; + }; - meta = with lib; { - description = "Media center"; - homepage = "https://kodi.tv/"; - license = licenses.gpl2Plus; - platforms = platforms.linux; - teams = [ teams.kodi ]; - mainProgram = "kodi"; - }; -}) + meta = with lib; { + description = "Media center"; + homepage = "https://kodi.tv/"; + license = licenses.gpl2Plus; + platforms = platforms.linux; + teams = [ teams.kodi ]; + mainProgram = "kodi"; + }; + } +)