pacman
pacman 软件包管理器 是 Arch Linux 的主要区别特征之一。它将简单的二进制软件包格式与易于使用的 Arch 构建系统 相结合。pacman 的目标是使用户可以轻松管理软件包,无论是来自 官方仓库 还是用户自己的构建。
Pacman 通过将软件包列表与主服务器同步来保持系统更新。这种服务器/客户端模型还允许用户使用简单的命令下载/安装软件包,并完整地处理所有必需的依赖项。
Pacman 使用 C 编程语言编写,并使用 bsdtar(1) tar 格式进行打包。
pacman -Ql pacman pacman-contrib | grep -E 'bin/.+'
可以查看完整列表。用法
以下只是 pacman 可以执行的操作的一小部分示例。要阅读更多示例,请参阅 pacman(8)。
安装软件包
软件包是一个包含以下内容的归档文件
- 应用程序的所有(已编译)文件
- 有关应用程序的元数据,例如应用程序名称、版本、依赖项等。
- pacman 的安装文件和指令
Arch 的软件包管理器 pacman 可以安装、更新和移除这些软件包。使用软件包而不是自己编译和安装程序有多种好处
- 易于更新:pacman 会在更新可用时立即更新现有软件包
- 依赖项检查:pacman 为您处理依赖项,您只需指定程序,pacman 就会将其与所需的每个其他程序一起安装
- 干净的移除:pacman 具有软件包中每个文件的列表;这样,当您决定移除软件包时,不会意外地留下任何文件。
pacman -Sy package_name
而不是 pacman -Syu package_name
,因为这可能会导致依赖项问题。请参阅 系统维护#不支持部分升级 和 BBS#89328。安装特定的软件包
要安装单个软件包或软件包列表(包括依赖项),请发出以下命令
# pacman -S package_name1 package_name2 ...
要使用正则表达式安装软件包列表(请参阅 此论坛帖子)
# pacman -S $(pacman -Ssq package_regex)
有时,不同仓库(例如 extra 和 testing)中存在软件包的多个版本。要安装此示例中 extra 仓库的版本,需要在软件包名称前面定义仓库
# pacman -S extra/package_name
要安装名称中共享相似模式的多个软件包,可以使用花括号扩展。例如
# pacman -S plasma-{desktop,mediacenter,nm}
这可以扩展到所需的任意级别
# pacman -S plasma-{workspace{,-wallpapers},pa}
虚拟软件包
虚拟软件包是一种特殊的软件包,它本身不存在,而是由一个或多个其他软件包 提供 的。虚拟软件包允许其他软件包不将特定的软件包命名为依赖项,以防有多个候选软件包。虚拟软件包不能通过其名称安装,相反,当您安装提供虚拟软件包的软件包时,它们会被安装到您的系统中。一个例子是 dbus-units 软件包。
pacman.conf
中出现的顺序排序,然后在同一仓库中存在多个结果时按字母顺序排序。安装软件包组
某些软件包属于一个 软件包组,可以同时安装所有软件包。例如,发出命令
# pacman -S gnome
将提示您从 gnome 组中选择要安装的软件包。
有时,软件包组将包含大量软件包,并且可能只有少数几个您想要或不想要安装。与其输入除您不想要的软件包之外的所有数字,有时更方便使用以下语法选择或排除软件包或软件包范围
Enter a selection (default=all): 1-10 15
这将选择软件包 1 到 10 和 15 进行安装,或者
Enter a selection (default=all): ^5-8 ^2
这将选择除软件包 5 到 8 和 2 之外的所有软件包进行安装。
要查看 gnome 组中包含哪些软件包,请运行
$ pacman -Sg gnome
另请访问 https://archlinux.org.cn/groups/ 以查看有哪些软件包组可用。
--needed
选项覆盖此行为。移除软件包
要移除单个软件包,保留其所有已安装的依赖项
# pacman -R package_name
要移除软件包及其任何其他已安装软件包都不需要的依赖项
# pacman -Rs package_name
当移除包含其他需要的软件包的组时,上述命令有时会拒绝运行。在这种情况下,请尝试
# pacman -Rsu package_name
要移除软件包、其依赖项以及所有依赖于目标软件包的软件包
# pacman -Rsc package_name
要移除另一个软件包所需的软件包,而不移除依赖软件包
# pacman -Rdd package_name
移除某些应用程序时,Pacman 会保存重要的配置文件,并将它们命名为扩展名:.pacsave。要阻止创建这些备份文件,请使用 -n
选项
# pacman -Rn package_name
升级软件包
- 用户应遵循 系统维护#升级系统 部分中的指导定期升级系统,而不是盲目运行以下命令。
- Arch 仅支持完整系统升级。有关详细信息,请参阅 系统维护#不支持部分升级 和 #安装软件包。
Pacman 可以使用一个命令更新系统上的所有软件包。这可能需要相当长的时间,具体取决于系统的最新状态。以下命令同步仓库数据库并更新系统的软件包,排除配置仓库中没有的“本地”软件包
# pacman -Syu
查询软件包数据库
Pacman 使用 -Q
标志查询本地软件包数据库,使用 -S
标志查询同步数据库,使用 -F
标志查询文件数据库。有关每个标志的相应子选项,请参阅 pacman -Q --help
、pacman -S --help
和 pacman -F --help
。
# pacman -Fy
Pacman 可以在数据库中搜索软件包,同时搜索软件包的名称和描述
$ pacman -Ss string1 string2 ...
有时,-s
的内置 ERE(扩展正则表达式)可能会导致大量不需要的结果,因此必须将其限制为仅匹配软件包名称;而不是描述或任何其他字段
$ pacman -Ss '^vim-'
要搜索已安装的软件包
$ pacman -Qs string1 string2 ...
要在远程软件包中搜索软件包文件名
$ pacman -F string1 string2 ...
要显示有关给定软件包的详细信息(例如,其依赖项)
$ pacman -Si package_name
对于本地安装的软件包
$ pacman -Qi package_name
传递两个 -i
标志还将显示备份文件列表及其修改状态
$ pacman -Qii package_name
要检索软件包安装的文件列表
$ pacman -Ql package_name
要检索远程软件包安装的文件列表
$ pacman -Fl package_name
要验证软件包安装的文件的存在
$ pacman -Qk package_name
将 k
标志传递两次将执行更彻底的检查。
要查询数据库以了解文件系统中文件所属的软件包
$ pacman -Qo /path/to/file_name
要查询数据库以了解文件所属的远程软件包
$ pacman -F /path/to/file_name
要列出所有不再作为依赖项需要的软件包(孤立软件包)
$ pacman -Qdt
要列出所有显式安装且不需要作为依赖项的软件包
$ pacman -Qet
有关更多示例,请参阅 pacman/技巧和窍门。
对于高级功能,请安装 pkgfile,它使用一个单独的数据库,其中包含所有文件及其关联的软件包。
Pactree
要查看软件包的依赖树
$ pactree package_name
要查看软件包的被依赖树,请将反向标志 -r
传递给 pactree。
数据库结构
pacman 数据库通常位于 /var/lib/pacman/sync
。对于 /etc/pacman.conf
中指定的每个仓库,都将有一个对应的数据库文件位于此处。数据库文件是 gzipped tar 归档文件,其中包含每个软件包的一个目录,例如对于 which 软件包
$ tree which-2.21-5
which-2.21-5 |-- desc
desc
文件包含元数据,例如软件包描述、依赖项、文件大小和 MD5 哈希值。
清理软件包缓存
Pacman 将其下载的软件包存储在 /var/cache/pacman/pkg/
中,并且不会自动移除旧版本或已卸载的版本。这有一些优点
- 它允许 降级 软件包,而无需通过其他方式(例如 Arch Linux 归档)检索以前的版本。
- 可以轻松地直接从缓存目录重新安装已卸载的软件包,而无需从仓库重新下载。
但是,有必要定期清理缓存,以防止目录大小无限增长。
paccache(8) 脚本(在 pacman-contrib 软件包中提供)默认情况下会删除已安装和已卸载软件包的所有缓存版本,但最近的三个版本除外
# paccache -r
启用 和 启动 paccache.timer
以每周丢弃未使用的软件包。您可以在 /etc/conf.d/pacman-contrib
中配置服务的参数,例如,对于以下两个示例,使用 PACCACHE_ARGS='-k1'
或 PACCACHE_ARGS='-uk0'
。
您还可以定义要保留多少个最近的版本。要仅保留一个过去的版本,请使用
# paccache -rk1
添加 -u
/--uninstalled
开关以将 paccache 的操作限制为已卸载的软件包。例如,要移除已卸载软件包的所有缓存版本,请使用以下命令
# paccache -ruk0
有关更多选项,请参阅 paccache -h
。
Pacman 还有一些内置选项可以清理缓存和不再在配置文件 /etc/pacman.conf
中列出的仓库的剩余数据库文件。但是,pacman 不提供保留过去版本数量的可能性,因此比 paccache 默认选项更激进。
要移除所有未当前安装的缓存软件包和未使用的同步数据库,请执行
# pacman -Sc
要移除缓存中的所有文件,请使用两次 clean 开关,这是最激进的方法,并且缓存目录中将不留下任何内容
# pacman -Scc
pkgcachecleanAUR 和 pacleanerAUR 是清理缓存的另外两种替代方案。
附加命令
下载软件包而不安装它
# pacman -Sw package_name
安装一个不是来自远程仓库的“本地”软件包(例如,软件包来自 AUR)
# pacman -U /path/to/package/package_name-version.pkg.tar.zst
要在 pacman 的缓存中保留本地软件包的副本,请使用
# pacman -U file:///path/to/package/package_name-version.pkg.tar.zst
安装一个“远程”软件包(不是来自 pacman 配置文件中声明的仓库)
# pacman -U http://www.example.com/repo/example.pkg.tar.zst
空运行
Pacman 始终 列出要安装或移除的软件包,并在采取任何操作之前请求许可。
要获得可处理格式的列表,并阻止 -S
、-U
和 -R
的操作,您可以使用 -p
,这是 --print
的缩写。
可以添加 --print-format
以各种方式格式化此列表。--print-format %n
将返回不带软件包版本的列表。
安装理由
pacman 数据库根据安装理由将已安装的软件包组织成两组
- 显式安装:字面上通过通用 pacman
-S
或-U
命令传递的软件包; - 依赖项:尽管通常从未传递给 pacman 安装命令,但由于它们是显式安装的软件包 需要 的,因此隐式安装的软件包。
安装软件包时,可以使用以下命令强制将其安装理由设为依赖项
# pacman -S --asdeps package_name
该命令通常用于以下情况:显式安装的软件包可能提供 可选软件包,通常用于用户可自行决定的非必要功能。
--asdeps
安装可选依赖项将确保,如果您 移除孤立软件包,pacman 也会移除以此方式设置的可选软件包。但是,当重新安装软件包时,默认情况下会保留当前的安装理由。
可以使用 pacman -Qe
显示显式安装软件包的列表,而可以使用 pacman -Qd
显示依赖项的补充列表。
要更改已安装软件包的安装理由,请执行
# pacman -D --asdeps package_name
使用 --asexplicit
执行相反的操作。
--asdeps
和 --asexplicit
选项,例如使用 pacman -Syu package_name --asdeps
。这将不仅更改正在安装的软件包的安装理由,还会更改正在升级的软件包的安装理由。软件包安装/升级/移除期间发生了什么
成功时,事务的工作流程遵循五个高级步骤以及事务前/后钩子
- 如果没有数据库锁,则初始化事务。
- 选择将在事务中添加或移除哪些软件包。
- 通过对同步数据库、软件包及其依赖项执行健全性检查,根据标志准备事务。
- 提交事务
- 如果适用,下载软件包 (
_alpm_sync_load
)。 - 如果存在适用的预先存在的 pacman
PreTransaction
钩子,则执行它们。 - 移除要替换、冲突或显式目标移除的软件包。
- 如果要添加软件包,则提交每个软件包
- 如果软件包具有安装脚本,则执行其
pre_install
函数(或者在升级或移除软件包的情况下执行pre_upgrade
或pre_remove
)。 - Pacman 删除软件包的先前版本中的所有文件(在升级或移除软件包的情况下)。但是,软件包中标记为配置文件的文件将保留(请参阅 /Pacnew 和 Pacsave)。
- Pacman 解压缩软件包并将其文件转储到文件系统中(在安装或升级软件包的情况下)。将覆盖保留的且手动修改的配置文件(请参阅上一步)的文件将以新名称 (.pacnew) 存储。
- 如果软件包具有安装脚本,则执行其
post_install
函数(或者在升级或移除软件包的情况下执行post_upgrade
或post_remove
)。
- 如果软件包具有安装脚本,则执行其
- 如果存在事务结束时适用的 pacman
PostTransaction
钩子,则执行它们。
- 如果适用,下载软件包 (
- 释放事务和事务资源(即数据库锁)。
配置
Pacman 设置位于 /etc/pacman.conf
中:这是用户配置程序以所需方式工作的位置。有关配置文件的深入信息,请参阅 pacman.conf(5)。
通用选项
通用选项位于 [options]
部分。请阅读 pacman.conf(5) 或查看默认的 pacman.conf
以获取有关此处可以执行的操作的信息。
更新前比较版本
要查看可用软件包的旧版本和新版本,请取消注释 /etc/pacman.conf
中的 “VerbosePkgLists” 行。pacman -Syu
的输出将如下所示
Package (6) Old Version New Version Net Change Download Size extra/libmariadbclient 10.1.9-4 10.1.10-1 0.03 MiB 4.35 MiB extra/libpng 1.6.19-1 1.6.20-1 0.00 MiB 0.23 MiB extra/mariadb 10.1.9-4 10.1.10-1 0.26 MiB 13.80 MiB
启用并行下载
可以使用 /etc/pacman.conf
中 [options]
下的 ParallelDownloads
设置并行下载(同时)的软件包数量。如果未设置该选项,软件包将按顺序下载。
跳过软件包升级
要跳过特定软件包的升级,请在 [options]
部分添加以下行
IgnorePkg=linux
对于多个软件包,请使用空格分隔的列表,或使用额外的 IgnorePkg
行。此外,可以使用 glob 模式。 如果您只想跳过软件包一次,也可以在命令行中使用 --ignore
选项 - 这次使用逗号分隔的列表。
仍然可以使用 pacman -S
升级被忽略的软件包:在这种情况下,pacman 会提醒您这些软件包已包含在 IgnorePkg
语句中。
跳过软件包组的升级
与软件包一样,也可以跳过整个软件包组
IgnoreGroup=gnome
跳过文件升级
所有使用 NoUpgrade
指令列出的文件在软件包安装/升级期间都不会被触及,并且新文件将以 .pacnew 扩展名安装。
NoUpgrade=path/to/file
可以像这样指定多个文件
NoUpgrade=path/to/file1 path/to/file2
跳过文件安装到系统
要始终跳过特定文件或目录的安装,请将它们列在 NoExtract
下。例如,要避免安装 systemd 单元,请使用以下内容
NoExtract=usr/lib/systemd/system/*
后面的规则会覆盖之前的规则,您可以通过在前面加上 !
来否定规则。
pacman.conf
中的 CheckSpace
选项会抑制此类警告,但请考虑空间检查功能将对所有软件包禁用。维护多个配置文件
如果您有多个配置文件(例如,主配置文件和启用 testing 仓库的配置文件),并且需要在配置之间共享选项,则可以使用在配置文件中声明的 Include
选项,例如:
Include = /path/to/common/settings
其中 /path/to/common/settings
文件包含两个配置的相同选项。
钩子
Pacman 可以从 /usr/share/libalpm/hooks/
目录运行事务前和事务后钩子;可以使用 pacman.conf
中的 HookDir
选项指定更多目录,默认为 /etc/pacman.d/hooks
。 钩子文件名称必须以 .hook 为后缀。 Pacman 钩子是非交互式的。
Pacman 钩子用于,例如,与 systemd-sysusers
和 systemd-tmpfiles
结合使用,以在软件包安装期间自动创建系统用户和文件。例如,tomcat8 指定它需要一个名为 tomcat8
的系统用户以及由此用户拥有的某些目录。 当 pacman 确定 tomcat8 包含指定用户和临时文件的文件时,pacman 钩子 systemd-sysusers.hook
和 systemd-tmpfiles.hook
会调用 systemd-sysusers
和 systemd-tmpfiles
。
有关 alpm 钩子的更多信息,请参阅 alpm-hooks(5)。
仓库和镜像
除了特殊的 [options] 部分外,pacman.conf
中的每个其他 [section]
都定义了一个要使用的软件包仓库。仓库 是软件包的逻辑集合,它们物理存储在一个或多个服务器上:因此,每个服务器都称为仓库的镜像。
仓库分为官方和非官方。 配置文件中仓库的顺序很重要; 当两个仓库中的软件包具有相同的名称时,无论版本号如何,首先列出的仓库将优先于文件中稍后列出的仓库。 为了在使用仓库之前添加它,您需要首先升级整个系统。
每个仓库部分都允许直接定义其镜像列表,或通过 Include
指令在专用的外部文件中定义; 例如,官方仓库的镜像包含在 /etc/pacman.d/mirrorlist
中。 有关镜像配置,请参阅 Mirrors 文章。
软件包缓存目录
Pacman 将下载的软件包文件存储在缓存中,目录由 pacman.conf
的 [options] 部分中的 CacheDir
指定(如果未设置,则默认为 /var/cache/pacman/pkg/
)。
即使只保留已安装软件包的最新版本,缓存目录也可能会随着时间的推移而增长。
如果您想将该目录移动到更方便的位置,请执行以下操作之一
- 在
pacman.conf
中将CacheDir
选项设置为新目录。 记住保留尾部斜杠。 这是推荐的解决方案。 - 在
/var/cache/pacman/pkg/
中挂载专用分区或例如 Btrfs 子卷。 - 在
/var/cache/pacman/pkg/
中绑定挂载选定的目录。
/var/cache/pacman/pkg/
目录到其他位置。 它会导致 pacman 行为异常,尤其是在 pacman 尝试更新自身时。软件包安全
Pacman 支持软件包签名,这为软件包增加了一层额外的安全性。 默认配置 SigLevel = Required DatabaseOptional
在全局级别为所有软件包启用签名验证。 这可以被每个仓库的 SigLevel
行覆盖。 有关软件包签名和签名验证的更多详细信息,请查看 pacman-key。
故障排除
“提交事务失败 (冲突文件)” 错误
如果您看到以下错误: [1]
error: could not prepare transaction error: failed to commit transaction (conflicting files) package: /path/to/file exists in filesystem Errors occurred, no packages were upgraded.
发生这种情况是因为 pacman 检测到文件冲突,并且根据设计,不会为您覆盖文件。 这是设计使然,而不是缺陷。
问题通常很容易解决(尽管为了确保安全,您应该尝试找出这些文件最初是如何到达那里的)。 一种安全的方法是首先检查另一个软件包是否拥有该文件 (pacman -Qo /path/to/file
)。 如果该文件由另一个软件包拥有,请提交错误报告。 如果该文件不属于另一个软件包,请重命名“存在于文件系统”中的文件,然后重新发出更新命令。 如果一切顺利,则可以删除该文件。
如果您手动安装了一个程序而没有使用 pacman,例如通过 make install
,则必须删除/卸载该程序及其所有文件。 另请参阅 Pacman 技巧#识别任何软件包未拥有的文件。
每个已安装的软件包都提供一个 /var/lib/pacman/local/package-version/files
文件,其中包含有关此软件包的元数据。 如果此文件损坏、为空或丢失,则在尝试更新软件包时会导致 file exists in filesystem
错误。 这种错误通常只涉及一个软件包。 您可以显式运行 pacman -S --overwrite glob package
以强制 pacman 覆盖与 glob
匹配的文件,而不是手动重命名然后在稍后删除属于该软件包的所有文件。
--overwrite
开关。 请参阅 系统维护#避免某些 pacman 命令。“提交事务失败 (无效或损坏的软件包)” 错误
在 /var/cache/pacman/pkg/
中查找 .part 文件(部分下载的软件包)并删除它们(通常是由 pacman.conf
中使用自定义 XferCommand
引起的)。
# find /var/cache/pacman/pkg/ -iname "*.part" -delete
如果 archlinux-keyring 过期,也可能出现相同的错误,从而阻止 pacman 验证签名。 有关修复方法以及如何在将来避免这种情况,请参阅 Pacman/软件包签名#定期升级系统。
“初始化事务失败 (无法锁定数据库)” 错误
当 pacman 即将更改软件包数据库时,例如安装软件包,它会在 /var/lib/pacman/db.lck
创建一个锁定文件。 这可以防止 pacman 的另一个实例同时尝试更改软件包数据库。
如果 pacman 在更改数据库时中断,则可能会保留此过时的锁定文件。 如果您确定没有 pacman 实例正在运行,则删除锁定文件
# rm /var/lib/pacman/db.lck
fuser /var/lib/pacman/db.lck
以验证是否仍有进程正在使用它。无法在安装时检索软件包
此错误表现为 Not found in sync db
、Target not found
或 Failed retrieving file
。
首先,确保软件包实际存在。 如果确定软件包存在,则您的软件包列表可能已过期。 尝试运行 pacman -Syu
以强制刷新所有软件包列表并升级。 另请确保选定的镜像是最新的,并且仓库配置正确。 您还可以使用 Reflector 来保持镜像最新。
也可能是包含软件包的仓库未在您的系统上启用,例如,软件包可能在 multilib 仓库中,但 multilib 未在您的 pacman.conf
中启用。
另请参阅 FAQ#为什么在官方仓库中每个共享库只有一个版本?。
修复由中断的升级导致系统无法启动
无论是由于断电、内核崩溃还是硬件故障,升级都可能中断。 在大多数情况下,不会造成太大损坏,但系统可能会无法启动。
- 准备一个USB 闪存安装介质并启动它。
- 挂载根文件系统。
arch-chroot
进入挂载的根文件系统。- 检查
/var/log/pacman.log
并通过向pacman -S
提供在失败的事务期间升级的整个软件包列表来复制确切的更新,并允许它重新安装,例如:
# pacman -S linux linux-headers systemd systemd-libs systemd-sysvcompat firefox texlive-basic texlive-fontsextra texlive-latex texlive-latexextra texlive-latexrecommended texlive-pictures
需要复制确切的升级,以确保正确的脚本和小工具和钩子将运行。
Pacman 在升级期间崩溃
如果 pacman 在删除软件包时因“数据库写入”错误而崩溃,并且此后重新安装或升级软件包失败,请执行以下操作
- 使用 Arch USB 闪存安装介质启动。 最好使用最新的介质,以便 pacman 版本与系统匹配/更新。
- 挂载系统的根文件系统,例如,以 root 身份
mount /dev/sdaX /mnt
,并使用df -h
检查挂载是否有足够的空间 - 也挂载 proc、sys 和 dev 文件系统:
mount -t proc proc /mnt/proc; mount --rbind /sys /mnt/sys; mount --rbind /dev /mnt/dev
- 如果系统使用默认数据库和目录位置,您现在可以更新系统的 pacman 数据库,并通过
pacman --root=/mnt --cachedir=/mnt/var/cache/pacman/pkg -Syu
以 root 身份升级它。- 或者,如果您无法更新/升级,请参阅 Pacman/技巧和窍门#重新安装所有软件包。
- 升级后,一种双重检查未升级但仍然损坏的软件包的方法:
find /mnt/usr/lib -size 0
- 然后通过
pacman --root /mnt --cachedir=/mnt/var/cache/pacman/pkg -S package
重新安装任何仍然损坏的软件包。
pacman: command not found
如果 /var/cache/pacman/pkg
是一个符号链接,pacman 将尝试创建一个目录来代替,因此在自我升级期间删除此符号链接。 这将导致更新失败。 结果,pacman 软件包的 /usr/bin/pacman
和其他内容将丢失。
永远不要符号链接 /var/cache/pacman/pkg
,因为它由 pacman 控制。 请改用 CacheDir
选项或绑定挂载; 请参阅 #软件包缓存目录。
如果您已经遇到此问题并破坏了您的系统,您可以手动从软件包中提取 /usr
内容以恢复 pacman,然后正确地重新安装它; 请参阅 FS#73306 和 相关论坛帖子 以了解详细信息。
手动重新安装 pacman
使用 pacman-static
pacman-staticAUR 是 pacman 的静态编译版本,因此即使系统上的库无法正常工作,它也能够运行。 当执行了部分升级并且 pacman 无法再运行时,这也可能会派上用场。
置顶评论和 PKGBUILD 提供了一种直接下载二进制文件的方法,该二进制文件可用于重新安装 pacman 或在部分升级的情况下升级整个系统。
使用外部 pacman
如果即使 pacman-static
也不起作用,则可以使用外部 pacman 进行恢复。 最简单的方法之一是使用 archiso,只需使用 --sysroot
或 --root
来指定要对其执行操作的系统的挂载点。 有关如何挂载 --sysroot
所需的必要文件系统,请参阅 Chroot#使用 chroot。
通过手动提取
即使 pacman 严重损坏,您也可以通过下载最新的软件包并将其提取到正确的位置来手动修复它。 要执行的大致步骤是
- 确定要安装的 pacman 依赖项
- 从您选择的镜像下载每个软件包
- 将每个软件包提取到根目录
- 使用
pacman -S --overwrite
重新安装这些软件包以相应地更新软件包数据库 - 进行完整的系统升级
如果您手头有一个健康的 Arch 系统,您可以使用以下命令查看完整的依赖项列表
$ pacman -Q $(pactree -u pacman)
但是您可能只需要更新其中的一些,具体取决于您的问题。 提取软件包的一个例子是
# tar -xvpwf package.tar.zst -C / --exclude .PKGINFO --exclude .INSTALL --exclude .MTREE --exclude .BUILDINFO
请注意使用 w
标志进行交互模式。 以非交互方式运行非常冒险,因为您最终可能会覆盖一个重要的文件。 还要注意以正确的顺序提取软件包(即,先提取依赖项)。 此论坛帖子 包含此过程的示例,其中只有几个 pacman 依赖项被破坏。
重启后出现“Unable to find root device”错误
最有可能的是,initramfs 在 内核 更新期间损坏(不正确使用 pacman 的 --overwrite
选项可能是原因之一)。 有两个选项; 首先,尝试 Fallback 条目。
Tab
键,或者按 e
键(对于 GRUB 或 systemd-boot),将其重命名为 initramfs-linux-fallback.img
,然后按 Enter
或 b
(取决于您的 启动加载程序)以使用新参数启动。系统启动后,从控制台或终端运行此命令(对于库存 linux 内核),以重建 initramfs 映像
# mkinitcpio -p linux
如果这不起作用,请从当前的 Arch 发行版(CD/DVD 或 USB 闪存盘)挂载您的根分区和启动分区到 /mnt
和 /mnt/boot
。 然后使用 arch-chroot chroot
# arch-chroot /mnt # pacman -Syu mkinitcpio systemd linux
重新安装内核(linux 软件包)将使用 mkinitcpio -p linux
自动重新生成 initramfs 映像。 无需单独执行此操作。
之后,建议您运行 exit
、umount /mnt/{boot,}
和 reboot
。
“警告:当前区域设置无效;使用默认 “C” 区域设置” 错误
正如错误消息所说,您的区域设置未正确配置。 请参阅 Locale。
Pacman 不遵守代理设置
确保相关环境变量($http_proxy
、$ftp_proxy
等)已设置。 如果您将 pacman 与 sudo 一起使用,则需要配置 sudo 以将这些环境变量传递给 pacman。 此外,确保 dirmngr 的配置在 /etc/pacman.d/gnupg/dirmngr.conf
中具有 honor-http-proxy
,以便在刷新密钥时遵守代理。
如何重新安装所有软件包,同时保留有关某些内容是显式安装还是作为依赖项安装的信息?
要重新安装所有原生软件包:pacman -Qnq | pacman -S -
或 pacman -S $(pacman -Qnq)
(-S
选项默认保留安装原因)。
然后,您将需要重新安装所有外部软件包,可以使用 pacman -Qmq
列出这些软件包。
看起来之前的 pacman 事务删除了或损坏了 pacman 本身所需的共享库。
要从这种情况中恢复,您需要手动将所需的库解压到您的文件系统中。 首先找到哪个软件包包含丢失的库,然后在 pacman 缓存 (/var/cache/pacman/pkg/
) 中找到它。 将所需的共享库解压到文件系统。 这将允许运行 pacman。
现在您需要重新安装损坏的软件包。 请注意,您需要使用 --overwrite
标志,因为您刚刚解压了系统文件,而 pacman 不知道这一点。 Pacman 将使用软件包中的文件正确替换我们的共享库文件。
就这样。 更新系统的其余部分。
软件包下载冻结
已报告一些关于网络问题阻止 pacman 更新/同步仓库的问题。 [2] [3] 当以原生方式安装 Arch Linux 时,通过将默认的 pacman 文件下载器替换为替代方案,这些问题已得到解决(有关更多详细信息,请参阅 提高 pacman 性能)。 当在 VirtualBox 中以访客操作系统安装 Arch Linux 时,通过在机器属性中使用主机接口而不是 NAT,也已解决此问题。
从镜像检索文件“core.db”失败
如果您收到此错误消息并且 镜像 正确,请尝试设置不同的名称服务器。
错误:“local-package.pkg.tar”:权限被拒绝
如果您想使用 pacman -U
在 sshfs 挂载上安装软件包并收到此错误,请将软件包移动到本地目录并再次尝试安装。
错误:无法确定 cachedir 挂载点 /var/cache/pacman/pkg
在 chroot 环境中执行例如 pacman -Syu
时遇到错误
error: could not determine cachedir mount point /var/cache/pacman/pkg error: failed to commit transaction (not enough free disk space)
这通常是由于在进入 chroot 时 chroot 目录不是挂载点引起的。 有关解决方案,请参阅 从现有 Linux 安装 Arch Linux#下载基本工具 中的说明,以及 arch-chroot(8) 以获取解释和使用绑定挂载使 chroot 目录成为挂载点的示例。
error: GPGME error: No data
如果您无法更新软件包并收到此错误,请在尝试更新之前尝试 rm -r /var/lib/pacman/sync/
。
如果删除同步文件没有帮助,请在使用 file /var/lib/pacman/sync/*
尝试更新之前检查同步文件是否为 gzip compressed data
。 路由器或代理可能会损坏下载。
如果同步文件类型正确,则可能是镜像服务器存在问题。 使用 pacman-conf -r core
和 pacman-conf -r extra
查找正在使用的镜像服务器。 将第一个返回的 url 粘贴到浏览器中,并检查是否返回了文件列表。 如果镜像返回错误,请在 /etc/pacman.d/mirrorlist
中注释掉它。
错误:GPGME 错误:一般错误和“:: 文件 /var/cache/pacman/pkg/<package>.pkg.tar.zst 已损坏(无效或损坏的软件包(PGP 签名))。
如果发生此错误,并且例如您无法更新系统或任何软件包,则可能是您已将 DISPLAY
设置为空白值,这似乎破坏了 GPG-Flow。
在这种情况下,unset DISPLAY
或将其设置为任意值很可能允许再次更新,以防上述任何选项尚未奏效。 有关更多详细信息,请参阅 此 帖子。
重新安装损坏或不同步的软件包
可以使用 pacman -Qk $pkg
检查 $pkg
软件包的已安装文件是否与其数据库版本中的文件匹配。 对于多个软件包,可以使用以下循环来重新安装所有缺少文件的软件包
# LC_ALL=C.UTF-8 pacman -Qk 2>/dev/null | grep -v ' 0 missing files' | cut -d: -f1 | while read -r package; do pacman -S "$package" --noconfirm done
假设您的本地数据库(位于 /var/lib/pacman
中)与 /
文件系统中的已安装软件包相比是最新的(例如,由于部分回滚),则此方法是使根文件系统与本地数据库重新同步的适当方法。