如何在Linux中将补丁程序应用到文件(和创建补丁程序)

Linux补丁命令允许您快速、安全地将更改从一组文件传输到另一组文件。了解如何以简单的方式使用补丁。

patch和diff命令

假设您的计算机上有一个文本文件。您从其他人那里收到该文本文件的修改版本。如何将所有更改从修改后的文件快速传输到原始文件?这就是Patch和Diff发挥作用的地方。补丁和Diff可以在Linux和其他类似Unix的操作系统(如MacOS)中找到。

diff命令检查文件的两个不同版本,并列出它们之间的差异。这些差异可以存储在一个称为补丁文件的文件中。

使用补丁程序命令可以读取补丁文件,并将其内容用作一组指令。按照这些说明操作,修改后的文件中的更改将复制到原始文件中。

现在假设这个过程发生在整个文本文件目录上。一气呵成。这就是补丁的力量。

有时您不会收到修改后的文件。你得到的只是补丁文件。既然可以发送一个文件,为什么还要发送几十个文件,或者发布一个文件以便于下载呢?

您如何处理修补程序文件以实际修补您的文件?除了几乎是绕口令之外,这也是一个很好的问题。在这篇文章中,我们将向您介绍这一点。

patch命令最常由使用软件源代码文件的人使用,但它也同样适用于任何一组文本文件,无论其用途是不是源代码。

相关:如何在Linux终端中比较两个文本文件

我们的示例场景

在此场景中,我们位于一个名为work的目录中,该目录包含另外两个目录。一个叫工作,另一个叫最新。工作目录包含一组源代码文件。最新目录保存这些源代码文件的最新版本,其中一些已被修改。

为安全起见,工作目录是文本文件的当前版本的副本。这并不是它们的唯一副本。

查找文件的两个版本之间的差异

diff命令查找两个文件之间的差异。它的默认操作是在终端窗口中列出修改后的行。

其中一个文件名为slang.c。我们将工作目录中的版本与最新目录中的版本进行比较。

-u补丁(统一)选项告诉diff还列出每个更改部分之前和之后的一些未修改的文本行。这些行称为上下文行。它们帮助补丁命令精确定位必须在原始文件中进行更改的位置。

我们提供文件的名称,以便diff知道要比较哪些文件。首先列出原始文件,然后列出修改后的文件。下面是我们发出的diff命令:

diff -u working/slang.c latest/slang.c

diff生成一个输出列表,显示文件之间的差异。如果文件相同,则根本不会列出任何输出。从diff看到这种类型的输出,可以确认两个文件版本之间存在差异,并且原始文件需要打补丁。

制作修补程序文件

要在补丁文件中捕获这些差异,请使用以下命令。该命令与上面的命令相同,将diff的输出重定向到一个名为slang.patch的文件中。

diff -u working/slang.c latest/slang.c > slang.patch

补丁文件的名称是任意的。你可以叫它任何你喜欢的名字。给它一个“.patch”扩展名是个好主意;但是,因为它确实清楚地表明了它是什么类型的文件。

要使补丁作用于补丁文件并修改Working/slang.c文件,请使用以下命令。u(统一)选项让补丁程序知道补丁程序文件包含统一的上下文行。换句话说,我们将-u选项与diff一起使用,因此我们将-u选项与patch一起使用。

patch-u working.slang.c-i slang.patch

如果一切顺利,会有一行输出告诉您修补程序正在修补文件。

备份原始文件

我们可以使用-b(备份)选项指示Patch在更改修补文件之前对其进行备份。-i(输入)选项告诉补丁要使用的补丁文件的名称:

patch -u -b working.slang.c -i slang.patch

文件像以前一样打了补丁,输出没有明显差异。但是,如果您查看工作文件夹,您将看到名为slang.c.orig的文件已经创建。文件的日期和时间戳显示slang.c.orig是原始文件,slang.c是Patch创建的新文件。

对目录使用diff

我们可以使用diff创建一个补丁文件,该文件包含两个目录中文件之间的所有差异。然后,我们可以将该补丁文件与补丁一起使用,通过单个命令将这些差异应用于工作文件夹中的文件。

我们将与diff一起使用的选项是前面使用的-u(统一上下文)选项、使diff查看任何子目录的-r(递归)选项和-N(新文件)选项。

-N选项告诉diff如何处理最新目录中不在工作目录中的文件。它强制diff将指令放入补丁文件中,以便补丁创建在最新目录中存在但在工作目录中缺失的文件。

您可以将这些选项捆绑在一起,以便它们使用单个连字符(-)。

请注意,我们仅提供目录名,而不是告诉diff查看特定文件:

diff -ruN working/ latest/ > slang.patch

窥探修补程序文件内部

让我们快速查看一下补丁文件。我们将使用LESS来查看其内容。

文件的顶部显示了slang.c的两个版本之间的差异。

进一步向下滚动补丁文件,我们看到它描述了另一个名为structs.h的文件中的更改。这将验证补丁文件是否确实包含多个文件的不同版本之间的差异。

三思而后行

修补大量文件可能会让人有点不安,因此我们将使用--ry-run选项来检查是否一切正常,然后再冒险并承诺进行更改。

干运行选项告诉补丁执行除实际修改文件之外的所有操作。Patch将对文件执行所有的飞行前检查,如果遇到任何问题,它会报告这些问题。无论采用哪种方式,都不会修改任何文件。

如果没有报告任何问题,我们可以重复该命令,而不使用--ry-run选项,并自信地修补我们的文件。

-d(目录)选项告诉Patch要处理哪个目录。

注意,我们没有使用-i(输入)选项来告诉补丁哪个补丁文件包含来自diff的指令。相反,我们使用<将修补程序文件重定向到修补程序。

patch --dry-run -ruN -d working < slang.patch

在整个目录中,diff找到了两个要修补的文件。补丁程序已经检查了这两个文件的修改说明,没有报告任何问题。

飞行前的检查都没问题,我们已经准备好起飞了。

修补目录

要真正将补丁应用到文件,我们使用前面的命令,但不带--ry-run选项。

patch -ruN -d working < slang.patch

这一次,输出的每一行都不是以“检查”开头,而是每一行都以“修补”开头。

并且没有报告任何问题。我们可以编译我们的源代码,我们将使用软件的最新版本。

解决你们之间的分歧

这是迄今为止使用补丁最简单、最安全的方式。将目标文件复制到文件夹并修补该文件夹。当您对修补过程无误地完成感到高兴时,请将它们复制回去。

相关文章