如何在Alpine Linux中安装最小的CUDA驱动文件

7
我想在Alpine Linux上安装最小的CUDA运行时文件,并创建比Nvidia官方提供的CUDA更小的Docker基础映像。正如通常一样,Nvidia官方版本非常庞大。在Docker构建过程中,如何获取这些运行时文件而不是拉取整个CUDA 8工具包?

我不是很了解CUDA。这个有用吗?https://hub.docker.com/r/nvidia/cuda/ - Robert
1
@Robert - 不是真的。他们做的就是下载一个包含完整工具包并使结果臃肿的大型安装文件。令人沮丧的是,NVIDIA希望您安装如此多的垃圾软件。在我看来,他们真的没有考虑部署问题。 - hookenz
哦,我现在明白了。你知道你需要从那张图片中精确获取什么吗?有选择性地说。你可以使用 Docker 多阶段构建来仅保留你从给定的先前图像中所需的内容。(使用多个 FROM 的 Dockerfile) - Robert
@Robert - 我的目标是获得一个相对较小的最终图像。理论上,我可以只复制共享对象,但这有点混乱。我希望能够下载驱动程序并提取所需的最小内容。我想创建一个易于维护的东西。 - hookenz
我投票关闭此问题,因为它不属于编程问题,而是应该在unix.stackexchange.com上发布。 - einpoklum
5个回答

1

我无法确定是否需要其他文件。然而,Nvidia驱动程序是使用glibc编译的,而alpine使用musl来保持其小巧的占用空间。你可能需要nvidia驱动程序的源代码,以便使用musl重新编译它,或者使用实现了glibc的alpine基础镜像,例如这个。我还没有尝试过使用这个,但我已经成功地在alpine 3.8容器上使用muslgcc/make编译了libcudacore。我还没有能够完全编译整个Nvidia/Cuda工具包。当我有更多时间时,我将尝试进一步测试。


Nvidia/Cuda在musl编译方面有任何进展吗? - chatzich
很抱歉,这个项目因为我团队上其他更高优先级的事项而被搁置了。对不起,朋友们。 - ThisGuyCantEven

1
实际情况是,Alpine Linux Musl或其libc端口不支持Nvidia/CUDA,并且即使您在alchemist尝试中成功,您最终仍将得到一个不稳定的映像。 Nvidia驱动程序和CUDA工具包是非常复杂的系统,老实说我看不出为什么要为不受支持的系统库或libc的不支持的端口自行编译它们,即使它们编译成功,所有意外情况也可能发生。使用Debian的slim镜像或Ubuntu minimal并手动安装官方支持文件,这是您可以做的最小化操作。或者更好地使用大小为“huge”的Nvidia DockerHub映像(基于Ubuntu LTS)。
总之,除了这个问题之外,Nvidia DockerHub是最佳选择,它们由CUDA Toolkit本身的创建者支持,而且非常简单易用。如果您想挑剔一点,请前往他们的Gitlab存储库以手动构建Debian/Ubuntu,非常容易快速完成。
是的,Nvidia DockerHub映像占用1-2个Gig的空间,但通常只需下载一次,因为您将映像用作基础,如果只添加您的代码,则仅需要频繁拉动/推送通常较小的几十Mbi的代码层,而不是整个映像,所以老实说,我看不出人们为什么会如此关注映像大小,小是更好的,毫无疑问,但在实际需要方面花费宝贵的时间要好得多。

1
小图像的使用案例是为了让开发人员快速将图像加载到内存中,因此小图像确实有其优点。然而,在大多数CUDA用例中,您要么在K8s集群中提供DL模型,要么使用其他服务库进行编排。因此,没有任何理由使用阿尔卑斯Linux镜像。 - aarnphm
1
@AaronPham 没错。通常最好的方法是安装一组卡并为实际应用程序(小巧而简洁)提供接口来使用它。 - danius
现在已经过去了几年,但我确实成功地使用cuda获得了一个完全功能的版本。但是,我从未公开记录它,所以我无法准确告诉任何人我是如何做到的。唉! - hookenz

1

有人针对alpine-cuda提供了解决方案:

https://arto.s3.amazonaws.com/notes/cuda

Drivers

    https://developer.nvidia.com/vulkan-driver

$ lsmod | fgrep nvidia

$ nvidia-smi

Driver Installation

    https://us.download.nvidia.com/XFree86/Linux-x86_64/390.77/README/
    https://github.com/NVIDIA/nvidia-installer

Driver Installation on Alpine Linux

    https://github.com/sgerrand/alpine-pkg-glibc
    https://github.com/sgerrand/alpine-pkg-glibc/releases
    https://wiki.alpinelinux.org/wiki/Running_glibc_programs

$ apk add sudo bash ca-certificates wget xz make gcc linux-headers

$ wget -q -O /etc/apk/keys/sgerrand.rsa.pub https://raw.githubusercontent.com/sgerrand/alpine-pkg-glibc/master/sgerrand.rsa.pub

