Clone of https://github.com/NixOS/nixpkgs.git (to stress-test knotserver)
1{
2 cudaVersion,
3 runPatches ? [ ],
4 autoPatchelfHook,
5 autoAddDriverRunpath,
6 addDriverRunpath,
7 alsa-lib,
8 curlMinimal,
9 expat,
10 fetchurl,
11 fontconfig,
12 freetype,
13 gdk-pixbuf,
14 glib,
15 glibc,
16 gst_all_1,
17 gtk2,
18 lib,
19 libxkbcommon,
20 libkrb5,
21 krb5,
22 makeWrapper,
23 markForCudatoolkitRootHook,
24 ncurses5,
25 numactl,
26 nss,
27 patchelf,
28 perl,
29 python3, # FIXME: CUDAToolkit 10 may still need python27
30 pulseaudio,
31 setupCudaHook,
32 stdenv,
33 backendStdenv, # E.g. gcc11Stdenv, set in extension.nix
34 unixODBC,
35 wayland,
36 xorg,
37 zlib,
38 libglut,
39 libGLU,
40 libsForQt5,
41 libtiff,
42 qt6Packages,
43 qt6,
44 rdma-core,
45 ucx,
46 rsync,
47 libglvnd,
48}:
49
50let
51 # Version info for the classic cudatoolkit packages that contain everything that is in redist.
52 releases = builtins.import ./releases.nix;
53 release = releases.${cudaVersion};
54in
55
56backendStdenv.mkDerivation rec {
57 pname = "cudatoolkit";
58 inherit (release) version;
59 inherit runPatches;
60
61 dontPatchELF = true;
62 dontStrip = true;
63
64 src = fetchurl { inherit (release) url sha256; };
65
66 outputs = [
67 "out"
68 "lib"
69 "doc"
70 ];
71
72 nativeBuildInputs =
73 [
74 perl
75 makeWrapper
76 rsync
77 addDriverRunpath
78 autoPatchelfHook
79 autoAddDriverRunpath
80 markForCudatoolkitRootHook
81 ]
82 ++ lib.optionals (lib.versionOlder version "11") [ libsForQt5.wrapQtAppsHook ]
83 ++ lib.optionals (lib.versionAtLeast version "11.8") [ qt6Packages.wrapQtAppsHook ];
84 propagatedBuildInputs = [ setupCudaHook ];
85 buildInputs =
86 lib.optionals (lib.versionOlder version "11") [
87 libsForQt5.qt5.qtwebengine
88 libglut
89 libGLU
90 ]
91 ++ [
92 # To get $GDK_PIXBUF_MODULE_FILE via setup-hook
93 gdk-pixbuf
94
95 # For autoPatchelf
96 ncurses5
97 expat
98 python3
99 zlib
100 glibc
101 xorg.libX11
102 xorg.libXext
103 xorg.libXrender
104 xorg.libXt
105 xorg.libXtst
106 xorg.libXi
107 xorg.libXext
108 xorg.libXdamage
109 xorg.libxcb
110 xorg.xcbutilimage
111 xorg.xcbutilrenderutil
112 xorg.xcbutilwm
113 xorg.xcbutilkeysyms
114 pulseaudio
115 libxkbcommon
116 libkrb5
117 krb5
118 gtk2
119 glib
120 fontconfig
121 freetype
122 numactl
123 nss
124 unixODBC
125 alsa-lib
126 wayland
127 libglvnd
128 ]
129 ++ lib.optionals (lib.versionAtLeast version "11.8") [
130 (lib.getLib libtiff)
131 qt6Packages.qtwayland
132 rdma-core
133 (ucx.override { enableCuda = false; }) # Avoid infinite recursion
134 xorg.libxshmfence
135 xorg.libxkbfile
136 ]
137 ++ (lib.optionals (lib.versionAtLeast version "12") (
138 map lib.getLib ([
139 # Used by `/target-linux-x64/CollectX/clx` and `/target-linux-x64/CollectX/libclx_api.so` for:
140 # - `libcurl.so.4`
141 curlMinimal
142
143 # Used by `/host-linux-x64/Scripts/WebRTCContainer/setup/neko/server/bin/neko`
144 gst_all_1.gstreamer
145 gst_all_1.gst-plugins-base
146 ])
147 ++ (with qt6; [
148 qtmultimedia
149 qttools
150 qtpositioning
151 qtscxml
152 qtsvg
153 qtwebchannel
154 qtwebengine
155 ])
156 ));
157
158 # Prepended to runpaths by autoPatchelf.
159 # The order inherited from older rpath preFixup code
160 runtimeDependencies = [
161 (placeholder "lib")
162 (placeholder "out")
163 "${placeholder "out"}/nvvm"
164 # NOTE: use the same libstdc++ as the rest of nixpkgs, not from backendStdenv
165 "${lib.getLib stdenv.cc.cc}/lib64"
166 "${placeholder "out"}/jre/lib/amd64/jli"
167 "${placeholder "out"}/lib64"
168 "${placeholder "out"}/nvvm/lib64"
169 ];
170
171 autoPatchelfIgnoreMissingDeps =
172 [
173 # This is the hardware-dependent userspace driver that comes from
174 # nvidia_x11 package. It must be deployed at runtime in
175 # /run/opengl-driver/lib or pointed at by LD_LIBRARY_PATH variable, rather
176 # than pinned in runpath
177 "libcuda.so.1"
178
179 # The krb5 expression ships libcom_err.so.3 but cudatoolkit asks for the
180 # older
181 # This dependency is asked for by target-linux-x64/CollectX/RedHat/x86_64/libssl.so.10
182 # - do we even want to use nvidia-shipped libssl?
183 "libcom_err.so.2"
184 ]
185 ++ lib.optionals (lib.versionOlder version "10.1") [
186 # For Cuda 10.0, nVidia also shipped a jre implementation which needed
187 # two old versions of ffmpeg which are not available in nixpkgs
188 "libavcodec.so.54"
189 "libavcodec.so.53"
190 "libavformat.so.54"
191 "libavformat.so.53"
192 ];
193
194 preFixup =
195 if (lib.versionAtLeast version "10.1" && lib.versionOlder version "11") then
196 ''
197 ${lib.getExe' patchelf "patchelf"} $out/targets/*/lib/libnvrtc.so --add-needed libnvrtc-builtins.so
198 ''
199 else
200 ''
201 ${lib.getExe' patchelf "patchelf"} $out/lib64/libnvrtc.so --add-needed libnvrtc-builtins.so
202 '';
203
204 unpackPhase = ''
205 sh $src --keep --noexec
206
207 ${lib.optionalString (lib.versionOlder version "10.1") ''
208 cd pkg/run_files
209 sh cuda-linux*.run --keep --noexec
210 sh cuda-samples*.run --keep --noexec
211 mv pkg ../../$(basename $src)
212 cd ../..
213 rm -rf pkg
214
215 for patch in $runPatches; do
216 sh $patch --keep --noexec
217 mv pkg $(basename $patch)
218 done
219 ''}
220 '';
221
222 installPhase =
223 ''
224 runHook preInstall
225 mkdir $out
226 ${lib.optionalString (lib.versionOlder version "10.1") ''
227 cd $(basename $src)
228 export PERL5LIB=.
229 perl ./install-linux.pl --prefix="$out"
230 cd ..
231 for patch in $runPatches; do
232 cd $(basename $patch)
233 perl ./install_patch.pl --silent --accept-eula --installdir="$out"
234 cd ..
235 done
236 ''}
237 ${lib.optionalString (lib.versionAtLeast version "10.1" && lib.versionOlder version "11") ''
238 cd pkg/builds/cuda-toolkit
239 mv * $out/
240 rm -f $out/nsight-systems-*/host-linux-x64/libstdc++.so*
241 ''}
242 ${lib.optionalString (lib.versionAtLeast version "11") ''
243 mkdir -p $out/bin $out/lib64 $out/include $doc
244 for dir in pkg/builds/* pkg/builds/cuda_nvcc/nvvm pkg/builds/cuda_cupti/extras/CUPTI; do
245 if [ -d $dir/bin ]; then
246 mv $dir/bin/* $out/bin
247 fi
248 if [ -d $dir/doc ]; then
249 (cd $dir/doc && find . -type d -exec mkdir -p $doc/\{} \;)
250 (cd $dir/doc && find . \( -type f -o -type l \) -exec mv \{} $doc/\{} \;)
251 fi
252 if [ -L $dir/include ] || [ -d $dir/include ]; then
253 (cd $dir/include && find . -type d -exec mkdir -p $out/include/\{} \;)
254 (cd $dir/include && find . \( -type f -o -type l \) -exec mv \{} $out/include/\{} \;)
255 fi
256 if [ -L $dir/lib64 ] || [ -d $dir/lib64 ]; then
257 (cd $dir/lib64 && find . -type d -exec mkdir -p $out/lib64/\{} \;)
258 (cd $dir/lib64 && find . \( -type f -o -type l \) -exec mv \{} $out/lib64/\{} \;)
259 fi
260 done
261 mv pkg/builds/cuda_nvcc/nvvm $out/nvvm
262
263 mv pkg/builds/cuda_sanitizer_api $out/cuda_sanitizer_api
264 ln -s $out/cuda_sanitizer_api/compute-sanitizer/compute-sanitizer $out/bin/compute-sanitizer
265
266 mv pkg/builds/nsight_systems/target-linux-x64 $out/target-linux-x64
267 mv pkg/builds/nsight_systems/host-linux-x64 $out/host-linux-x64
268 rm $out/host-linux-x64/libstdc++.so*
269 ''}
270 ${
271 lib.optionalString (lib.versionAtLeast version "11.8" && lib.versionOlder version "12")
272 # error: auto-patchelf could not satisfy dependency libtiff.so.5 wanted by /nix/store/.......-cudatoolkit-12.0.1/host-linux-x64/Plugins/imageformats/libqtiff.so
273 # we only ship libtiff.so.6, so let's use qt plugins built by Nix.
274 # TODO: don't copy, come up with a symlink-based "merge"
275 ''
276 rsync ${lib.getLib qt6Packages.qtimageformats}/lib/qt-6/plugins/ $out/host-linux-x64/Plugins/ -aP
277 ''
278 }
279 ${
280 lib.optionalString (lib.versionAtLeast version "12")
281 # Use Qt plugins built by Nix.
282 ''
283 for qtlib in $out/host-linux-x64/Plugins/*/libq*.so; do
284 qtdir=$(basename $(dirname $qtlib))
285 filename=$(basename $qtlib)
286 for qtpkgdir in ${
287 lib.concatMapStringsSep " " (x: qt6Packages.${x}) [
288 "qtbase"
289 "qtimageformats"
290 "qtsvg"
291 "qtwayland"
292 ]
293 }; do
294 if [ -e $qtpkgdir/lib/qt-6/plugins/$qtdir/$filename ]; then
295 ln -snf $qtpkgdir/lib/qt-6/plugins/$qtdir/$filename $qtlib
296 fi
297 done
298 done
299 ''
300 }
301
302 rm -f $out/tools/CUDA_Occupancy_Calculator.xls # FIXME: why?
303
304 ${lib.optionalString (lib.versionOlder version "10.1") ''
305 # let's remove the 32-bit libraries, they confuse the lib64->lib mover
306 rm -rf $out/lib
307 ''}
308
309 ${lib.optionalString (lib.versionAtLeast version "12.0") ''
310 rm $out/host-linux-x64/libQt6*
311 ''}
312
313 # Remove some cruft.
314 ${lib.optionalString (
315 (lib.versionAtLeast version "7.0") && (lib.versionOlder version "10.1")
316 ) "rm $out/bin/uninstall*"}
317
318 # Fixup path to samples (needed for cuda 6.5 or else nsight will not find them)
319 if [ -d "$out"/cuda-samples ]; then
320 mv "$out"/cuda-samples "$out"/samples
321 fi
322
323 # Change the #error on GCC > 4.9 to a #warning.
324 sed -i $out/include/host_config.h -e 's/#error\(.*unsupported GNU version\)/#warning\1/'
325
326 # Fix builds with newer glibc version
327 sed -i "1 i#define _BITS_FLOATN_H" "$out/include/host_defines.h"
328 ''
329 +
330 # Point NVCC at a compatible compiler
331 # CUDA_TOOLKIT_ROOT_DIR is legacy,
332 # Cf. https://cmake.org/cmake/help/latest/module/FindCUDA.html#input-variables
333 ''
334 mkdir -p $out/nix-support
335 cat <<EOF >> $out/nix-support/setup-hook
336 cmakeFlags+=' -DCUDA_TOOLKIT_ROOT_DIR=$out'
337 EOF
338
339 # Move some libraries to the lib output so that programs that
340 # depend on them don't pull in this entire monstrosity.
341 mkdir -p $lib/lib
342 mv -v $out/lib64/libcudart* $lib/lib/
343
344 # Remove OpenCL libraries as they are provided by ocl-icd and driver.
345 rm -f $out/lib64/libOpenCL*
346 ${lib.optionalString (lib.versionAtLeast version "10.1" && (lib.versionOlder version "11")) ''
347 mv $out/lib64 $out/lib
348 mv $out/extras/CUPTI/lib64/libcupti* $out/lib
349 ''}
350
351 # nvprof do not find any program to profile if LD_LIBRARY_PATH is not set
352 wrapProgram $out/bin/nvprof \
353 --prefix LD_LIBRARY_PATH : $out/lib
354 ''
355 + lib.optionalString (lib.versionOlder version "8.0") ''
356 # Hack to fix building against recent Glibc/GCC.
357 echo "NIX_CFLAGS_COMPILE+=' -D_FORCE_INLINES'" >> $out/nix-support/setup-hook
358 ''
359 # 11.8 includes a broken symlink, include/include, pointing to targets/x86_64-linux/include
360 + lib.optionalString (lib.versions.majorMinor version == "11.8") ''
361 rm $out/include/include
362 ''
363 + ''
364 runHook postInstall
365 '';
366
367 postInstall = ''
368 for b in nvvp ${lib.optionalString (lib.versionOlder version "11") "nsight"}; do
369 wrapProgram "$out/bin/$b" \
370 --set GDK_PIXBUF_MODULE_FILE "$GDK_PIXBUF_MODULE_FILE"
371 done
372 ${lib.optionalString (lib.versionAtLeast version "12")
373 # Check we don't have any lurking vendored qt libraries that weren't
374 # replaced during installPhase
375 ''
376 qtlibfiles=$(find $out -name "libq*.so" -type f)
377 if [ ! -z "$qtlibfiles" ]; then
378 echo "Found unexpected vendored Qt library files in $out" >&2
379 echo $qtlibfiles >&2
380 echo "These should be replaced with symlinks in installPhase" >&2
381 exit 1
382 fi
383 ''
384 }
385 '';
386
387 # cuda-gdb doesn't run correctly when not using sandboxing, so
388 # temporarily disabling the install check. This should be set to true
389 # when we figure out how to get `cuda-gdb --version` to run correctly
390 # when not using sandboxing.
391 doInstallCheck = false;
392 postInstallCheck = ''
393 # Smoke test binaries
394 pushd $out/bin
395 for f in *; do
396 case $f in
397 crt) continue;;
398 nvcc.profile) continue;;
399 nsight_ee_plugins_manage.sh) continue;;
400 uninstall_cuda_toolkit_6.5.pl) continue;;
401 computeprof|nvvp|nsight) continue;; # GUIs don't feature "--version"
402 *) echo "Executing '$f --version':"; ./$f --version;;
403 esac
404 done
405 popd
406 '';
407 passthru = {
408 inherit (backendStdenv) cc;
409 majorMinorVersion = lib.versions.majorMinor version;
410 majorVersion = lib.versions.majorMinor version;
411 };
412
413 meta = with lib; {
414 description = "Deprecated runfile-based CUDAToolkit installation (a compiler for NVIDIA GPUs, math libraries, and tools)";
415 homepage = "https://developer.nvidia.com/cuda-toolkit";
416 platforms = [ "x86_64-linux" ];
417 license = licenses.nvidiaCuda;
418 maintainers = teams.cuda.members;
419 };
420}