为什么驱动程序要编译到内核中?为什么没有更多的驱动程序作为动态内核模块分发?

为什么驱动程序要编译到内核中?为什么没有更多的驱动程序作为动态内核模块分发?

我对 Linux 内核还是个新手,所以请原谅这个基本问题。如果您能给我指出我可以阅读/观看的资源,我将不胜感激。

对于 Windows,硬件驱动程序工作流程似乎是先安装核心操作系统,然后单独安装驱动程序。

对于 Linux,似乎所有驱动程序都直接编译到内核中 - 这是否意味着安装的 Linux 发行版支持所有受支持的硬件,即使您只使用其中的一个子集?

这是否意味着安装诸如专有 NVIDIA 驱动程序(不包含在内核中)之类的东西实际上需要使用 NVIDIA 驱动程序重新编译内核 - Ubuntu 和 Fedora 等发行版提供了内置驱动程序的预编译内核?

我最近在 Linux 安装上安装了一个驱动程序,增加了对 Xbox 无线适配器的支持。它使用“DKMS”将驱动程序添加到我的系统中,而不将其编译到内核中。

DKMS 是一种向 Linux 添加微内核功能的方法吗?为什么不是所有驱动程序都作为动态模块分发?内核模块安装在 下时不是已经是动态的了吗/ib/modules

动态内核模块如何影响自签名 Linux 安装上下文中的安全启动?

答案1

我认为您混淆了两个相关但不同的概念:内核如何使用驱动程序(静态编译,动态加载),以及它们是如何开发的(树内、树外)。

树内开发的驱动程序可以编译到内核中或动态加载。大多数都是动态加载的。从树中开发的驱动程序几乎总是会动态加载,因为它们不会出现在大多数发行版的内核源代码中,因此根本无法编译它们。如果您必须单独安装驱动程序,那么它是在内核外开发的。

驱动程序依赖于内核的许多内部API,据我了解,Linux 不关心这些 API 的向后兼容性。人们更喜欢干净的代码,而不是为了向后兼容(某种意义上)而维护古老的代码和现代代码的混乱。因此,他们更喜欢在树中拥有驱动程序 - 如果有人对 API 进行一些重构,他们也应该修复该 API 的任何用户,并且他们可以这样做,因为所有用户都在相同的源代码中。

当然,这对于树外驱动程序是无法完成的。因此,它们必须针对特定的内核版本进行编译,因为其他版本可能会破坏它们所依赖的 API。对于 NVIDIA(可能还有其他公司)来说,驱动程序基本上是一个封装了专有二进制文件的填充程序。 (填充程序支持多个内核版本。)这意味着对于发行版,您必须为每个打包的内核版本拥有一个驱动程序包。

DKMS是一种机制为了帮助此类树外内核 - DKMS 将为每个已安装的内核版本编译驱动程序,而不是为每个版本的内核打包一个版本的驱动程序。

相关内容