$ wget https://github.com/sgerrand/alpine-pkg-glibc/releases/download/2.27-r0/glibc-2.27-r0.apk
$ wget https://github.com/sgerrand/alpine-pkg-glibc/releases/download/2.27-r0/glibc-bin-2.27-r0.apk
$ wget https://github.com/sgerrand/alpine-pkg-glibc/releases/download/2.27-r0/glibc-dev-2.27-r0.apk
$ wget https://github.com/sgerrand/alpine-pkg-glibc/releases/download/2.27-r0/glibc-i18n-2.27-r0.apk

$ apk add glibc-2.27-r0.apk glibc-bin-2.27-r0.apk glibc-dev-2.27-r0.apk glibc-i18n-2.27-r0.apk

$ /usr/glibc-compat/bin/localedef -i en_US -f UTF-8 en_US.UTF-8

$ bash NVIDIA-Linux-x86_64-390.77.run --check

$ bash NVIDIA-Linux-x86_64-390.77.run --extract-only

$ cd NVIDIA-Linux-x86_64-390.77 && ./nvidia-installer

Driver Uninstallation

$ nvidia-uninstall

Driver Troubleshooting

    Uncompressing NVIDIA Accelerated Graphics Driver for Linux-x86_64 390.77NVIDIA-Linux-x86_64-390.77.run: line 998: /tmp/makeself.XXX/xz: No such file or directory\nExtraction failed.

    $ apk add xz  # Alpine Linux

    bash: ./nvidia-installer: No such file or directory

    Install the glibc compatibility layer package for Alpine Linux.

    ERROR: You do not appear to have libc header files installed on your system. Please install your distribution's libc development package.

    $ apk add musl-dev  # Alpine Linux

    ERROR: Unable to find the kernel source tree for the currently running kernel. Please make sure you have installed the kernel source files for your kernel and that they are properly configured

    $ apk add linux-vanilla-dev  # Alpine Linux

    ERROR: Failed to execute `/sbin/ldconfig`: The installer has encountered the following error during installation: 'Failed to execute `/sbin/ldconfig`'. Would you like to continue installation anyway?

    Continue installation.

Toolkit

    https://developer.nvidia.com/cuda-toolkit
    https://docs.nvidia.com/cuda/cuda-toolkit-release-notes/

Toolkit Download

    https://developer.nvidia.com/cuda-downloads?target_os=Linux&target_arch=x86_64&target_distro=Ubuntu&target_version=1604&target_type=runfilelocal

$ wget -c https://developer.nvidia.com/compute/cuda/9.2/Prod2/local_installers/cuda_9.2.148_396.37_linux

Toolkit Installation

    https://docs.nvidia.com/cuda/cuda-installation-guide-linux/

Toolkit Installation on Alpine Linux

$ apk add sudo bash

$ sudo bash cuda_9.2.148_396.37_linux

# You are attempting to install on an unsupported configuration. Do you wish to continue? y
# Install NVIDIA Accelerated Graphics Driver for Linux-x86_64 396.37? y
# Do you want to install the OpenGL libraries? y
# Do you want to run nvidia-xconfig? n
# Install the CUDA 9.2 Toolkit? y
# Enter Toolkit Location: /opt/cuda-9.2
# Do you want to install a symbolic link at /usr/local/cuda? y
# Install the CUDA 9.2 Samples? y
# Enter CUDA Samples Location: /opt/cuda-9.2/samples

$ sudo ln -s cuda-9.2 /opt/cuda

$ export PATH="/opt/cuda/bin:$PATH"

Toolkit Uninstallation

$ sudo /opt/cuda-9.2/bin/uninstall_cuda_9.2.pl

Toolkit Troubleshooting

    Cannot find termcap: Can't find a valid termcap file at /usr/share/perl5/core_perl/Term/ReadLine.pm line 377.

    $ export PERL_RL="Perl o=0"

    gcc: error trying to exec 'cc1plus': execvp: No such file or directory

    $ apk add g++  # Alpine Linux

    cicc: Relink `/usr/lib/libgcc_s.so.1' with `/usr/glibc-compat/lib/libc.so.6' for IFUNC symbol `memset'

    https://github.com/sgerrand/alpine-pkg-glibc/issues/58

    $ scp /lib/x86_64-linux-gnu/libgcc_s.so.1 root@alpine:/usr/glibc-compat/lib/libgcc_s.so.1

    $ sudo /usr/glibc-compat/sbin/ldconfig /usr/glibc-compat/lib /lib /usr/lib

Compiler

    https://docs.nvidia.com/cuda/cuda-compiler-driver-nvcc/

$ nvcc -V

-1
请定义您所说的“进入Alpine Linux”是什么意思。
无论您是直接在主机上运行工作负载还是在容器或chroot中运行,都需要在主机上安装整个NVidia驱动程序堆栈(包括Cuda libs、内核驱动程序等)。此外,内核和用户空间驱动程序是同一产品的两个方面,两者必须具有相同的版本。
这意味着:无论主机操作系统实际上是什么,它都必须是NVidia直接支持的那些操作系统之一。您必须使用NVidia为其专有/二进制驱动程序构建的确切内核版本(和配置)。使用不同的内核版本或以不同的配置重新编译内核可能会起作用,但这是危险的。即使使用正式支持的发行版,仍然存在风险,并且取决于月相或中国大米袋是否倒下。它通常有效,但当它不再有效时,您很可能没有希望了。

