openSUSE:打包补丁指南
补丁生命周期
需要将补丁添加到软件包的原因有很多,补丁的生命周期定义良好非常重要。这有助于防止补丁“丢失”,并且没有人知道为什么以及何时将其删除。生命周期定义在以下简单步骤中
- 补丁添加到软件包
- 补丁回溯到软件包
- 补丁被修改(功能/重新应用)
- 补丁被禁用(但未删除)
- 补丁从软件包中删除
补丁生命周期的中间阶段是可选的,并非每个补丁都会经历这些阶段。
这些阶段中的任何一个都需要在 .changes 文件中提及,包括补丁的文件名。这仅是为了方便人工阅读,因此不需要采用严格的机器可解析格式;以下是一些建议格式的示例
- 添加 package-awesomeness.patch:使软件包变得出色
- 回溯 package-awesomeness.patch:从上游到 openSUSE,以修复 CVE 或添加新功能。
- 重新应用 package-awesomeness.patch:应用于新版本。
- 修改 package-awesomeness.patch:修复导入的错误或改进原始解决方案。
- 禁用 package-awesomeness.patch:测试用户是否可以没有出色功能
- 删除 package-awesomeness.patch:上游使其变得更加出色。
上游策略
为了定义上游策略,我们可以将补丁分为两类
- 上游 - 上游可能对此感兴趣
- openSUSE/SLE 特定 - 上游对此不感兴趣
上游补丁策略
如果您想添加一个可能对上游有兴趣的补丁,请注意,此补丁必须始终发送到上游。这是确保我们的修复程序集成到上游并可以在下一个上游版本中消除这些补丁的唯一方法。一个显著的优势是上游可以为您提供合理性检查和有关您补丁的宝贵反馈。
何时将补丁发送到上游
通常,在将补丁提交到 OBS 之前,最好先联系上游。如果您发现上游在补丁中发现错误,您可以避免重新提交补丁。此外,一些软件包维护者可能会要求在将补丁包含在 OBS 软件包中之前,先执行此“上游优先”策略。通常,应在这些软件包的 specfile 中提及“上游优先”策略(例如 SuSEfirewall)。但是,有时上游不够活跃,在提交补丁到 OBS 后发送给他们是唯一合理的途径。
如何找到上游
您需要挖掘。一个好的起点是检查 specfile 中的“Url”或“Source”标签,并访问上游网站。然后您需要找到上游首选的发送补丁的方式。例如,邮件、邮件列表、Bugzilla、git 等。
openSUSE/SLE 特定补丁策略
通常,我们尝试添加可以合并到上游的补丁。但是,可能会发生我们的软件包与上游不同,并且特定的补丁是唯一的解决方案。然后请注意,每个 openSUSE/SLE 特定的补丁都应正确记录,并说明为什么需要此特定修复。
补丁标记(也称为“标记补丁”)
为了便于使用自动工具(总有一天),并帮助告知未来的软件包处理者有关补丁的性质,我们为补丁存在以下类别
- 修复:这些是正常的修复,分为三类
- 修复 openSUSE 特定的内容,上游维护者对此不感兴趣。
- 修复 SLE 特定的内容,上游维护者对此不感兴趣,并且在 openSUSE 中不需要。
- 修复上游源代码,应将其上游化。
- 功能:添加到软件包的新功能,也分为三类
- openSUSE 特定的功能(例如,通过 /etc/sysconfig 切换显示管理器),上游维护者对此不感兴趣。
- SLE 特定的功能,上游维护者或 openSUSE 不感兴趣。
- 应上游化的功能。每当我们编写这种类型的新功能时,重要的是要与上游维护者协调。这样,我们可以开发出上游可以接受而无需更改的内容。完成功能后,要使其可被上游维护者接受,需要进行大量工作。因此,最好从一开始就确切知道上游维护者会期望什么。
有两种标准。
类型 1:spec 文件中的最简单行注释
最简格式是在 Patch 行上方的注释行中,包含补丁类别(见上文)、文件名(冗余)和行其余部分的自由格式字符串。由于单行不能容纳太多单词或其他元数据,请也查看下面的类型 2。
类型 1 格式示例
# PATCH-FIX-OPENSUSE fix-for-opensuse-specific-things.patch bsc#123456 Patch1: fix-for-opensuse-specific-things.patch # PATCH-FIX-SLE fix-for-sle-specific-things.patch bsc#123456 Patch2: fix-for-sle-specific-things.patch # PATCH-FIX-UPSTREAM fix-for-upstream-sources.patch bsc#123456 Patch3: fix-for-upstream-sources.patch # PATCH-FEATURE-OPENSUSE feature-for-opensuse-specific-things.patch bsc#123456 Patch4: feature-for-opensuse-specific-things.patch # PATCH-FEATURE-SLE feature-for-sle-specific-things.patch bsc#123456 Patch5: feature-for-sle-specific-things.patch # PATCH-FEATURE-UPSTREAM feature-for-upstream.patch bsc#123456 Patch6: feature-for-upstream.patch # PATCH-FIX-UPSTREAM fix-wayland-compatibility.patch -- based on commit abc123 Patch7: https://github.com/example/project/commit/abc123.patch # PATCH-FIX-UPSTREAM fix-wayland-compatibility.patch -- based on PR 123 Patch8: https://github.com/example/project/pull/132.patch
稍后在 %prep 部分
%autopatch -p1 ...
或者,如果并非所有补丁都适用 -p1
[...] %patch -P 1 -P 2 -P 3 -P 5 -p1 %patch -P 6 -p0 %patch -P 7 -p2
特殊情况:在使用 %patch 时:我们经常有暂时注释掉的补丁,因为它们不适用于最新的源代码,并且需要重新应用补丁。不要注释掉补丁的声明,而是注释掉其应用。在将补丁标记为需要重新应用时,保留其旧标签是一个好主意。
# PATCH-NEEDS-REBASE old-patch.patch bsc#123456 -- Does something old. Was: PATCH-FEATURE-OPENSUSE Patch7: old-patch.patch [...] # %patch -P 7
最后,我们包含电子邮件地址,以便稍后如果对补丁有疑问,可以更轻松地找到作者,并在“--”之后添加自由格式的注释。
即
# PATCH-{FIX|FEATURE}-{OPENSUSE|SLE|UPSTREAM} name-of-file.patch bsc#[0-9]+ you@example.com -- this patch makes things totally awesome
如果 SUSE 或其他 bugzilla 中有相关的错误,请添加它们,这将有助于我们获得更准确的信息。如果有两个或多个可用,则最好同时列出(或更多)。
通常,新补丁不需要 bugzilla 字段。对于将作为更新发布的已发布软件包,需要一个整体更新的 bugzilla 条目(BSC#)在 changes 文件中。如果合适,补丁描述也应包含它。
补丁字段的主要用例应该是对 上游 错误跟踪器的引用,对于 PATCH-*-UPSTREAM 补丁,此类补丁应首先提交到上游,然后在补丁标签中引用(最好包括 URL)。这有助于跟踪补丁,可以轻松确定在版本更新时上游是否在他们的 changelog 或发行说明中引用了哪些补丁仍然需要。当然,如果已经打开了相应的 bsc# 错误,也应引用它。
您可以在本文档末尾找到当前缩写集。如果需要,我们也可以稍后定义更多缩写。
有些补丁修复了未明确记录在任何地方的错误。在这种情况下,需要软件包处理者进行一些判断,但以下是一些想法
- 如果即将发布,请为其创建一个错误。这通常是必需的,即使不是,仍然是正确的事情。
- 如果发布还很遥远,并且错误已经在上游修复,请在注释中指出它已经在 SVN(或任何地方)中修复,并且当我们下次升级时补丁将消失。
类型 2:补丁中提供完整信息
类型 1 标准缺乏补丁最重要的部分:为什么需要或希望它,其单行格式很少足以传达所有所需的信息,并且补丁的状态(上游或 opensuse 特定的、修复或功能等)与实际补丁分离。
openSUSE 内核软件包中的补丁传统上使用一种将元数据直接附加到其所需位置(即补丁文件本身)的标记形式。这有助于将补丁提交到上游,因为描述不会被意外省略,并且 Git SCM(如果使用)知道在导入时保留元数据。相反,从 Git 仓库中提取补丁也会产生单个文件。
补丁文件应遵循 "key: value" 对和描述,可选地附带 diffstat,然后是实际的 hunk。示例。
From: Random J Developer <email@example.org> Date: 2012-07-28 01:28:22 +0200 Subject: input: add Acer Aspire 5710 to nomux blacklist References: bnc#404881 Upstream: submitted Acer Aspire needs to be added to nomux blacklist, otherwise the touchpad misbehaves. --- drivers/input/serio/i8042-x86ia64io.h | 7 +++++++ 1 file changed, 7 insertions(+) --- a/drivers/input/serio/i8042-x86ia64io.h +++ b/drivers/input/serio/i8042-x86ia64io.h @@ -371,6 +371,13 @@ static const struct dmi_system_id __init [...]
使用git format-patch -1获取最后一个提交的补丁文件。您需要手动添加缺少的键(Subject、References、Upstream)。
建议使用例如 Quilt,它可以保留刷新时的描述。quilt ref --sort --diffstat -p1创建/刷新此类补丁,排序,并采用所需的 -p1 格式。
遇到的常见字段
- From: 应指定补丁的原始作者的电子邮件地址。
- Date: 补丁首次创建的时间。最好使用带有时区的 ISO-8601 时间戳。如果刚刚创建了一个新补丁并且没有时间戳,可以使用 `stat your.patch` 确定时间戳。
- References: 链接到邮件列表帖子、bugzilla 等。没有固定格式,但 URL 更好,因为它们易于复制并粘贴到浏览器中。有关详细信息,请参阅下面的“#当前缩写集”。
- Upstream: 补丁的处置。没有固定格式,但常见的选项有“never”/“no”(openSUSE 特定的)、“to be done”(tbd)、“sent”/“submitted”(发送给上游开发人员;如果可能,请提供参考)、“merged”(上游已接受;如果可能,请提供参考)和“dead”(上游项目没有活动)。
- Subject: 补丁的简短单行摘要。
补丁应提供描述。 描述应说明 _为什么_ 需要它。尽可能详细,因为它会影响不同的开发人员在补丁不再适用时应该对补丁做什么。 “你执行了什么命令?”、“你观察到了什么?”、“你期望看到什么?”这三个问题可以提供一些指导。如果有一个相关的错误消息可用,例如在创建修复源代码文件中的语法错误的补丁时,该错误消息会导致编译中止,则应将其包含在内,并将其修剪为重要部分。此外,关于如何实现解决方案的摘要可以帮助读者理解更大的补丁。
在使用此格式时,建议也提供一个简短的类型 1 样式标记,这样无需检查每个补丁文件即可更轻松地查看补丁状态。
补丁命名
所有新补丁应以“.patch”扩展名结尾。
补丁名称是否应该以其应用包的名称开头是一个争论或风格问题。 如果不确定,请遵循您正在修改的包中使用的约定。
不要在Patch:行中使用%{version}宏,请手动指定版本。 使用该宏
- 会导致版本更新时大量重命名
- 容易忽略不再需要的补丁
- 难以确定补丁上次修改的时间
- 容易查明补丁破坏的时间(包考古学)
对此有一个例外:修复编译器由于错误代码而发出的警告的补丁通常命名为abuild.patch.
首选的补丁级别是-p1因为它使使用诸如quilt之类的工具进行导入更加简单。
当前缩写集
为了避免混淆和双重负担,允许引用其他问题跟踪器。 以下是一些常用问题跟踪器的快捷方式,应在问题 ID 的“#”之前添加。 请注意,快捷方式和问题 ID 之间没有空格。
注意:此列表不具有权威性,请检查 Open Build Service 如何在其中定义它们(osc api /issue_trackers)。 您也可以通过 OBS github 项目请求新的跟踪器。
| 快捷键 | 问题跟踪器 URL | 示例 |
|---|---|---|
| openSUSE Bug 跟踪器 | http://bugzilla.opensuse.org/show_bug.cgi?id=123456 | (boo#123456) |
| Boost | https://svn.boost.org/trac/boost/ | (boost#123456) |
| Clutter Project Bugzilla (已失效) | http://bugzilla.clutter-project.org/ | (bco#123) |
| CPAN 公共 Bug 跟踪器 | http://rt.cpan.org/Public/ | (RT#123456) |
| Debian | http://bugs.debian.org/ | (deb#123456) |
| Eclipse (只读,使用他们的 GitLab 或 GitHub 上的 org) | https://bugs.eclipse.org/bugs/ | (beo#123456) |
| Eclipse GitLab | https://gitlab.eclipse.org/eclipse/ | (geo#123456) |
| freedesktop.org (bugzilla) | http://bugs.freedesktop.org/ | (fdo#123456) |
| freedesktop.org (gitlab) | https://gitlab.freedesktop.org/ | (glfo#<project>/<repository>#123456) |
| GCC | http://gcc.gnu.org/bugzilla/ | (GCC#123456) |
| Github 问题跟踪器 | https://github.com/ | (gh#openSUSE/open-build-service#9395) gh#project/repository#issue |
| GNOME (已过时的 bugzilla) | https://bugzilla.gnome.org/ | (bgo#123456) |
| GNOME (gitlab) | https://gitlab.gnome.org/ | (glgo#GNOME/<project_name>#issue) 或 (glgo#GNOME/<project_name>!merge_request) |
| ICCULUS | http://bugzilla.icculus.org/ | (bio#123456) |
| Kernel 或 K | http://bugzilla.kernel.org/ | (bko#123456) |
| KDE | http://bugs.kde.org/ | (kde#123456) |
| Launchpad (Ubuntu) | https://bugs.launchpad.net/ | (lp#123456) |
| MeeGo (已失效) | http://bugs.meego.com | (MeeGo#123456) |
| Mozilla | http://bugzilla.mozilla.org/ | (bmo#123456) |
| Novell | https://bugzilla.novell.com/ | (bnc#123456) |
| SUSE 错误 | https://bugzilla.suse.com/ | (bsc#123456) |
| OpenLDAP | http://www.openldap.org/its/ | (ITS#123456) |
| OpenOffice.org Issuezilla (已过时) | http://qa.openoffice.org/issues/ (重定向到 https://bz.apache.org/ooo/) | (i#123456) |
| Fate (功能跟踪工具;功能失调) | https://fate.suse.com | (fate#123456) |
| RedHat | https://bugzilla.redhat.com/ | (rh#123456) |
| Samba (功能失调) | https://bugzilla.samba.org/ | (bso#123456) |
| Sourceforge (已过时,重定向) | http://sf.net/support/tracker.php?aid=1234567 | (sf#1234567); 数字在 URL 的“aid=”部分 |
| Sourceforge | https://sourceforge.net/p/project/bugs/48/ | (sf#project#1234567); 为每个项目使用单独的跟踪器 |
| Xamarin (已失效) | http://bugzilla.xamarin.com/ | (bxc#4321) |
| CVE 条目(请添加数字,即使有额外的 bugzilla) | http://cve.mitre.org | (CVE-2009-0067) |
| Xfce (只读,使用他们的 GitLab) | https://bugzilla.xfce.org/ | (bxo#123456) |
| Xfce GitLab | https://gitlab.xfce.org/ | (bxo#123456) |
| Bitbucket | https://bitbucket.org/owner/project/issues/1490 | (bt#owner/project#123456) |
| OBS GitHub Issues | https://api.github.com/repos/openSUSE/open-build-service/issues | (obs#123) |
| OBS 构建脚本 Issues | https://api.github.com/repos/openSUSE/obs-build/issues | (build#123) |
| OBS CLI Issues | https://api.github.com/repos/openSUSE/osc/issues | (osc#123) |
| Progress openSUSE issue | https://progress.opensuse.org/issues | (poo#123) |
| Linux Foundation | https://developerbugs.linux-foundation.org/ | (lf#1234) |
| Savannah GNU 项目 | https://debbugs.gnu.org/ | (sav#1234) |
| Savannah 非 GNU 项目 | https://savannah.nongnu.org/bugs/ | (savno#1234) |
| SUSE SLE 功能(应始终使用 epic id,而不是 dev task id) | https://jira.suse.com/ | (jsc#SLE-1234) |
| openSUSE Pagure | https://code.opensuse.org/ | (coo#leap/features#123) coo#<project_name>#issue 或另一种方式 code-o-o#<project_name>#issue |
对于其他问题 ID,请在补丁文件的开头使用指向相应问题跟踪器的完整 URL。 例如
实用程序 osurl 来自 https://git.sr.ht/~mcepl/vim-suse-changes 扩展这些缩写并使用您的浏览器打开它:
$ osurl bsc#1188001
(还有 abbrevURL 脚本,如果可能,会将 URL 转换为适当的缩写)