Flutter终端模拟器-Linux源编译

概述

本文记录的经验适用于以下需求

  • 1.fork 了 termux 仓库,想要改包名编译集成到自己的项目。
  • 2.完全的自己开发了一个终端模拟器。

Termux-app是一个Android上的Linux虚拟机工具,它拥有自己的包管理工具和软件源,可以实现很多Linux上的功能。源码地址:https://github.com/termux/termux-app

Termux在初始化安装时会从远端下载一个对应系统架构的bootstraps-arch.zip文件,它是一个Linux的基本环境,其目录结构如下:

1
2
3
4
5
6
7
8
9
10
bootstraps-arch/
├── bin
├── etc
├── include
├── lib
├── libexec
├── share
├── SYMLINKS.txt
├── tmp
└── var

这个 bootstrap 包含了最小的启动环境,有 bash、apt 等必备的执行程序,所以 termux app 在启动后,会下载这个 zip,然后解压到自己的环境。

为什么改了包名就要重新编译?

termux 的目录结构与 Linux 有差异,由于 termux 始终是作为一个android app 运行在设备上,所以在普通模式下,能是用的目录是 /data/data/com.termux,这意味着任何的程序都不能使用 /usr、/lib 等路径,需要在所有用到的路径前加上一个 prifix 变量,即 /data/data/com.termux/files

而这个 prifix 在程序中是被硬编码进去的,也就是说,一旦编译,则不能更改,所以如果我的包名是 com.nightmare 的话,即使下载了 termux 编译好的执行程序,它的工作目录也是在 /data/data/com.termux/files 下,这是我们不希望看到的。

开始编译

在 script 文件夹下有setup-archlinux.shsetup-ubuntu.shsetup-termux.sh这类的脚本,所以其实是可以在各个不同版本的 Linux 中进行编译的,但实际情况是,在 ubuntu、archlinux 等系统下直接编译,往往会有特别麻烦的编译错误需要处理,这些错误的导致大都来自于系统某个资源的依赖版本等,而且会把本机的环境搞得一团糟,最终编译下来,本机安装了很多我们可能不太会用到的环境。

编译平台:macOS 11.2

编译环境:docker

启动环境

编译 bootstrap

根据 generate-bootstraps.sh 这个脚本,我们可以先编译启动环境需要的包。

制作 deb 源

生成 bootstrap.zip

编译错误:下载失败

Termux-package 写入了 800多 个包的源码下载地址以及补丁方式,所以在编译的过程中极有可能遇见下载的源无法访问的情况。

例如在 packages 文件夹下的 apt 包,build.sh 部分代码如下:

1
2
TERMUX_PKG_VERSION=2.1.18
TERMUX_PKG_SRCURL=http://deb.debian.org/debian/pool/main/a/apt/apt_${TERMUX_PKG_VERSION}.tar.xz

当我访问 http://deb.debian.org/debian/pool/main/a/apt/apt_2.1.18.tar.xz 发现页面404了,
并且 http://deb.debian.org/debian/pool/main/a/apt/ 下只有 apt_2.1.20.tar.xz,apt_2.1.18.tar.xz 已经被删了。
而且仓库是才从原仓库 clone 下来的。

所以这个时候只有在其他的地方找到这个版本的下载地址。

1
TERMUX_PKG_SRCURL=http://mirrors.sohu.com/raspbian/raspbian/pool/main/a/apt/apt_2.1.18.tar.xz

不能够直接提升版本的原因在于,在每个包的文件夹下,还有一些 .patch 文件,这些文件是专门适配这个版本的包做出的补丁。

编译错误:SHA256 校验失败

这个校验码是来保值下载的源码压缩包是完整无损的,但是有的时候的确是相应包的源做了更新,导致实际的 sha256 值有了变化,这种时候也会存在校验失败的问题。

zlib 下载会检测 VPN,需要暂时关闭梯子,下载完成后再打开

作者

梦魇兽

发布于

2021-02-24

更新于

2023-06-24

许可协议

评论