Skip to content
Xeonacid edited this page Nov 6, 2023 · 16 revisions

项目内容

我们的主要工作内容是把 Arch Linux x86_64 架构上的软件包移植到 RISC-V 64 位架构上。由于指令集差异,这些软件有时没法在 RISC-V 上正常通过编译和打包流程。我们的工作就是给软件的上游提交报告,尝试移植并 暂时 将修复的 patch 放在这个仓库里。我们的终极目标是消灭这个代码仓库里的所有修复,在上游把 RISC-V 支持的优先级提高。

工作流程

在我们的 公会页 有一列的包状态记录,最右边标记 *failing 的都是无法正常编译打包的软件包。第二列 user 列则记录了这个包目前由哪位用户负责,你可以在工会页里找一个还没有人领取的包尝试进行修复。

每个失败的包的名字都是一个超链接,你可以点进去看失败的构建日志

前言

在你开始成为仓库贡献者之前,请先认真通读一遍 贡献指南

打包前的环境部署

在修复之前,你需要先配置一下必要的构建环境。

archbuild

Arch Linux 里软件打包的脚本是一个 PKGBUILD 文件,其本质是一个 shell 脚本。如果你不熟悉 PKGBUILD 脚本的内容,可以在 Arch Linux Wiki 阅读学习。如果你不熟悉打包流程,可以参考 Creating packages 。在本仓库工作的过程中我们会默认你已经有了基础的打包知识基础。

为了在干净的环境下打包,Arch Linux 提供了 devtools 工具。而我们需要为 RISC-V 架构适配的 devtools。这个特殊版本的 devtools 在 Arch Linux CN 上有提前修改打包好的版本,你可以添加 Arch Linux CN 源并使用 pacman 下载。

具体操作步骤可以看 ArchBuild 脚本解读#安装 devtools

QEMU

在平常调试的时候,你可能需要一个虚拟机环境。你可以参考这一篇 Wiki 来搭建 QEMU user 虚拟机。如果你需要 QEMU system 虚拟机,可以参考使用 CoelacanthusHex/archriscv-scriptlet的脚本。

其他工具

你将需要 pkgctl 工具来拉取跟踪上游 PKGBUILD,以及 updpkgsums 帮助你生成文件校验。

sudo pacman -S devtools pacman-contrib

开始打包

首先调用 pkgctl 脚本下载 PKGBUILD 脚本,这里我拿 stylua 这个包举例 :

pkgctl repo clone stylua

请注意,pkgctl 默认使用 git 获取 PKGBUILD 脚本.

由于仓库并不允许匿名访问,请确保你注册了 Arch Linux GitLab 账户并在其中添加了你的 SSH Key。否则将无法获取仓库内容。

Please make sure you have the correct access rights and the repository exists.
==> ERROR: failed to clone stylua

你也可以通过指定下载协议的方式来匿名获取 PKGBUILD 脚本,但需要注意访问频率,避免触发限制。

pkgctl repo clone --protocol=https stylua

执行完命令之后,在当前目录下将会有一个同名的目录,而 PKGBUILD 则在该目录下:

cd stylua
ls

进入目录之后,我们首先需要修改 PKGBUILD 的 arch 数组。你可以使用自己熟悉的编辑器在数组里添加值 riscv64,也可以用下面这个命令:

setconf PKGBUILD arch '(riscv64 x86_64)'

修改完之后执行 extra-riscv64-build 命令来执行打包构建:

# 创建一个临时目录
CACHE_DIR=$(mktemp -d -t 'rvpkg_cache_XXX')
extra-riscv64-build -- -d "$CACHE_DIR:/var/cache/pacman/pkg/"

如果嫌修改 arch 又改回来麻烦,可以用 makepkg 的 -A 选项:

extra-riscv64-build -- -d "$CACHE_DIR:/var/cache/pacman/pkg/" -- -A

extra-riscv64-build 是 devtools 包提供的一个脚本文件,它可以帮我们快速建起干净的 chroot 环境并在里面执行 makepkg 打包。而 -d 参数将会被传给下一层的 makechrootpkg 程序。-d 参数主要提供了一层路径映射,它将会把 $CACHE_DIR 路径绑定到 chroot 里的 /var/cache/pacman/pkg 目录上。一个独立干净的目录可以避免缓存签名冲突。

执行完命令之后等待一会,archbuild 会报错:

...

error: Error loading target specification: Could not find specification for target "riscv64-unknown-linux-gnu".

...

接下来就是要尝试进行修复了。

尝试修复

软件包的源码通常放在 /var/lib/archbuild/extra-riscv64/$USER/build/ 目录下。继续拿 stylua 举例子,stylua 的源码则在 /var/lib/archbuild/extra-riscv64/$USER/build/stylua/src/stylua-$pkgver 目录下。其中,$USER 是你上次执行 extra-riscv64-build 时的用户名,$pkgver 则是当前软件包的版本。你可以把这整个目录复制到你的 qemu 虚拟机里进行局部测试。

推荐在进行修改之前先把所有文件加入 git 的跟踪里,方便之后生成 patch: git init && git add . && git commit -m "Init"。修改出可用的源码之后,直接执行 git diff > fix-xxx.patch 就可以出补丁。


在 stylua 这个例子里,我们不需要修改源码,我们要修改是 PKGBUILD。Arch Linux 上游在打包时加入了一行 --target "$CARCH-unknown-linux-gnu" 参数来限制依赖的架构。而 $CARCH 变量在我们的环境里值是 riscv64,rustc 编译器期望值的则是 riscv64gc [^1] ,所以依赖下载失败了。

这个问题目前的默认修复方式是把这个 target 参数删除。

[^1]: 关于这个问题的更详细讨论可以参考这个 issue: https://github.com/felixonmars/archriscv-packages/issues/670

提交更改

在 PKGBUILD 目录里,首先我们需要把 arch 数组改回原样,肥猫的脚本会把这个变量处理好,我们不需要提交这个变量的修改。然后使用命令 git diff --no-prefix > riscv64.patch 生成一个名为 riscv64.patch 的补丁。使用编辑器打开这个补丁,在文件头部只需要保留 PKGBUILD 部分:

diff --git PKGBUILD PKGBUILD                          <- 这一行可以全部删掉
index 06cfef1..38870de 100644                         <- 这一行可以全部删掉
--- PKGBUILD                                          <- 只留下 PKGBUILD 字样
+++ PKGBUILD                                          <- 同上

除了手动编辑补丁之外, 我们也可以直接在 PKGBUILD 所在目录下执行以下命令直接生成补丁:

git diff --no-prefix --relative | tail -n +3  > riscv64.patch

接下来 fork 这个仓库,创建一个新的分支,分支名可以随意定,一般和包名同名。在根目录下创建一个与包名同名的目录,把 riscv64.patch 文件复制进去。然后填写 commit: addpkg: stylua,并推送到到远程分支发起 PR。

🔙 返回主页

Clone this wiki locally