我的 Linux 内核是否已应用补丁?

我的 Linux 内核是否已应用补丁?

我即将安装补丁对于名为兼容无线为了解决我的 WiFi 通道问题(它锁定不存在的 -1 通道)Ubuntu Linux v12.04卡利Linux v1.0.9

但首先我想知道这个补丁是否已经安装了(为什么要安装我已有的东西?)。

我已经做了一些研究,但我找不到一种方法来知道我的补丁是否已经存在,也找不到列出已安装补丁的通用方法。我什至不知道是否有可能的或者不从正在运行的 Linux 获取此类信息。

有什么想法吗?

答案1

我的 Linux 内核是否已应用补丁?

如果一个人对 Linux 足够熟悉,可以应用补丁(正如提问者所表现的那样),那么检查补丁是否已经在默认内核中就相对简单:只需检查源代码即可。

使用来源,卢克!

以下内容应该适用于任何源自 Debian GNU/Linux 的发行版,其中包括提问者要求的 Ubuntu:

apt source linux

这将下载 Linux 源代码并将其修补为与编译时使用的发行版完全相同的状态。 linux-xyz 目录中包含补丁中提到的文件。只需查看行号并确保不存在带减号的行而存在带加号的行。就是这样。

更详细的答案

补丁是如下所示的文本文件:

Signed-off-by: Alexey Brodkin <[email protected]>
---
 drivers/usb/core/urb.c | 5 -----
 1 file changed, 5 deletions(-)

--- a/drivers/usb/core/urb.c
+++ b/drivers/usb/core/urb.c
@@ -321,9 +321,6 @@ EXPORT_SYMBOL_GPL(usb_unanchor_urb);
  */
 int usb_submit_urb(struct urb *urb, gfp_t mem_flags)
 {
-   static int          pipetypes[4] = {
-       PIPE_CONTROL, PIPE_ISOCHRONOUS, PIPE_BULK, PIPE_INTERRUPT
-   };
    int             xfertype, max;
    struct usb_device       *dev;
    struct usb_host_endpoint    *ep;
@@ -441,11 +438,6 @@ int usb_submit_urb(struct urb *urb, gfp_
     * cause problems in HCDs if they get it wrong.
     */

-   /* Check that the pipe's type matches the endpoint's type */
-   if (usb_pipetype(urb->pipe) != pipetypes[xfertype])
-       dev_WARN(&dev->dev, "BOGUS urb xfer, pipe %x != type %x\n",
-           usb_pipetype(urb->pipe), pipetypes[xfertype]);
-
    /* Check against a simple/standard policy */
    allowed = (URB_NO_TRANSFER_DMA_MAP | URB_NO_INTERRUPT | URB_DIR_MASK |
            URB_FREE_BUFFER);

通常,人们会patch在编译之前使用该程序将补丁文件应用于源代码,但对于这个问题,可能不值得这么麻烦。人们可以快速浏览补丁文件并查看顶部的文件名和行号,然后在其中打开文本编辑器(在本例中为emacs +321 drivers/usb/core/urb.c)。快速浏览一下就可以知道。 (减号标记应删除的行,加号标记应添加的行)。

但是,也许跑步是个好主意patch

另一方面,如果计划重新编译 Linux,从发行版的默认内核开始并不是一个坏主意。在这种情况下,没有理由不尝试运行patch.该程序足够智能,可以识别补丁是否已经应用,并询问操作员是否想要撤消补丁。

运行补丁的示例(之前未打补丁)

以下是不在默认内核中的补丁上的示例:

$ patch -p1 < foo.patch
patching file drivers/usb/core/urb.c
Hunk #1 succeeded at 323 (offset 2 lines).
Hunk #2 succeeded at 440 (offset 2 lines).

如果成功,则发行版的默认设置未修补,需要重新编译。幸运的是,Linux 源代码现在就在那里,并且应用了补丁。

运行补丁的示例(之前打过补丁)

如果发行版的默认内核已经被修补,情况如下:

$ patch -p1 < foo.patch
patching file drivers/usb/core/urb.c
Reversed (or previously applied) patch detected!  Assume -R? [n] 
Apply anyway? [n] 
Skipping patch.
2 out of 2 hunks ignored -- saving rejects to file drivers/usb/core/urb.c.rej

“反转或先前应用”意味着无需执行任何其他操作,因为默认内核已修补。


脚注 1抱歉,我用了不好的双关语,但不要因此责怪我;这是很久很久以前 UNIX 大师以源头之道明智地教导我的鼓励。他们说,当源头与你同在时,你将变得比任何专有供应商想象的更强大。

答案2

Linux 不是 Windows,因此“补丁”实际上是在源代码修改后从基本代码完全重新编译/重新加载并作为包分发的。因此,在不下载源代码并检查特定源代码更改的情况下,很难知道某些特定更改是否已合并到二进制文件中。

版本也不总是有帮助。例如,RedHat 将源代码更改向后移植到较旧但受支持的应用程序版本,并重新发布包,仅更改内部版本号而不更改版本。因此,在 RedHat 中,您无法完全确定开发人员发布新子版本时所做的更改是否尚未向后移植到他们重新发布的模块之一。这种东西让我发疯。

最后,请记住,Linux 有多个发行版,它们具有不同的包管理、版本控制和支持方法。

总之,要绝对确定源代码更改已实施,您必须转到您正在使用的特定发行版的特定包的源代码。

答案3

就您的具体情况而言,你的链接是从 2012 年开始的,讨论的是 Ubuntu 版本 11.10 及更早版本。

里面提到compat-wireless-3.0-rc4-1.tar.bz2的好像已经不能下载了;我认为内容本质上是内核版本 3.0-rc4 的无线驱动程序,适合安装到比该版本更旧的内核。您的 Ubuntu 12.04 具有 3.2 或更高版本的内核版本;这个包将是一个降级为你。 Kali 1.0.9 于 2014 年发布,可能有更新的内核版本。

通道-1补丁您的链接中提到的仅修改<kernel source root>/net/wireless/chan.c文件中的 6 行,并且不会更改任何内核模块固件版本。因此,除了下载当前安装的内核的内核源代码包并查看该源代码文件之外,没有简单的方法可以确定补丁是否已安装。

但我可以去https://www.kernel.org并浏览那里的代码而不下载它。目前最旧的长期支持内核是 3.2.98:查看其.../net/wireless/chan.c文件,补丁似乎不存在:虽然行号与补丁的内容相差约 30 行,但函数的结构cfg80211_set_freq()仍然是本质上是相同的,因此理论上可以将该补丁应用于“vanilla”3.2。系列内核。

下一个长期内核此时是3.16.53版本:当我查看它的.../net/wireless/chan.c文件时,我发现它已经被彻底修改了:补丁修改的功能cfg80211_set_freq()根本不存在了。无法按原样将通道 -1 补丁安装到此版本:您必须了解新代码,查明该补丁是否仍然适用,并应用补丁中列出的更改的等效版本如有必要,转移到适当的新位置。

这只是“香草”标准内核。 Ubuntu 或 Kali 可能已自行在标准内核上应用了更多补丁。

相关内容