现在,当您将工作负载放入某些单独的操作系统映像中(例如chroot或容器)时,您还必须在该映像中安装相同的驱动程序包版本。使用容器或chroot的主要原因之一是隔离和解耦应用程序与主机操作系统(因此您不再需要将它们适配到主机操作系统中并独立进行升级,甚至可以拥有独立于主机操作系统的容器映像),但现在这个原因立即被取消了。主机和工作负载需要完全匹配。

简而言之:如果您想要一个CUDA工作负载,则主机操作系统以及工作负载映像(容器,chroot等)都需要支持它,并且它们都需要安装相同的驱动程序版本。否则就像玩俄罗斯轮盘一样危险。

由于有人提到了“nvidia-docker”。这会破坏Docker最初用于的安全隔离功能。(只需查看源代码,实际上可在GitHub上找到)。它只是一个更好的chroot。但是,主机和Docker映像仍然需要安装相同的驱动程序堆栈版本。

最后,我想问一下,您在这里的实际用例是什么。

警告:这可能适用于在完全不重要的家用计算机上玩游戏,但对于任何需要稳定性和安全性的专业事务都不适合。如果您受到某些数据安全/隐私法规(如GDPO)的约束,请远离此类驱动程序-您无法遵守这些专有驱动程序的法规。存在法律风险。

--mtx

补充说明:为什么专有内核驱动程序从未可靠地工作?简单回答:Linux内核从未为此而设计,因此不支持。

较长的回答:内核模块不是在某个隔离环境中执行的外部程序(例如用户空间程序)-它们(根据定义)是内核的组成部分,只有在需要时才会被惰性加载。(它们甚至不像共享库/DLL)。这意味着它们必须在二进制级别上完全适合您正在运行的内核的实际构建。编译内核时,有许多配置选项会以微妙的方式影响实际的内部二进制布局,例如启用/禁用某些功能可能会更改某些数据结构的布局,特定于CPU的优化可能会更改数据结构、调用约定、锁定机制等等。
而且这些东西也会从一个内核版本变化到另一个版本。例如,我们正在进行大量的内部重构(例如在数据结构、宏和内联函数中),之后相同的源代码片段将生成非常不同的二进制代码。
因此,任何内核模块都需要精确地为特定的内核映像编译(使用相同的配置选项、针对相同的包含文件、使用相同的编译器标志),否则您将面临可怕的故障,可能导致死机、安全漏洞、数据损坏甚至完全数据丢失。
你已经被警告了。

Docker容器运行Alpine Linux。我使用了Alpine的一部分,但最终改用了定制的Debian镜像。 - hookenz

-2

澄清一下,这只是驱动程序,不是CUDA。那是另一回事。

事实上,这比预期的要容易得多。我只是没有完全理解nvidia-docker项目的进展情况以及它是如何工作的。

基本上,从nvidia-docker项目下载并安装最新版本的nvidia-docker即可。

https://github.com/NVIDIA/nvidia-docker/releases

然后创建一个alpine Linux的Dockerfile。
FROM alpine:3.5
LABEL com.nvidia.volumes.needed="nvidia_driver"
ENV PATH /usr/local/nvidia/bin:/usr/local/cuda/bin:${PATH}
ENV LD_LIBRARY_PATH /usr/local/nvidia/lib:/usr/local/nvidia/lib64

RUN /bin/sh

开始构建。

docker build -t alpine-nvidia

运行

nvidia-docker run -ti --rm alpine-nvidia

请注意使用nvidia-docker cli而不是普通的docker cli。 nvidia-docker会使用额外的参数调用docker cli。

2
你能解释一下你是如何使用这个alpine镜像的吗? 你会在容器中安装cuda吗?我真的很困惑,因为我认为你需要在那里安装cuda才能运行任何东西。此外,由nvidia-docker挂载的卷在容器中提供了一个nvidia-smi文件,但它实际上并没有运行(我猜二进制文件没有为alpine编译)。这不是一个问题吗? - ldirer
这个项目有一段时间被搁置了。虽然它们可以运行,但存在一些其他无关的问题。具体情况可能因人而异。 - hookenz
1
我尝试了您提供的最小示例,但“nvidia-smi”拒绝在我的容器中运行。我理解您可能没有真正部署它,无论如何还是谢谢。 - ldirer
因为有一些东西缺失。nvidia-smi 可能是针对 stdc lib 编译的。Alpine 不使用它,而是使用另一个库。我并没有说不会有痛苦。 - hookenz
澄清一下,这只是驱动程序,不是CUDA。那是另外一个故事。 - hookenz
1
我之前走过这条路......并用musl编译了一些nvidia驱动程序。那个项目也被搁置了。现在不知怎么又发现自己在寻找这个功能。我会在这里发布当我找到的时候。 - ThisGuyCantEven

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接